Upgrade to font awesome 7, make sure chart includes currencies outside of limits.

This commit is contained in:
James Cole
2025-07-30 06:59:58 +02:00
parent 7451659824
commit 333004c4d9
4 changed files with 95 additions and 36 deletions

View File

@@ -49,7 +49,7 @@ class BudgetController extends Controller
use CleansChartData;
use ValidatesUserGroupTrait;
protected array $acceptedRoles = [UserRoleEnum::READ_ONLY];
protected array $acceptedRoles = [UserRoleEnum::READ_ONLY];
protected OperationsRepositoryInterface $opsRepository;
private BudgetLimitRepositoryInterface $blRepository;
@@ -77,16 +77,17 @@ class BudgetController extends Controller
/**
* TODO see autocomplete/accountcontroller
* @throws FireflyException
*/
public function dashboard(DateRequest $request): JsonResponse
{
$params = $request->getAll();
$params = $request->getAll();
/** @var Carbon $start */
$start = $params['start'];
$start = $params['start'];
/** @var Carbon $end */
$end = $params['end'];
$end = $params['end'];
// code from FrontpageChartGenerator, but not in separate class
$budgets = $this->repository->getActiveBudgets();
@@ -108,16 +109,52 @@ class BudgetController extends Controller
{
// get all limits:
$limits = $this->blRepository->getBudgetLimits($budget, $start, $end);
$rows = [];
// 'currency_id' => string '1' (length=1)
// 'currency_code' => string 'EUR' (length=3)
// 'currency_name' => string 'Euro' (length=4)
// 'currency_symbol' => string '€' (length=3)
// 'currency_decimal_places' => int 2
// 'start' => string '2025-07-01T00:00:00+02:00' (length=25)
// 'end' => string '2025-07-31T23:59:59+02:00' (length=25)
// 'budgeted' => string '100.000000000000' (length=16)
// 'spent' => string '-421.230000000000' (length=17)
// 'left' => string '0' (length=1)
// 'overspent' => string '321.230000000000' (length=16)
$rows = [];
// instead of using the budget limits as a thing to collect all expenses,
// use the budget range itself to collect and group them,
// AND THEN add budgeted amounts from the limits to the rows.
$spent = $this->opsRepository->listExpenses($start, $end, null, new Collection([$budget]));
$expenses = $this->processExpenses($budget->id, $spent, $start, $end);
/**
* @var int $currencyId
* @var array $row
*/
foreach ($expenses as $currencyId => $row) {
// budgeted, left and overspent are now 0.
$limit = $this->filterLimit($currencyId, $limits);
if (null !== $limit) {
$row['budgeted'] = $limit->amount;
$row['left'] = bcsub($row['budgeted'], bcmul($row['spent'], '-1'));
$row['overspent'] = bcmul($row['left'], '-1');
$row['left'] = 1 === bccomp($row['left'], '0') ? $row['left'] : '0';
$row['overspent'] = 1 === bccomp($row['overspent'], '0') ? $row['overspent'] : '0';
}
$rows[] = $row;
}
// if no limits
if (0 === $limits->count()) {
// return as a single item in an array
$rows = $this->noBudgetLimits($budget, $start, $end);
}
if ($limits->count() > 0) {
$rows = $this->budgetLimits($budget, $limits);
}
// if (0 === $limits->count()) {
// return as a single item in an array
// $rows = $this->noBudgetLimits($budget, $start, $end);
// }
// is always an array
$return = [];
foreach ($rows as $row) {
@@ -170,7 +207,7 @@ class BudgetController extends Controller
* This array contains the expenses in this budget. Grouped per currency.
* The grouping is on the main currency only.
*
* @var int $currencyId
* @var int $currencyId
* @var array $block
*/
foreach ($spent as $currencyId => $block) {
@@ -188,7 +225,7 @@ class BudgetController extends Controller
'left' => '0',
'overspent' => '0',
];
$currentBudgetArray = $block['budgets'][$budgetId];
$currentBudgetArray = $block['budgets'][$budgetId];
// var_dump($return);
/** @var array $journal */
@@ -229,7 +266,7 @@ class BudgetController extends Controller
private function processLimit(Budget $budget, BudgetLimit $limit): array
{
Log::debug(sprintf('Created new ExchangeRateConverter in %s', __METHOD__));
$end = clone $limit->end_date;
$end = clone $limit->end_date;
$end->endOfDay();
$spent = $this->opsRepository->listExpenses($limit->start_date, $end, null, new Collection([$budget]));
$limitCurrencyId = $limit->transaction_currency_id;
@@ -237,8 +274,8 @@ class BudgetController extends Controller
/** @var array $entry */
// only spent the entry where the entry's currency matches the budget limit's currency
// so $filtered will only have 1 or 0 entries
$filtered = array_filter($spent, fn ($entry) => $entry['currency_id'] === $limitCurrencyId);
$result = $this->processExpenses($budget->id, $filtered, $limit->start_date, $end);
$filtered = array_filter($spent, fn($entry) => $entry['currency_id'] === $limitCurrencyId);
$result = $this->processExpenses($budget->id, $filtered, $limit->start_date, $end);
if (1 === count($result)) {
$compare = bccomp($limit->amount, (string)app('steam')->positive($result[$limitCurrencyId]['spent']));
$result[$limitCurrencyId]['budgeted'] = $limit->amount;
@@ -253,4 +290,14 @@ class BudgetController extends Controller
return $result;
}
private function filterLimit(int $currencyId, Collection $limits): ?BudgetLimit
{
foreach ($limits as $limit) {
if ($limit->transaction_currency_id === $currencyId) {
return $limit;
}
}
return null;
}
}

2
package-lock.json generated
View File

@@ -12525,7 +12525,7 @@
"resources/assets/v2": {
"hasInstallScript": true,
"dependencies": {
"@fortawesome/fontawesome-free": "^7.0.0",
"@fortawesome/fontawesome-free": "^7",
"@popperjs/core": "^2.11.8",
"admin-lte": "^4.0.0-rc4",
"alpinejs": "^3.13.7",

View File

@@ -16,7 +16,7 @@
"vite-plugin-manifest-sri": "^0.2.0"
},
"dependencies": {
"@fortawesome/fontawesome-free": "^7.0.0",
"@fortawesome/fontawesome-free": "^7",
"@popperjs/core": "^2.11.8",
"admin-lte": "^4.0.0-rc4",
"alpinejs": "^3.13.7",

View File

@@ -26,7 +26,28 @@ $danger: #CD5029 !default;
$primary: #1E6581 !default;
$success: #64B624 !default;
// admin LTE
@use "admin-lte/src/scss/adminlte" with (
$color-mode-type: $color-mode-type,
$link-decoration: $link-decoration,
$font-family-sans-serif: $font-family-sans-serif,
$danger: $danger,
$primary: $primary,
$success: $success
);
@use '@fortawesome/fontawesome-free/scss/variables' with (
$font-path: "@fortawesome/fontawesome-free/webfonts"
);
@use '@fortawesome/fontawesome-free/scss/fontawesome';
@use '@fortawesome/fontawesome-free/scss/fa' as fa;
@use '@fortawesome/fontawesome-free/scss/solid.scss' as fa-solid;
@use '@fortawesome/fontawesome-free/scss/brands.scss' as fa-brands;
@use '@fortawesome/fontawesome-free/scss/regular.scss' as fa-regular;
// some local CSS
.skip-links {display: none;}
/*
@@ -59,16 +80,7 @@ h3.hover-expand:hover {
appearance: auto;
}
// Bootstrap
// @import "bootstrap/scss/bootstrap";
// admin LTE
@import "adminlte-filtered";
// @import "~bootstrap-sass/assets/stylesheets/bootstrap";
// hover buttons
// edit buttons
.hidden-edit-button {
cursor: pointer;
}
@@ -76,12 +88,12 @@ td:not(:hover) .hidden-edit-button {
visibility: hidden;
}
// Bootstrap
// @import "bootstrap/scss/bootstrap";
// @import "~bootstrap-sass/assets/stylesheets/bootstrap";
// hover buttons
// Font awesome
//@import "~font-awesome/css/font-awesome";
$fa-font-path: "@fortawesome/fontawesome-free/webfonts";
@import "@fortawesome/fontawesome-free/scss/fontawesome.scss";
@import "@fortawesome/fontawesome-free/scss/solid.scss";
@import "@fortawesome/fontawesome-free/scss/brands.scss";
@import "@fortawesome/fontawesome-free/scss/regular.scss";