Some optimisations.

This commit is contained in:
James Cole
2015-05-16 08:05:04 +02:00
parent bed1adc367
commit b94781aef1
4 changed files with 116 additions and 9 deletions

View File

@@ -232,6 +232,69 @@ class ReportQuery implements ReportQueryInterface
return $data;
}
/**
* This method returns all "expense" journals in a certain period, which are both transfers to a shared account
* and "ordinary" withdrawals. The query used is almost equal to ReportQueryInterface::journalsByRevenueAccount but it does
* not group and returns different fields.
*
* @param Carbon $start
* @param Carbon $end
* @param bool $includeShared
*
* @return Collection
*
*/
public function expenseInPeriod(Carbon $start, Carbon $end, $includeShared = false) {
$query = $this->queryJournalsWithTransactions($start, $end);
if ($includeShared === false) {
// only get withdrawals not from a shared account
// and transfers from a shared account.
$query->where(
function (Builder $query) {
$query->where(
function (Builder $q) {
$q->where('transaction_types.type', 'Withdrawal');
$q->where('acm_from.data', '!=', '"sharedAsset"');
}
);
$query->orWhere(
function (Builder $q) {
$q->where('transaction_types.type', 'Transfer');
$q->where('acm_to.data', '=', '"sharedAsset"');
}
);
}
);
} else {
// any withdrawal is fine.
$query->where('transaction_types.type', 'Withdrawal');
}
$query->groupBy('transaction_journals.id')->orderBy('transaction_journals.date');
// get everything, decrypt and return
$data = $query->get(
['transaction_journals.id',
'transaction_journals.description',
'transaction_journals.encrypted',
'transaction_types.type',
DB::Raw('SUM(`t_from`.`amount`) as `queryAmount`'),
'transaction_journals.date',
't_to.account_id as account_id',
'ac_to.name as name',
'ac_to.encrypted as account_encrypted'
]
);
$data->each(
function (Model $object) {
$object->name = intval($object->account_encrypted) == 1 ? Crypt::decrypt($object->name) : $object->name;
}
);
$data->sortByDesc('queryAmount');
return $data;
}
/**
* Gets a list of expenses grouped by the budget they were filed under.
*

View File

@@ -86,6 +86,20 @@ interface ReportQueryInterface
*/
public function incomeInPeriod(Carbon $start, Carbon $end, $includeShared = false);
/**
* This method returns all "expense" journals in a certain period, which are both transfers to a shared account
* and "ordinary" withdrawals. The query used is almost equal to ReportQueryInterface::journalsByRevenueAccount but it does
* not group and returns different fields.
*
* @param Carbon $start
* @param Carbon $end
* @param bool $includeShared
*
* @return Collection
*
*/
public function expenseInPeriod(Carbon $start, Carbon $end, $includeShared = false);
/**
* Gets a list of expenses grouped by the budget they were filed under.
*

View File

@@ -266,8 +266,8 @@ class ReportController extends Controller
$subTitleIcon = 'fa-bar-chart';
$totalExpense = 0;
$totalIncome = 0;
$incomeTopLength = 5;
$expenseTopLength = 10;
$incomeTopLength = 8;
$expenseTopLength = 8;
if ($shared == 'shared') {
$shared = true;
@@ -327,10 +327,35 @@ class ReportController extends Controller
* GET ALL EXPENSES
* Summarized.
*/
$expenses = $this->query->journalsByExpenseAccount($date, $end, $shared);
foreach ($expenses as $expense) {
$totalExpense += floatval($expense->queryAmount);
$set = $this->query->expenseInPeriod($date, $end, $shared);
// group, sort and sum:
$expenses = [];
foreach ($set as $entry) {
$id = $entry->account_id;
$totalExpense += floatval($entry->queryAmount);
if (isset($expenses[$id])) {
$expenses[$id]['amount'] += floatval($entry->queryAmount);
$expenses[$id]['count']++;
} else {
$expenses[$id] = [
'amount' => floatval($entry->queryAmount),
'name' => $entry->name,
'count' => 1,
'id' => $id,
];
}
}
// sort with callback:
uasort(
$expenses, function ($a, $b) {
if ($a['amount'] == $b['amount']) {
return 0;
}
return ($a['amount'] < $b['amount']) ? -1 : 1;
}
);
unset($set, $id);
return view(
'reports.year',

View File

@@ -125,16 +125,21 @@
</div>
<table class="table">
{% set sum =0 %}
{% for expense in expenses %}
{% for row in expenses %}
{% if loop.index > expenseTopLength %}
<tr class="collapse out expenseCollapsed">
{% else %}
<tr>
{% endif %}
<td><a href="{{ route('accounts.show',expense.id) }}">{{ expense.name }}</a></td>
<td><span class="text-danger">{{ expense.queryAmount|formatAmountPlain }}</span></td>
<td>
<a href="{{ route('accounts.show',row.id) }}">{{ row.name }}</a>
{% if row.count > 1 %}
<br /><small>{{ row.count }} {{ 'transactions'|_|lower }}</small>
{% endif %}
</td>
<td><span class="text-danger">{{ (row.amount*-1)|formatAmountPlain }}</span></td>
</tr>
{% set sum = sum + (expense.queryAmount * -1) %}
{% set sum = sum + row.amount %}
{% endfor %}
{% if expenses|length > expenseTopLength %}
<tr>