From 4ba1c5bcfcb444a9d078d23122a13f5df56b95f6 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Tue, 26 Nov 2024 18:04:32 +0100
Subject: [PATCH 001/167] New set of PHP 8.4 files
---
app/Http/Controllers/Controller.php | 3 +
app/Http/Controllers/HomeController.php | 1 +
app/Models/AccountType.php | 28 ++--
app/Models/AutoBudget.php | 6 +-
app/Models/RecurrenceRepetition.php | 8 +-
app/Models/TransactionType.php | 14 +-
composer.json | 2 +-
composer.lock | 206 ++++++++++++------------
8 files changed, 137 insertions(+), 131 deletions(-)
diff --git a/app/Http/Controllers/Controller.php b/app/Http/Controllers/Controller.php
index 772020f672..c5db5b85f7 100644
--- a/app/Http/Controllers/Controller.php
+++ b/app/Http/Controllers/Controller.php
@@ -44,6 +44,9 @@ abstract class Controller extends BaseController
use UserNavigation;
use ValidatesRequests;
+ // fails on PHP < 8.4
+ public protected(set) string $name;
+
protected string $dateTimeFormat;
protected string $monthAndDayFormat;
protected string $monthFormat;
diff --git a/app/Http/Controllers/HomeController.php b/app/Http/Controllers/HomeController.php
index 72fc6ba722..0370161be8 100644
--- a/app/Http/Controllers/HomeController.php
+++ b/app/Http/Controllers/HomeController.php
@@ -43,6 +43,7 @@ use Illuminate\Support\Facades\Log;
*/
class HomeController extends Controller
{
+
/**
* HomeController constructor.
*/
diff --git a/app/Models/AccountType.php b/app/Models/AccountType.php
index 013b7269bd..6517f16dee 100644
--- a/app/Models/AccountType.php
+++ b/app/Models/AccountType.php
@@ -35,46 +35,46 @@ class AccountType extends Model
{
use ReturnsIntegerIdTrait;
- /** @deprecated */
+ #[\Deprecated]
public const string ASSET = 'Asset account';
- /** @deprecated */
+ #[\Deprecated]
public const string BENEFICIARY = 'Beneficiary account';
- /** @deprecated */
+ #[\Deprecated]
public const string CASH = 'Cash account';
- /** @deprecated */
+ #[\Deprecated]
public const string CREDITCARD = 'Credit card';
- /** @deprecated */
+ #[\Deprecated]
public const string DEBT = 'Debt';
- /** @deprecated */
+ #[\Deprecated]
public const string DEFAULT = 'Default account';
- /** @deprecated */
+ #[\Deprecated]
public const string EXPENSE = 'Expense account';
- /** @deprecated */
+ #[\Deprecated]
public const string IMPORT = 'Import account';
- /** @deprecated */
+ #[\Deprecated]
public const string INITIAL_BALANCE = 'Initial balance account';
- /** @deprecated */
+ #[\Deprecated]
public const string LIABILITY_CREDIT = 'Liability credit account';
- /** @deprecated */
+ #[\Deprecated]
public const string LOAN = 'Loan';
- /** @deprecated */
+ #[\Deprecated]
public const string MORTGAGE = 'Mortgage';
- /** @deprecated */
+ #[\Deprecated]
public const string RECONCILIATION = 'Reconciliation account';
- /** @deprecated */
+ #[\Deprecated]
public const string REVENUE = 'Revenue account';
protected $casts
diff --git a/app/Models/AutoBudget.php b/app/Models/AutoBudget.php
index b67ca3be23..4504522edf 100644
--- a/app/Models/AutoBudget.php
+++ b/app/Models/AutoBudget.php
@@ -39,13 +39,13 @@ class AutoBudget extends Model
use ReturnsIntegerIdTrait;
use SoftDeletes;
- /** @deprecated */
+ #[\Deprecated]
public const int AUTO_BUDGET_ADJUSTED = 3;
- /** @deprecated */
+ #[\Deprecated]
public const int AUTO_BUDGET_RESET = 1;
- /** @deprecated */
+ #[\Deprecated]
public const int AUTO_BUDGET_ROLLOVER = 2;
protected $fillable = ['budget_id', 'amount', 'period'];
diff --git a/app/Models/RecurrenceRepetition.php b/app/Models/RecurrenceRepetition.php
index f3daa1657b..5680b09c51 100644
--- a/app/Models/RecurrenceRepetition.php
+++ b/app/Models/RecurrenceRepetition.php
@@ -39,16 +39,16 @@ class RecurrenceRepetition extends Model
use ReturnsIntegerIdTrait;
use SoftDeletes;
- /** @deprecated */
+ #[\Deprecated]
public const int WEEKEND_DO_NOTHING = 1;
- /** @deprecated */
+ #[\Deprecated]
public const int WEEKEND_SKIP_CREATION = 2;
- /** @deprecated */
+ #[\Deprecated]
public const int WEEKEND_TO_FRIDAY = 3;
- /** @deprecated */
+ #[\Deprecated]
public const int WEEKEND_TO_MONDAY = 4;
protected $casts
diff --git a/app/Models/TransactionType.php b/app/Models/TransactionType.php
index dfc466cf3a..d0b948a469 100644
--- a/app/Models/TransactionType.php
+++ b/app/Models/TransactionType.php
@@ -38,25 +38,25 @@ class TransactionType extends Model
use ReturnsIntegerIdTrait;
use SoftDeletes;
- /** @deprecated */
+ #[\Deprecated]
public const string DEPOSIT = 'Deposit';
- /** @deprecated */
+ #[\Deprecated]
public const string INVALID = 'Invalid';
- /** @deprecated */
+ #[\Deprecated]
public const string LIABILITY_CREDIT = 'Liability credit';
- /** @deprecated */
+ #[\Deprecated]
public const string OPENING_BALANCE = 'Opening balance';
- /** @deprecated */
+ #[\Deprecated]
public const string RECONCILIATION = 'Reconciliation';
- /** @deprecated */
+ #[\Deprecated]
public const string TRANSFER = 'Transfer';
- /** @deprecated */
+ #[\Deprecated]
public const string WITHDRAWAL = 'Withdrawal';
protected $casts
diff --git a/composer.json b/composer.json
index b28b135953..c85437acdc 100644
--- a/composer.json
+++ b/composer.json
@@ -65,7 +65,7 @@
}
],
"require": {
- "php": ">=8.3",
+ "php": ">=8.4",
"ext-bcmath": "*",
"ext-curl": "*",
"ext-fileinfo": "*",
diff --git a/composer.lock b/composer.lock
index 761703e201..79b33dcb29 100644
--- a/composer.lock
+++ b/composer.lock
@@ -4,7 +4,7 @@
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
"This file is @generated automatically"
],
- "content-hash": "eb0a48bb5142f68837c2ca1f9b82aa0d",
+ "content-hash": "f813653aac7be9e344fb4ca91513df61",
"packages": [
{
"name": "bacon/bacon-qr-code",
@@ -1936,20 +1936,21 @@
},
{
"name": "laravel-json-api/core",
- "version": "v4.2.0",
+ "version": "v4.3.0",
"source": {
"type": "git",
"url": "https://github.com/laravel-json-api/core.git",
- "reference": "5a3d1771a63e222d902ccd7d57c9323c8aac8d32"
+ "reference": "37c4734dbd5c9fd7f2d5cca490553a0a664b2a69"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/laravel-json-api/core/zipball/5a3d1771a63e222d902ccd7d57c9323c8aac8d32",
- "reference": "5a3d1771a63e222d902ccd7d57c9323c8aac8d32",
+ "url": "https://api.github.com/repos/laravel-json-api/core/zipball/37c4734dbd5c9fd7f2d5cca490553a0a664b2a69",
+ "reference": "37c4734dbd5c9fd7f2d5cca490553a0a664b2a69",
"shasum": ""
},
"require": {
"ext-json": "*",
+ "illuminate/auth": "^11.33",
"illuminate/contracts": "^11.0",
"illuminate/http": "^11.0",
"illuminate/support": "^11.0",
@@ -1994,9 +1995,9 @@
],
"support": {
"issues": "https://github.com/laravel-json-api/core/issues",
- "source": "https://github.com/laravel-json-api/core/tree/v4.2.0"
+ "source": "https://github.com/laravel-json-api/core/tree/v4.3.0"
},
- "time": "2024-08-21T19:29:20+00:00"
+ "time": "2024-11-26T16:37:40+00:00"
},
{
"name": "laravel-json-api/eloquent",
@@ -2547,23 +2548,23 @@
},
{
"name": "laravel/framework",
- "version": "v11.33.2",
+ "version": "v11.34.0",
"source": {
"type": "git",
"url": "https://github.com/laravel/framework.git",
- "reference": "6b9832751cf8eed18b3c73df5071f78f0682aa5d"
+ "reference": "858184e8def3f20f588f9ab88355003750845a6c"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/laravel/framework/zipball/6b9832751cf8eed18b3c73df5071f78f0682aa5d",
- "reference": "6b9832751cf8eed18b3c73df5071f78f0682aa5d",
+ "url": "https://api.github.com/repos/laravel/framework/zipball/858184e8def3f20f588f9ab88355003750845a6c",
+ "reference": "858184e8def3f20f588f9ab88355003750845a6c",
"shasum": ""
},
"require": {
"brick/math": "^0.9.3|^0.10.2|^0.11|^0.12",
"composer-runtime-api": "^2.2",
"doctrine/inflector": "^2.0.5",
- "dragonmantank/cron-expression": "^3.3.2",
+ "dragonmantank/cron-expression": "^3.4",
"egulias/email-validator": "^3.2.1|^4.0",
"ext-ctype": "*",
"ext-filter": "*",
@@ -2573,35 +2574,36 @@
"ext-session": "*",
"ext-tokenizer": "*",
"fruitcake/php-cors": "^1.3",
- "guzzlehttp/guzzle": "^7.8",
+ "guzzlehttp/guzzle": "^7.8.2",
"guzzlehttp/uri-template": "^1.0",
"laravel/prompts": "^0.1.18|^0.2.0|^0.3.0",
"laravel/serializable-closure": "^1.3|^2.0",
"league/commonmark": "^2.2.1",
- "league/flysystem": "^3.8.0",
+ "league/flysystem": "^3.25.1",
+ "league/flysystem-local": "^3.25.1",
"monolog/monolog": "^3.0",
- "nesbot/carbon": "^2.72.2|^3.0",
+ "nesbot/carbon": "^2.72.2|^3.4",
"nunomaduro/termwind": "^2.0",
"php": "^8.2",
"psr/container": "^1.1.1|^2.0.1",
"psr/log": "^1.0|^2.0|^3.0",
"psr/simple-cache": "^1.0|^2.0|^3.0",
"ramsey/uuid": "^4.7",
- "symfony/console": "^7.0",
- "symfony/error-handler": "^7.0",
- "symfony/finder": "^7.0",
- "symfony/http-foundation": "^7.0",
- "symfony/http-kernel": "^7.0",
- "symfony/mailer": "^7.0",
- "symfony/mime": "^7.0",
- "symfony/polyfill-php83": "^1.28",
- "symfony/process": "^7.0",
- "symfony/routing": "^7.0",
- "symfony/uid": "^7.0",
- "symfony/var-dumper": "^7.0",
+ "symfony/console": "^7.0.3",
+ "symfony/error-handler": "^7.0.3",
+ "symfony/finder": "^7.0.3",
+ "symfony/http-foundation": "^7.0.3",
+ "symfony/http-kernel": "^7.0.3",
+ "symfony/mailer": "^7.0.3",
+ "symfony/mime": "^7.0.3",
+ "symfony/polyfill-php83": "^1.31",
+ "symfony/process": "^7.0.3",
+ "symfony/routing": "^7.0.3",
+ "symfony/uid": "^7.0.3",
+ "symfony/var-dumper": "^7.0.3",
"tijsverkoyen/css-to-inline-styles": "^2.2.5",
- "vlucas/phpdotenv": "^5.4.1",
- "voku/portable-ascii": "^2.0"
+ "vlucas/phpdotenv": "^5.6.1",
+ "voku/portable-ascii": "^2.0.2"
},
"conflict": {
"mockery/mockery": "1.6.8",
@@ -2651,29 +2653,32 @@
},
"require-dev": {
"ably/ably-php": "^1.0",
- "aws/aws-sdk-php": "^3.235.5",
+ "aws/aws-sdk-php": "^3.322.9",
"ext-gmp": "*",
- "fakerphp/faker": "^1.23",
- "league/flysystem-aws-s3-v3": "^3.0",
- "league/flysystem-ftp": "^3.0",
- "league/flysystem-path-prefixing": "^3.3",
- "league/flysystem-read-only": "^3.3",
- "league/flysystem-sftp-v3": "^3.0",
+ "fakerphp/faker": "^1.24",
+ "guzzlehttp/promises": "^2.0.3",
+ "guzzlehttp/psr7": "^2.4",
+ "league/flysystem-aws-s3-v3": "^3.25.1",
+ "league/flysystem-ftp": "^3.25.1",
+ "league/flysystem-path-prefixing": "^3.25.1",
+ "league/flysystem-read-only": "^3.25.1",
+ "league/flysystem-sftp-v3": "^3.25.1",
"mockery/mockery": "^1.6.10",
"nyholm/psr7": "^1.2",
"orchestra/testbench-core": "^9.6",
- "pda/pheanstalk": "^5.0",
+ "pda/pheanstalk": "^5.0.6",
"phpstan/phpstan": "^1.11.5",
- "phpunit/phpunit": "^10.5|^11.0",
- "predis/predis": "^2.0.2",
+ "phpunit/phpunit": "^10.5.35|^11.3.6",
+ "predis/predis": "^2.3",
"resend/resend-php": "^0.10.0",
- "symfony/cache": "^7.0",
- "symfony/http-client": "^7.0",
- "symfony/psr-http-message-bridge": "^7.0"
+ "symfony/cache": "^7.0.3",
+ "symfony/http-client": "^7.0.3",
+ "symfony/psr-http-message-bridge": "^7.0.3",
+ "symfony/translation": "^7.0.3"
},
"suggest": {
"ably/ably-php": "Required to use the Ably broadcast driver (^1.0).",
- "aws/aws-sdk-php": "Required to use the SQS queue driver, DynamoDb failed job storage, and SES mail driver (^3.235.5).",
+ "aws/aws-sdk-php": "Required to use the SQS queue driver, DynamoDb failed job storage, and SES mail driver (^3.322.9).",
"brianium/paratest": "Required to run tests in parallel (^7.0|^8.0).",
"ext-apcu": "Required to use the APC cache driver.",
"ext-fileinfo": "Required to use the Filesystem class.",
@@ -2687,16 +2692,16 @@
"fakerphp/faker": "Required to use the eloquent factory builder (^1.9.1).",
"filp/whoops": "Required for friendly error pages in development (^2.14.3).",
"laravel/tinker": "Required to use the tinker console command (^2.0).",
- "league/flysystem-aws-s3-v3": "Required to use the Flysystem S3 driver (^3.0).",
- "league/flysystem-ftp": "Required to use the Flysystem FTP driver (^3.0).",
- "league/flysystem-path-prefixing": "Required to use the scoped driver (^3.3).",
- "league/flysystem-read-only": "Required to use read-only disks (^3.3)",
- "league/flysystem-sftp-v3": "Required to use the Flysystem SFTP driver (^3.0).",
+ "league/flysystem-aws-s3-v3": "Required to use the Flysystem S3 driver (^3.25.1).",
+ "league/flysystem-ftp": "Required to use the Flysystem FTP driver (^3.25.1).",
+ "league/flysystem-path-prefixing": "Required to use the scoped driver (^3.25.1).",
+ "league/flysystem-read-only": "Required to use read-only disks (^3.25.1)",
+ "league/flysystem-sftp-v3": "Required to use the Flysystem SFTP driver (^3.25.1).",
"mockery/mockery": "Required to use mocking (^1.6).",
"nyholm/psr7": "Required to use PSR-7 bridging features (^1.2).",
"pda/pheanstalk": "Required to use the beanstalk queue driver (^5.0).",
"phpunit/phpunit": "Required to use assertions and run tests (^10.5|^11.0).",
- "predis/predis": "Required to use the predis connector (^2.0.2).",
+ "predis/predis": "Required to use the predis connector (^2.3).",
"psr/http-message": "Required to allow Storage::put to accept a StreamInterface (^1.0).",
"pusher/pusher-php-server": "Required to use the Pusher broadcast driver (^6.0|^7.0).",
"resend/resend-php": "Required to enable support for the Resend mail transport (^0.10.0).",
@@ -2752,7 +2757,7 @@
"issues": "https://github.com/laravel/framework/issues",
"source": "https://github.com/laravel/framework"
},
- "time": "2024-11-19T22:47:13+00:00"
+ "time": "2024-11-26T15:11:52+00:00"
},
{
"name": "laravel/passport",
@@ -2891,16 +2896,16 @@
},
{
"name": "laravel/sanctum",
- "version": "v4.0.4",
+ "version": "v4.0.5",
"source": {
"type": "git",
"url": "https://github.com/laravel/sanctum.git",
- "reference": "819782c75aaf2b08da1765503893bd2b8023d3b3"
+ "reference": "fe361b9a63407a228f884eb78d7217f680b50140"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/laravel/sanctum/zipball/819782c75aaf2b08da1765503893bd2b8023d3b3",
- "reference": "819782c75aaf2b08da1765503893bd2b8023d3b3",
+ "url": "https://api.github.com/repos/laravel/sanctum/zipball/fe361b9a63407a228f884eb78d7217f680b50140",
+ "reference": "fe361b9a63407a228f884eb78d7217f680b50140",
"shasum": ""
},
"require": {
@@ -2951,7 +2956,7 @@
"issues": "https://github.com/laravel/sanctum/issues",
"source": "https://github.com/laravel/sanctum"
},
- "time": "2024-11-15T14:47:23+00:00"
+ "time": "2024-11-26T14:36:23+00:00"
},
{
"name": "laravel/serializable-closure",
@@ -3016,16 +3021,16 @@
},
{
"name": "laravel/slack-notification-channel",
- "version": "v3.4.0",
+ "version": "v3.4.1",
"source": {
"type": "git",
"url": "https://github.com/laravel/slack-notification-channel.git",
- "reference": "8ffbb9f0578956cc192bffc8d75f5b07beb35aa3"
+ "reference": "f43f63f1e0d22de1ded93425e4a9a5f977bfe34c"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/laravel/slack-notification-channel/zipball/8ffbb9f0578956cc192bffc8d75f5b07beb35aa3",
- "reference": "8ffbb9f0578956cc192bffc8d75f5b07beb35aa3",
+ "url": "https://api.github.com/repos/laravel/slack-notification-channel/zipball/f43f63f1e0d22de1ded93425e4a9a5f977bfe34c",
+ "reference": "f43f63f1e0d22de1ded93425e4a9a5f977bfe34c",
"shasum": ""
},
"require": {
@@ -3075,22 +3080,22 @@
],
"support": {
"issues": "https://github.com/laravel/slack-notification-channel/issues",
- "source": "https://github.com/laravel/slack-notification-channel/tree/v3.4.0"
+ "source": "https://github.com/laravel/slack-notification-channel/tree/v3.4.1"
},
- "time": "2024-10-24T15:06:08+00:00"
+ "time": "2024-11-21T15:06:30+00:00"
},
{
"name": "laravel/ui",
- "version": "v4.5.2",
+ "version": "v4.6.0",
"source": {
"type": "git",
"url": "https://github.com/laravel/ui.git",
- "reference": "c75396f63268c95b053c8e4814eb70e0875e9628"
+ "reference": "a34609b15ae0c0512a0cf47a21695a2729cb7f93"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/laravel/ui/zipball/c75396f63268c95b053c8e4814eb70e0875e9628",
- "reference": "c75396f63268c95b053c8e4814eb70e0875e9628",
+ "url": "https://api.github.com/repos/laravel/ui/zipball/a34609b15ae0c0512a0cf47a21695a2729cb7f93",
+ "reference": "a34609b15ae0c0512a0cf47a21695a2729cb7f93",
"shasum": ""
},
"require": {
@@ -3138,9 +3143,9 @@
"ui"
],
"support": {
- "source": "https://github.com/laravel/ui/tree/v4.5.2"
+ "source": "https://github.com/laravel/ui/tree/v4.6.0"
},
- "time": "2024-05-08T18:07:10+00:00"
+ "time": "2024-11-21T15:06:41+00:00"
},
{
"name": "lcobucci/clock",
@@ -5150,21 +5155,21 @@
},
{
"name": "php-http/guzzle7-adapter",
- "version": "1.0.0",
+ "version": "1.1.0",
"source": {
"type": "git",
"url": "https://github.com/php-http/guzzle7-adapter.git",
- "reference": "fb075a71dbfa4847cf0c2938c4e5a9c478ef8b01"
+ "reference": "03a415fde709c2f25539790fecf4d9a31bc3d0eb"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/php-http/guzzle7-adapter/zipball/fb075a71dbfa4847cf0c2938c4e5a9c478ef8b01",
- "reference": "fb075a71dbfa4847cf0c2938c4e5a9c478ef8b01",
+ "url": "https://api.github.com/repos/php-http/guzzle7-adapter/zipball/03a415fde709c2f25539790fecf4d9a31bc3d0eb",
+ "reference": "03a415fde709c2f25539790fecf4d9a31bc3d0eb",
"shasum": ""
},
"require": {
"guzzlehttp/guzzle": "^7.0",
- "php": "^7.2 | ^8.0",
+ "php": "^7.3 | ^8.0",
"php-http/httplug": "^2.0",
"psr/http-client": "^1.0"
},
@@ -5175,14 +5180,11 @@
},
"require-dev": {
"php-http/client-integration-tests": "^3.0",
+ "php-http/message-factory": "^1.1",
+ "phpspec/prophecy-phpunit": "^2.0",
"phpunit/phpunit": "^8.0|^9.3"
},
"type": "library",
- "extra": {
- "branch-alias": {
- "dev-master": "0.2.x-dev"
- }
- },
"autoload": {
"psr-4": {
"Http\\Adapter\\Guzzle7\\": "src/"
@@ -5206,9 +5208,9 @@
],
"support": {
"issues": "https://github.com/php-http/guzzle7-adapter/issues",
- "source": "https://github.com/php-http/guzzle7-adapter/tree/1.0.0"
+ "source": "https://github.com/php-http/guzzle7-adapter/tree/1.1.0"
},
- "time": "2021-03-09T07:35:15+00:00"
+ "time": "2024-11-26T11:14:36+00:00"
},
{
"name": "php-http/httplug",
@@ -10443,16 +10445,16 @@
"packages-dev": [
{
"name": "barryvdh/laravel-debugbar",
- "version": "v3.14.7",
+ "version": "v3.14.9",
"source": {
"type": "git",
"url": "https://github.com/barryvdh/laravel-debugbar.git",
- "reference": "f484b8c9124de0b163da39958331098ffcd4a65e"
+ "reference": "2e805a6bd4e1aa83774316bb062703c65d0691ef"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/barryvdh/laravel-debugbar/zipball/f484b8c9124de0b163da39958331098ffcd4a65e",
- "reference": "f484b8c9124de0b163da39958331098ffcd4a65e",
+ "url": "https://api.github.com/repos/barryvdh/laravel-debugbar/zipball/2e805a6bd4e1aa83774316bb062703c65d0691ef",
+ "reference": "2e805a6bd4e1aa83774316bb062703c65d0691ef",
"shasum": ""
},
"require": {
@@ -10511,7 +10513,7 @@
],
"support": {
"issues": "https://github.com/barryvdh/laravel-debugbar/issues",
- "source": "https://github.com/barryvdh/laravel-debugbar/tree/v3.14.7"
+ "source": "https://github.com/barryvdh/laravel-debugbar/tree/v3.14.9"
},
"funding": [
{
@@ -10523,7 +10525,7 @@
"type": "github"
}
],
- "time": "2024-11-14T09:12:35+00:00"
+ "time": "2024-11-25T14:51:20+00:00"
},
{
"name": "barryvdh/laravel-ide-helper",
@@ -10731,16 +10733,16 @@
},
{
"name": "composer/class-map-generator",
- "version": "1.4.0",
+ "version": "1.5.0",
"source": {
"type": "git",
"url": "https://github.com/composer/class-map-generator.git",
- "reference": "98bbf6780e56e0fd2404fe4b82eb665a0f93b783"
+ "reference": "4b0a223cf5be7c9ee7e0ef1bc7db42b4a97c9915"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/composer/class-map-generator/zipball/98bbf6780e56e0fd2404fe4b82eb665a0f93b783",
- "reference": "98bbf6780e56e0fd2404fe4b82eb665a0f93b783",
+ "url": "https://api.github.com/repos/composer/class-map-generator/zipball/4b0a223cf5be7c9ee7e0ef1bc7db42b4a97c9915",
+ "reference": "4b0a223cf5be7c9ee7e0ef1bc7db42b4a97c9915",
"shasum": ""
},
"require": {
@@ -10749,10 +10751,10 @@
"symfony/finder": "^4.4 || ^5.3 || ^6 || ^7"
},
"require-dev": {
- "phpstan/phpstan": "^1.6",
- "phpstan/phpstan-deprecation-rules": "^1",
- "phpstan/phpstan-phpunit": "^1",
- "phpstan/phpstan-strict-rules": "^1.1",
+ "phpstan/phpstan": "^1.12 || ^2",
+ "phpstan/phpstan-deprecation-rules": "^1 || ^2",
+ "phpstan/phpstan-phpunit": "^1 || ^2",
+ "phpstan/phpstan-strict-rules": "^1.1 || ^2",
"phpunit/phpunit": "^8",
"symfony/filesystem": "^5.4 || ^6"
},
@@ -10784,7 +10786,7 @@
],
"support": {
"issues": "https://github.com/composer/class-map-generator/issues",
- "source": "https://github.com/composer/class-map-generator/tree/1.4.0"
+ "source": "https://github.com/composer/class-map-generator/tree/1.5.0"
},
"funding": [
{
@@ -10800,7 +10802,7 @@
"type": "tidelift"
}
],
- "time": "2024-10-03T18:14:00+00:00"
+ "time": "2024-11-25T16:11:06+00:00"
},
{
"name": "composer/pcre",
@@ -11218,16 +11220,16 @@
},
{
"name": "laravel-json-api/testing",
- "version": "v3.0.0",
+ "version": "v3.0.1",
"source": {
"type": "git",
"url": "https://github.com/laravel-json-api/testing.git",
- "reference": "1ada998d2087479351e01dd22ca13a00a96b4118"
+ "reference": "5ec2a84e725f93b6e0f79091b92c30bec88fe639"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/laravel-json-api/testing/zipball/1ada998d2087479351e01dd22ca13a00a96b4118",
- "reference": "1ada998d2087479351e01dd22ca13a00a96b4118",
+ "url": "https://api.github.com/repos/laravel-json-api/testing/zipball/5ec2a84e725f93b6e0f79091b92c30bec88fe639",
+ "reference": "5ec2a84e725f93b6e0f79091b92c30bec88fe639",
"shasum": ""
},
"require": {
@@ -11277,9 +11279,9 @@
],
"support": {
"issues": "https://github.com/laravel-json-api/testing/issues",
- "source": "https://github.com/laravel-json-api/testing/tree/v3.0.0"
+ "source": "https://github.com/laravel-json-api/testing/tree/v3.0.1"
},
- "time": "2024-03-12T20:30:38+00:00"
+ "time": "2024-11-26T16:49:53+00:00"
},
{
"name": "maximebf/debugbar",
@@ -13565,7 +13567,7 @@
"prefer-stable": false,
"prefer-lowest": false,
"platform": {
- "php": ">=8.3",
+ "php": ">=8.4",
"ext-bcmath": "*",
"ext-curl": "*",
"ext-fileinfo": "*",
From c25c0d37c5969ac1caf9bcc00232fb862a85eb6d Mon Sep 17 00:00:00 2001
From: James Cole
Date: Wed, 27 Nov 2024 08:08:52 +0100
Subject: [PATCH 002/167] Replace constants with enums.
---
app/Models/AccountType.php | 2 +-
config/firefly.php | 632 ++++++++++++++++++-------------------
2 files changed, 317 insertions(+), 317 deletions(-)
diff --git a/app/Models/AccountType.php b/app/Models/AccountType.php
index 6517f16dee..0ef77adcc2 100644
--- a/app/Models/AccountType.php
+++ b/app/Models/AccountType.php
@@ -44,7 +44,7 @@ class AccountType extends Model
#[\Deprecated]
public const string CASH = 'Cash account';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string CREDITCARD = 'Credit card';
#[\Deprecated]
diff --git a/config/firefly.php b/config/firefly.php
index 1cce0a20e0..2b651de7d9 100644
--- a/config/firefly.php
+++ b/config/firefly.php
@@ -22,9 +22,9 @@
declare(strict_types=1);
+use FireflyIII\Enums\AccountTypeEnum;
use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Models\Account;
-use FireflyIII\Models\AccountType;
use FireflyIII\Models\Attachment;
use FireflyIII\Models\AvailableBudget;
use FireflyIII\Models\Bill;
@@ -226,14 +226,14 @@ return [
// account types that may have or set a currency
'valid_currency_account_types' => [
- AccountType::ASSET,
- AccountType::LOAN,
- AccountType::DEBT,
- AccountType::MORTGAGE,
- AccountType::CASH,
- AccountType::INITIAL_BALANCE,
- AccountType::LIABILITY_CREDIT,
- AccountType::RECONCILIATION,
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::MORTGAGE->value,
+ AccountTypeEnum::CASH->value,
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::LIABILITY_CREDIT->value,
+ AccountTypeEnum::RECONCILIATION->value,
],
// "value must be in this list" values
@@ -324,7 +324,7 @@ return [
'application/json',
],
'accountRoles' => ['defaultAsset', 'sharedAsset', 'savingAsset', 'ccAsset', 'cashWalletAsset'],
- 'valid_liabilities' => [AccountType::DEBT, AccountType::LOAN, AccountType::MORTGAGE],
+ 'valid_liabilities' => [AccountTypeEnum::DEBT->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::MORTGAGE->value],
'ccTypes' => ['monthlyFull' => 'Full payment every month'],
'credit_card_types' => ['monthlyFull'],
@@ -351,60 +351,60 @@ return [
'liability' => 'Liabilities',
],
'subIconsByIdentifier' => [
- 'asset' => 'fa-money',
- AccountType::ASSET => 'fa-money',
- AccountType::DEFAULT => 'fa-money',
- AccountType::CASH => 'fa-money',
- 'expense' => 'fa-shopping-cart',
- AccountType::EXPENSE => 'fa-shopping-cart',
- AccountType::BENEFICIARY => 'fa-shopping-cart',
- 'revenue' => 'fa-download',
- AccountType::REVENUE => 'fa-download',
- 'import' => 'fa-download',
- AccountType::IMPORT => 'fa-download',
- 'liabilities' => 'fa-ticket',
+ 'asset' => 'fa-money',
+ AccountTypeEnum::ASSET->value => 'fa-money',
+ AccountTypeEnum::DEFAULT->value => 'fa-money',
+ AccountTypeEnum::CASH->value => 'fa-money',
+ 'expense' => 'fa-shopping-cart',
+ AccountTypeEnum::EXPENSE->value => 'fa-shopping-cart',
+ AccountTypeEnum::BENEFICIARY->value => 'fa-shopping-cart',
+ 'revenue' => 'fa-download',
+ AccountTypeEnum::REVENUE->value => 'fa-download',
+ 'import' => 'fa-download',
+ AccountTypeEnum::IMPORT->value => 'fa-download',
+ 'liabilities' => 'fa-ticket',
],
'accountTypesByIdentifier' => [
- 'asset' => [AccountType::DEFAULT, AccountType::ASSET],
- 'expense' => [AccountType::EXPENSE, AccountType::BENEFICIARY],
- 'revenue' => [AccountType::REVENUE],
- 'import' => [AccountType::IMPORT],
- 'liabilities' => [AccountType::LOAN, AccountType::DEBT, AccountType::CREDITCARD, AccountType::MORTGAGE],
+ 'asset' => [AccountTypeEnum::DEFAULT->value, AccountTypeEnum::ASSET->value],
+ 'expense' => [AccountTypeEnum::EXPENSE->value, AccountTypeEnum::BENEFICIARY->value],
+ 'revenue' => [AccountTypeEnum::REVENUE->value],
+ 'import' => [AccountTypeEnum::IMPORT->value],
+ 'liabilities' => [AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::CREDITCARD->value, AccountTypeEnum::MORTGAGE->value],
],
'accountTypeByIdentifier' => [
- 'asset' => [AccountType::ASSET],
- 'expense' => [AccountType::EXPENSE],
- 'revenue' => [AccountType::REVENUE],
- 'opening' => [AccountType::INITIAL_BALANCE],
- 'initial' => [AccountType::INITIAL_BALANCE],
- 'import' => [AccountType::IMPORT],
- 'reconcile' => [AccountType::RECONCILIATION],
- 'loan' => [AccountType::LOAN],
- 'debt' => [AccountType::DEBT],
- 'mortgage' => [AccountType::MORTGAGE],
- 'liabilities' => [AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE, AccountType::CREDITCARD],
- 'liability' => [AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE, AccountType::CREDITCARD],
+ 'asset' => [AccountTypeEnum::ASSET->value],
+ 'expense' => [AccountTypeEnum::EXPENSE->value],
+ 'revenue' => [AccountTypeEnum::REVENUE->value],
+ 'opening' => [AccountTypeEnum::INITIAL_BALANCE->value],
+ 'initial' => [AccountTypeEnum::INITIAL_BALANCE->value],
+ 'import' => [AccountTypeEnum::IMPORT->value],
+ 'reconcile' => [AccountTypeEnum::RECONCILIATION->value],
+ 'loan' => [AccountTypeEnum::LOAN->value],
+ 'debt' => [AccountTypeEnum::DEBT->value],
+ 'mortgage' => [AccountTypeEnum::MORTGAGE->value],
+ 'liabilities' => [AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value, AccountTypeEnum::CREDITCARD->value],
+ 'liability' => [AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value, AccountTypeEnum::CREDITCARD->value],
],
'shortNamesByFullName' => [
- AccountType::DEFAULT => 'asset',
- AccountType::ASSET => 'asset',
- AccountType::IMPORT => 'import',
- AccountType::EXPENSE => 'expense',
- AccountType::BENEFICIARY => 'expense',
- AccountType::REVENUE => 'revenue',
- AccountType::CASH => 'cash',
- AccountType::INITIAL_BALANCE => 'initial-balance',
- AccountType::RECONCILIATION => 'reconciliation',
- AccountType::CREDITCARD => 'liabilities',
- AccountType::LOAN => 'liabilities',
- AccountType::DEBT => 'liabilities',
- AccountType::MORTGAGE => 'liabilities',
+ AccountTypeEnum::DEFAULT->value => 'asset',
+ AccountTypeEnum::ASSET->value => 'asset',
+ AccountTypeEnum::IMPORT->value => 'import',
+ AccountTypeEnum::EXPENSE->value => 'expense',
+ AccountTypeEnum::BENEFICIARY->value => 'expense',
+ AccountTypeEnum::REVENUE->value => 'revenue',
+ AccountTypeEnum::CASH->value => 'cash',
+ AccountTypeEnum::INITIAL_BALANCE->value => 'initial-balance',
+ AccountTypeEnum::RECONCILIATION->value => 'reconciliation',
+ AccountTypeEnum::CREDITCARD->value => 'liabilities',
+ AccountTypeEnum::LOAN->value => 'liabilities',
+ AccountTypeEnum::DEBT->value => 'liabilities',
+ AccountTypeEnum::MORTGAGE->value => 'liabilities',
],
'shortLiabilityNameByFullName' => [
- AccountType::CREDITCARD => 'creditcard',
- AccountType::LOAN => AccountType::LOAN,
- AccountType::DEBT => AccountType::DEBT,
- AccountType::MORTGAGE => AccountType::MORTGAGE,
+ AccountTypeEnum::CREDITCARD->value => 'creditcard',
+ AccountTypeEnum::LOAN->value => AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::DEBT->value => AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::MORTGAGE->value => AccountTypeEnum::MORTGAGE->value,
],
'transactionTypesByType' => [
'expenses' => ['Withdrawal'],
@@ -430,7 +430,7 @@ return [
'transfers' => 'fa-exchange',
],
- 'bindables' => [
+ 'bindables' => [
// models
'account' => Account::class,
'attachment' => Attachment::class,
@@ -488,7 +488,7 @@ return [
'userGroupBill' => UserGroupBill::class,
'userGroup' => UserGroup::class,
],
- 'rule-actions' => [
+ 'rule-actions' => [
'set_category' => SetCategory::class,
'clear_category' => ClearCategory::class,
'set_budget' => SetBudget::class,
@@ -522,7 +522,7 @@ return [
// 'set_foreign_amount' => SetForeignAmount::class,
// 'set_foreign_currency' => SetForeignCurrency::class,
],
- 'context-rule-actions' => [
+ 'context-rule-actions' => [
'set_category',
'set_budget',
'add_tag',
@@ -541,321 +541,321 @@ return [
'convert_transfer',
],
- 'test-triggers' => [
+ 'test-triggers' => [
'limit' => 10,
'range' => 200,
],
// expected source types for each transaction type, in order of preference.
- 'expected_source_types' => [
+ 'expected_source_types' => [
'source' => [
- TransactionTypeModel::WITHDRAWAL => [AccountType::ASSET, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
- TransactionTypeEnum::DEPOSIT->value => [AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE, AccountType::REVENUE, AccountType::CASH],
- TransactionTypeModel::TRANSFER => [AccountType::ASSET, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
- TransactionTypeModel::OPENING_BALANCE => [
- AccountType::INITIAL_BALANCE,
- AccountType::ASSET,
- AccountType::LOAN,
- AccountType::DEBT,
- AccountType::MORTGAGE,
+ TransactionTypeEnum::WITHDRAWAL->value => [AccountTypeEnum::ASSET->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
+ TransactionTypeEnum::DEPOSIT->value => [AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value, AccountTypeEnum::REVENUE->value, AccountTypeEnum::CASH->value],
+ TransactionTypeEnum::TRANSFER->value => [AccountTypeEnum::ASSET->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
+ TransactionTypeEnum::OPENING_BALANCE->value => [
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::MORTGAGE->value,
],
- TransactionTypeModel::RECONCILIATION => [AccountType::RECONCILIATION, AccountType::ASSET],
- TransactionTypeModel::LIABILITY_CREDIT => [AccountType::LIABILITY_CREDIT, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
+ TransactionTypeEnum::RECONCILIATION->value => [AccountTypeEnum::RECONCILIATION->value, AccountTypeEnum::ASSET->value],
+ TransactionTypeEnum::LIABILITY_CREDIT->value => [AccountTypeEnum::LIABILITY_CREDIT->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
// in case no transaction type is known yet, it could be anything.
'none' => [
- AccountType::ASSET,
- AccountType::EXPENSE,
- AccountType::REVENUE,
- AccountType::LOAN,
- AccountType::DEBT,
- AccountType::MORTGAGE,
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::EXPENSE->value,
+ AccountTypeEnum::REVENUE->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::MORTGAGE->value,
],
],
'destination' => [
- TransactionTypeModel::WITHDRAWAL => [
- AccountType::LOAN,
- AccountType::DEBT,
- AccountType::MORTGAGE,
- AccountType::EXPENSE,
- AccountType::CASH,
+ TransactionTypeEnum::WITHDRAWAL->value => [
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::MORTGAGE->value,
+ AccountTypeEnum::EXPENSE->value,
+ AccountTypeEnum::CASH->value,
],
- TransactionTypeEnum::DEPOSIT->value => [AccountType::ASSET, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
- TransactionTypeModel::TRANSFER => [AccountType::ASSET, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
- TransactionTypeModel::OPENING_BALANCE => [
- AccountType::INITIAL_BALANCE,
- AccountType::ASSET,
- AccountType::LOAN,
- AccountType::DEBT,
- AccountType::MORTGAGE,
+ TransactionTypeEnum::DEPOSIT->value => [AccountTypeEnum::ASSET->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
+ TransactionTypeEnum::TRANSFER->value => [AccountTypeEnum::ASSET->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
+ TransactionTypeEnum::OPENING_BALANCE->value => [
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::MORTGAGE->value,
],
- TransactionTypeModel::RECONCILIATION => [AccountType::RECONCILIATION, AccountType::ASSET],
- TransactionTypeModel::LIABILITY_CREDIT => [AccountType::LIABILITY_CREDIT, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
+ TransactionTypeEnum::RECONCILIATION->value => [AccountTypeEnum::RECONCILIATION->value, AccountTypeEnum::ASSET->value],
+ TransactionTypeEnum::LIABILITY_CREDIT->value => [AccountTypeEnum::LIABILITY_CREDIT->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
],
],
- 'allowed_opposing_types' => [
+ 'allowed_opposing_types' => [
'source' => [
- AccountType::ASSET => [
- AccountType::ASSET,
- AccountType::CASH,
- AccountType::DEBT,
- AccountType::EXPENSE,
- AccountType::INITIAL_BALANCE,
- AccountType::LOAN,
- AccountType::RECONCILIATION,
- AccountType::MORTGAGE,
+ AccountTypeEnum::ASSET->value => [
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::CASH->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::EXPENSE->value,
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::RECONCILIATION->value,
+ AccountTypeEnum::MORTGAGE->value,
],
- AccountType::CASH => [AccountType::ASSET],
- AccountType::DEBT => [
- AccountType::ASSET,
- AccountType::DEBT,
- AccountType::EXPENSE,
- AccountType::INITIAL_BALANCE,
- AccountType::LOAN,
- AccountType::MORTGAGE,
- AccountType::LIABILITY_CREDIT,
+ AccountTypeEnum::CASH->value => [AccountTypeEnum::ASSET->value],
+ AccountTypeEnum::DEBT->value => [
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::EXPENSE->value,
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::MORTGAGE->value,
+ AccountTypeEnum::LIABILITY_CREDIT->value,
],
- AccountType::EXPENSE => [], // is not allowed as a source.
- AccountType::INITIAL_BALANCE => [AccountType::ASSET, AccountType::DEBT, AccountType::LOAN, AccountType::MORTGAGE],
- AccountType::LOAN => [
- AccountType::ASSET,
- AccountType::DEBT,
- AccountType::EXPENSE,
- AccountType::INITIAL_BALANCE,
- AccountType::LOAN,
- AccountType::MORTGAGE,
- AccountType::LIABILITY_CREDIT,
+ AccountTypeEnum::EXPENSE->value => [], // is not allowed as a source.
+ AccountTypeEnum::INITIAL_BALANCE->value => [AccountTypeEnum::ASSET->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::MORTGAGE->value],
+ AccountTypeEnum::LOAN->value => [
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::EXPENSE->value,
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::MORTGAGE->value,
+ AccountTypeEnum::LIABILITY_CREDIT->value,
],
- AccountType::MORTGAGE => [
- AccountType::ASSET,
- AccountType::DEBT,
- AccountType::EXPENSE,
- AccountType::INITIAL_BALANCE,
- AccountType::LOAN,
- AccountType::MORTGAGE,
- AccountType::LIABILITY_CREDIT,
+ AccountTypeEnum::MORTGAGE->value => [
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::EXPENSE->value,
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::MORTGAGE->value,
+ AccountTypeEnum::LIABILITY_CREDIT->value,
],
- AccountType::RECONCILIATION => [AccountType::ASSET],
- AccountType::REVENUE => [AccountType::ASSET, AccountType::DEBT, AccountType::LOAN, AccountType::MORTGAGE],
- AccountType::LIABILITY_CREDIT => [AccountType::DEBT, AccountType::LOAN, AccountType::MORTGAGE],
+ AccountTypeEnum::RECONCILIATION->value => [AccountTypeEnum::ASSET->value],
+ AccountTypeEnum::REVENUE->value => [AccountTypeEnum::ASSET->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::MORTGAGE->value],
+ AccountTypeEnum::LIABILITY_CREDIT->value => [AccountTypeEnum::DEBT->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::MORTGAGE->value],
],
'destination' => [
- AccountType::ASSET => [
- AccountType::ASSET,
- AccountType::CASH,
- AccountType::DEBT,
- AccountType::INITIAL_BALANCE,
- AccountType::LOAN,
- AccountType::MORTGAGE,
- AccountType::RECONCILIATION,
- AccountType::REVENUE,
+ AccountTypeEnum::ASSET->value => [
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::CASH->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::MORTGAGE->value,
+ AccountTypeEnum::RECONCILIATION->value,
+ AccountTypeEnum::REVENUE->value,
],
- AccountType::CASH => [AccountType::ASSET],
- AccountType::DEBT => [
- AccountType::ASSET,
- AccountType::DEBT,
- AccountType::INITIAL_BALANCE,
- AccountType::LOAN,
- AccountType::MORTGAGE,
- AccountType::REVENUE,
+ AccountTypeEnum::CASH->value => [AccountTypeEnum::ASSET->value],
+ AccountTypeEnum::DEBT->value => [
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::MORTGAGE->value,
+ AccountTypeEnum::REVENUE->value,
],
- AccountType::EXPENSE => [AccountType::ASSET, AccountType::DEBT, AccountType::LOAN, AccountType::MORTGAGE],
- AccountType::INITIAL_BALANCE => [AccountType::ASSET, AccountType::DEBT, AccountType::LOAN, AccountType::MORTGAGE],
- AccountType::LOAN => [
- AccountType::ASSET,
- AccountType::DEBT,
- AccountType::INITIAL_BALANCE,
- AccountType::LOAN,
- AccountType::MORTGAGE,
- AccountType::REVENUE,
+ AccountTypeEnum::EXPENSE->value => [AccountTypeEnum::ASSET->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::MORTGAGE->value],
+ AccountTypeEnum::INITIAL_BALANCE->value => [AccountTypeEnum::ASSET->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::MORTGAGE->value],
+ AccountTypeEnum::LOAN->value => [
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::MORTGAGE->value,
+ AccountTypeEnum::REVENUE->value,
],
- AccountType::MORTGAGE => [
- AccountType::ASSET,
- AccountType::DEBT,
- AccountType::INITIAL_BALANCE,
- AccountType::LOAN,
- AccountType::MORTGAGE,
- AccountType::REVENUE,
+ AccountTypeEnum::MORTGAGE->value => [
+ AccountTypeEnum::ASSET->value,
+ AccountTypeEnum::DEBT->value,
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::LOAN->value,
+ AccountTypeEnum::MORTGAGE->value,
+ AccountTypeEnum::REVENUE->value,
],
- AccountType::RECONCILIATION => [AccountType::ASSET],
- AccountType::REVENUE => [], // is not allowed as a destination
- AccountType::LIABILITY_CREDIT => [], // is not allowed as a destination
+ AccountTypeEnum::RECONCILIATION->value => [AccountTypeEnum::ASSET->value],
+ AccountTypeEnum::REVENUE->value => [], // is not allowed as a destination
+ AccountTypeEnum::LIABILITY_CREDIT->value => [], // is not allowed as a destination
],
],
// depending on the account type, return the allowed transaction types:
- 'allowed_transaction_types' => [
+ 'allowed_transaction_types' => [
'source' => [
- AccountType::ASSET => [
- TransactionTypeModel::WITHDRAWAL,
- TransactionTypeModel::TRANSFER,
- TransactionTypeModel::OPENING_BALANCE,
- TransactionTypeModel::RECONCILIATION,
+ AccountTypeEnum::ASSET->value => [
+ TransactionTypeEnum::WITHDRAWAL->value,
+ TransactionTypeEnum::TRANSFER->value,
+ TransactionTypeEnum::OPENING_BALANCE->value,
+ TransactionTypeEnum::RECONCILIATION->value,
],
- AccountType::EXPENSE => [], // is not allowed as a source.
- AccountType::REVENUE => [TransactionTypeEnum::DEPOSIT->value],
- AccountType::LOAN => [
- TransactionTypeModel::WITHDRAWAL,
+ AccountTypeEnum::EXPENSE->value => [], // is not allowed as a source.
+ AccountTypeEnum::REVENUE->value => [TransactionTypeEnum::DEPOSIT->value],
+ AccountTypeEnum::LOAN->value => [
+ TransactionTypeEnum::WITHDRAWAL->value,
TransactionTypeEnum::DEPOSIT->value,
- TransactionTypeModel::TRANSFER,
- TransactionTypeModel::OPENING_BALANCE,
- TransactionTypeModel::LIABILITY_CREDIT,
+ TransactionTypeEnum::TRANSFER->value,
+ TransactionTypeEnum::OPENING_BALANCE->value,
+ TransactionTypeEnum::LIABILITY_CREDIT->value,
],
- AccountType::DEBT => [
- TransactionTypeModel::WITHDRAWAL,
+ AccountTypeEnum::DEBT->value => [
+ TransactionTypeEnum::WITHDRAWAL->value,
TransactionTypeEnum::DEPOSIT->value,
- TransactionTypeModel::TRANSFER,
- TransactionTypeModel::OPENING_BALANCE,
- TransactionTypeModel::LIABILITY_CREDIT,
+ TransactionTypeEnum::TRANSFER->value,
+ TransactionTypeEnum::OPENING_BALANCE->value,
+ TransactionTypeEnum::LIABILITY_CREDIT->value,
],
- AccountType::MORTGAGE => [
- TransactionTypeModel::WITHDRAWAL,
+ AccountTypeEnum::MORTGAGE->value => [
+ TransactionTypeEnum::WITHDRAWAL->value,
TransactionTypeEnum::DEPOSIT->value,
- TransactionTypeModel::TRANSFER,
- TransactionTypeModel::OPENING_BALANCE,
- TransactionTypeModel::LIABILITY_CREDIT,
+ TransactionTypeEnum::TRANSFER->value,
+ TransactionTypeEnum::OPENING_BALANCE->value,
+ TransactionTypeEnum::LIABILITY_CREDIT->value,
],
- AccountType::INITIAL_BALANCE => [TransactionTypeModel::OPENING_BALANCE],
- AccountType::RECONCILIATION => [TransactionTypeModel::RECONCILIATION],
- AccountType::LIABILITY_CREDIT => [TransactionTypeModel::LIABILITY_CREDIT],
+ AccountTypeEnum::INITIAL_BALANCE->value => [TransactionTypeEnum::OPENING_BALANCE->value],
+ AccountTypeEnum::RECONCILIATION->value => [TransactionTypeEnum::RECONCILIATION->value],
+ AccountTypeEnum::LIABILITY_CREDIT->value => [TransactionTypeEnum::LIABILITY_CREDIT->value],
],
'destination' => [
- AccountType::ASSET => [
+ AccountTypeEnum::ASSET->value => [
TransactionTypeEnum::DEPOSIT->value,
- TransactionTypeModel::TRANSFER,
- TransactionTypeModel::OPENING_BALANCE,
- TransactionTypeModel::RECONCILIATION,
+ TransactionTypeEnum::TRANSFER->value,
+ TransactionTypeEnum::OPENING_BALANCE->value,
+ TransactionTypeEnum::RECONCILIATION->value,
],
- AccountType::EXPENSE => [TransactionTypeModel::WITHDRAWAL],
- AccountType::REVENUE => [], // is not allowed as destination.
- AccountType::LOAN => [
- TransactionTypeModel::WITHDRAWAL,
+ AccountTypeEnum::EXPENSE->value => [TransactionTypeEnum::WITHDRAWAL->value],
+ AccountTypeEnum::REVENUE->value => [], // is not allowed as destination.
+ AccountTypeEnum::LOAN->value => [
+ TransactionTypeEnum::WITHDRAWAL->value,
TransactionTypeEnum::DEPOSIT->value,
- TransactionTypeModel::TRANSFER,
- TransactionTypeModel::OPENING_BALANCE,
+ TransactionTypeEnum::TRANSFER->value,
+ TransactionTypeEnum::OPENING_BALANCE->value,
],
- AccountType::DEBT => [
- TransactionTypeModel::WITHDRAWAL,
+ AccountTypeEnum::DEBT->value => [
+ TransactionTypeEnum::WITHDRAWAL->value,
TransactionTypeEnum::DEPOSIT->value,
- TransactionTypeModel::TRANSFER,
- TransactionTypeModel::OPENING_BALANCE,
+ TransactionTypeEnum::TRANSFER->value,
+ TransactionTypeEnum::OPENING_BALANCE->value,
],
- AccountType::MORTGAGE => [
- TransactionTypeModel::WITHDRAWAL,
+ AccountTypeEnum::MORTGAGE->value => [
+ TransactionTypeEnum::WITHDRAWAL->value,
TransactionTypeEnum::DEPOSIT->value,
- TransactionTypeModel::TRANSFER,
- TransactionTypeModel::OPENING_BALANCE,
+ TransactionTypeEnum::TRANSFER->value,
+ TransactionTypeEnum::OPENING_BALANCE->value,
],
- AccountType::INITIAL_BALANCE => [TransactionTypeModel::OPENING_BALANCE],
- AccountType::RECONCILIATION => [TransactionTypeModel::RECONCILIATION],
- AccountType::LIABILITY_CREDIT => [], // is not allowed as a destination
+ AccountTypeEnum::INITIAL_BALANCE->value => [TransactionTypeEnum::OPENING_BALANCE->value],
+ AccountTypeEnum::RECONCILIATION->value => [TransactionTypeEnum::RECONCILIATION->value],
+ AccountTypeEnum::LIABILITY_CREDIT->value => [], // is not allowed as a destination
],
],
// having the source + dest will tell you the transaction type.
- 'account_to_transaction' => [
- AccountType::ASSET => [
- AccountType::ASSET => TransactionTypeModel::TRANSFER,
- AccountType::CASH => TransactionTypeModel::WITHDRAWAL,
- AccountType::DEBT => TransactionTypeModel::WITHDRAWAL,
- AccountType::EXPENSE => TransactionTypeModel::WITHDRAWAL,
- AccountType::INITIAL_BALANCE => TransactionTypeModel::OPENING_BALANCE,
- AccountType::LOAN => TransactionTypeModel::WITHDRAWAL,
- AccountType::MORTGAGE => TransactionTypeModel::WITHDRAWAL,
- AccountType::RECONCILIATION => TransactionTypeModel::RECONCILIATION,
+ 'account_to_transaction' => [
+ AccountTypeEnum::ASSET->value => [
+ AccountTypeEnum::ASSET->value => TransactionTypeEnum::TRANSFER->value,
+ AccountTypeEnum::CASH->value => TransactionTypeEnum::WITHDRAWAL->value,
+ AccountTypeEnum::DEBT->value => TransactionTypeEnum::WITHDRAWAL->value,
+ AccountTypeEnum::EXPENSE->value => TransactionTypeEnum::WITHDRAWAL->value,
+ AccountTypeEnum::INITIAL_BALANCE->value => TransactionTypeEnum::OPENING_BALANCE->value,
+ AccountTypeEnum::LOAN->value => TransactionTypeEnum::WITHDRAWAL->value,
+ AccountTypeEnum::MORTGAGE->value => TransactionTypeEnum::WITHDRAWAL->value,
+ AccountTypeEnum::RECONCILIATION->value => TransactionTypeEnum::RECONCILIATION->value,
],
- AccountType::CASH => [
- AccountType::ASSET => TransactionTypeModel::DEPOSIT,
- AccountType::LOAN => TransactionTypeModel::DEPOSIT,
- AccountType::DEBT => TransactionTypeModel::DEPOSIT,
- AccountType::MORTGAGE => TransactionTypeModel::DEPOSIT,
+ AccountTypeEnum::CASH->value => [
+ AccountTypeEnum::ASSET->value => TransactionTypeEnum::DEPOSIT->value,
+ AccountTypeEnum::LOAN->value => TransactionTypeEnum::DEPOSIT->value,
+ AccountTypeEnum::DEBT->value => TransactionTypeEnum::DEPOSIT->value,
+ AccountTypeEnum::MORTGAGE->value => TransactionTypeEnum::DEPOSIT->value,
],
- AccountType::DEBT => [
- AccountType::ASSET => TransactionTypeEnum::DEPOSIT->value,
- AccountType::DEBT => TransactionTypeModel::TRANSFER,
- AccountType::EXPENSE => TransactionTypeModel::WITHDRAWAL,
- AccountType::INITIAL_BALANCE => TransactionTypeModel::OPENING_BALANCE,
- AccountType::LOAN => TransactionTypeModel::TRANSFER,
- AccountType::MORTGAGE => TransactionTypeModel::TRANSFER,
+ AccountTypeEnum::DEBT->value => [
+ AccountTypeEnum::ASSET->value => TransactionTypeEnum::DEPOSIT->value,
+ AccountTypeEnum::DEBT->value => TransactionTypeEnum::TRANSFER->value,
+ AccountTypeEnum::EXPENSE->value => TransactionTypeEnum::WITHDRAWAL->value,
+ AccountTypeEnum::INITIAL_BALANCE->value => TransactionTypeEnum::OPENING_BALANCE->value,
+ AccountTypeEnum::LOAN->value => TransactionTypeEnum::TRANSFER->value,
+ AccountTypeEnum::MORTGAGE->value => TransactionTypeEnum::TRANSFER->value,
],
- AccountType::INITIAL_BALANCE => [
- AccountType::ASSET => TransactionTypeModel::OPENING_BALANCE,
- AccountType::DEBT => TransactionTypeModel::OPENING_BALANCE,
- AccountType::LOAN => TransactionTypeModel::OPENING_BALANCE,
- AccountType::MORTGAGE => TransactionTypeModel::OPENING_BALANCE,
+ AccountTypeEnum::INITIAL_BALANCE->value => [
+ AccountTypeEnum::ASSET->value => TransactionTypeEnum::OPENING_BALANCE->value,
+ AccountTypeEnum::DEBT->value => TransactionTypeEnum::OPENING_BALANCE->value,
+ AccountTypeEnum::LOAN->value => TransactionTypeEnum::OPENING_BALANCE->value,
+ AccountTypeEnum::MORTGAGE->value => TransactionTypeEnum::OPENING_BALANCE->value,
],
- AccountType::LOAN => [
- AccountType::ASSET => TransactionTypeEnum::DEPOSIT->value,
- AccountType::DEBT => TransactionTypeModel::TRANSFER,
- AccountType::EXPENSE => TransactionTypeModel::WITHDRAWAL,
- AccountType::INITIAL_BALANCE => TransactionTypeModel::OPENING_BALANCE,
- AccountType::LOAN => TransactionTypeModel::TRANSFER,
- AccountType::MORTGAGE => TransactionTypeModel::TRANSFER,
+ AccountTypeEnum::LOAN->value => [
+ AccountTypeEnum::ASSET->value => TransactionTypeEnum::DEPOSIT->value,
+ AccountTypeEnum::DEBT->value => TransactionTypeEnum::TRANSFER->value,
+ AccountTypeEnum::EXPENSE->value => TransactionTypeEnum::WITHDRAWAL->value,
+ AccountTypeEnum::INITIAL_BALANCE->value => TransactionTypeEnum::OPENING_BALANCE->value,
+ AccountTypeEnum::LOAN->value => TransactionTypeEnum::TRANSFER->value,
+ AccountTypeEnum::MORTGAGE->value => TransactionTypeEnum::TRANSFER->value,
],
- AccountType::MORTGAGE => [
- AccountType::ASSET => TransactionTypeEnum::DEPOSIT->value,
- AccountType::DEBT => TransactionTypeModel::TRANSFER,
- AccountType::EXPENSE => TransactionTypeModel::WITHDRAWAL,
- AccountType::INITIAL_BALANCE => TransactionTypeModel::OPENING_BALANCE,
- AccountType::LOAN => TransactionTypeModel::TRANSFER,
- AccountType::MORTGAGE => TransactionTypeModel::TRANSFER,
+ AccountTypeEnum::MORTGAGE->value => [
+ AccountTypeEnum::ASSET->value => TransactionTypeEnum::DEPOSIT->value,
+ AccountTypeEnum::DEBT->value => TransactionTypeEnum::TRANSFER->value,
+ AccountTypeEnum::EXPENSE->value => TransactionTypeEnum::WITHDRAWAL->value,
+ AccountTypeEnum::INITIAL_BALANCE->value => TransactionTypeEnum::OPENING_BALANCE->value,
+ AccountTypeEnum::LOAN->value => TransactionTypeEnum::TRANSFER->value,
+ AccountTypeEnum::MORTGAGE->value => TransactionTypeEnum::TRANSFER->value,
],
- AccountType::RECONCILIATION => [
- AccountType::ASSET => TransactionTypeModel::RECONCILIATION,
+ AccountTypeEnum::RECONCILIATION->value => [
+ AccountTypeEnum::ASSET->value => TransactionTypeEnum::RECONCILIATION->value,
],
- AccountType::REVENUE => [
- AccountType::ASSET => TransactionTypeEnum::DEPOSIT->value,
- AccountType::DEBT => TransactionTypeEnum::DEPOSIT->value,
- AccountType::LOAN => TransactionTypeEnum::DEPOSIT->value,
- AccountType::MORTGAGE => TransactionTypeEnum::DEPOSIT->value,
+ AccountTypeEnum::REVENUE->value => [
+ AccountTypeEnum::ASSET->value => TransactionTypeEnum::DEPOSIT->value,
+ AccountTypeEnum::DEBT->value => TransactionTypeEnum::DEPOSIT->value,
+ AccountTypeEnum::LOAN->value => TransactionTypeEnum::DEPOSIT->value,
+ AccountTypeEnum::MORTGAGE->value => TransactionTypeEnum::DEPOSIT->value,
],
- AccountType::LIABILITY_CREDIT => [
- AccountType::DEBT => TransactionTypeModel::LIABILITY_CREDIT,
- AccountType::LOAN => TransactionTypeModel::LIABILITY_CREDIT,
- AccountType::MORTGAGE => TransactionTypeModel::LIABILITY_CREDIT,
+ AccountTypeEnum::LIABILITY_CREDIT->value => [
+ AccountTypeEnum::DEBT->value => TransactionTypeEnum::LIABILITY_CREDIT->value,
+ AccountTypeEnum::LOAN->value => TransactionTypeEnum::LIABILITY_CREDIT->value,
+ AccountTypeEnum::MORTGAGE->value => TransactionTypeEnum::LIABILITY_CREDIT->value,
],
- // AccountType::EXPENSE unlisted because it cant be a source
+ // AccountTypeEnum::EXPENSE->value unlisted because it cant be a source
],
// allowed source -> destination accounts.
- 'source_dests' => [
- TransactionTypeModel::WITHDRAWAL => [
- AccountType::ASSET => [AccountType::EXPENSE, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE, AccountType::CASH],
- AccountType::LOAN => [AccountType::EXPENSE, AccountType::CASH],
- AccountType::DEBT => [AccountType::EXPENSE, AccountType::CASH],
- AccountType::MORTGAGE => [AccountType::EXPENSE, AccountType::CASH],
+ 'source_dests' => [
+ TransactionTypeEnum::WITHDRAWAL->value => [
+ AccountTypeEnum::ASSET->value => [AccountTypeEnum::EXPENSE->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value, AccountTypeEnum::CASH->value],
+ AccountTypeEnum::LOAN->value => [AccountTypeEnum::EXPENSE->value, AccountTypeEnum::CASH->value],
+ AccountTypeEnum::DEBT->value => [AccountTypeEnum::EXPENSE->value, AccountTypeEnum::CASH->value],
+ AccountTypeEnum::MORTGAGE->value => [AccountTypeEnum::EXPENSE->value, AccountTypeEnum::CASH->value],
],
TransactionTypeEnum::DEPOSIT->value => [
- AccountType::REVENUE => [AccountType::ASSET, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
- AccountType::CASH => [AccountType::ASSET, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
- AccountType::LOAN => [AccountType::ASSET],
- AccountType::DEBT => [AccountType::ASSET],
- AccountType::MORTGAGE => [AccountType::ASSET],
+ AccountTypeEnum::REVENUE->value => [AccountTypeEnum::ASSET->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
+ AccountTypeEnum::CASH->value => [AccountTypeEnum::ASSET->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
+ AccountTypeEnum::LOAN->value => [AccountTypeEnum::ASSET->value],
+ AccountTypeEnum::DEBT->value => [AccountTypeEnum::ASSET->value],
+ AccountTypeEnum::MORTGAGE->value => [AccountTypeEnum::ASSET->value],
],
- TransactionTypeModel::TRANSFER => [
- AccountType::ASSET => [AccountType::ASSET],
- AccountType::LOAN => [AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
- AccountType::DEBT => [AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
- AccountType::MORTGAGE => [AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
+ TransactionTypeEnum::TRANSFER->value => [
+ AccountTypeEnum::ASSET->value => [AccountTypeEnum::ASSET->value],
+ AccountTypeEnum::LOAN->value => [AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
+ AccountTypeEnum::DEBT->value => [AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
+ AccountTypeEnum::MORTGAGE->value => [AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
],
- TransactionTypeModel::OPENING_BALANCE => [
- AccountType::ASSET => [AccountType::INITIAL_BALANCE],
- AccountType::LOAN => [AccountType::INITIAL_BALANCE],
- AccountType::DEBT => [AccountType::INITIAL_BALANCE],
- AccountType::MORTGAGE => [AccountType::INITIAL_BALANCE],
- AccountType::INITIAL_BALANCE => [AccountType::ASSET, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
+ TransactionTypeEnum::OPENING_BALANCE->value => [
+ AccountTypeEnum::ASSET->value => [AccountTypeEnum::INITIAL_BALANCE->value],
+ AccountTypeEnum::LOAN->value => [AccountTypeEnum::INITIAL_BALANCE->value],
+ AccountTypeEnum::DEBT->value => [AccountTypeEnum::INITIAL_BALANCE->value],
+ AccountTypeEnum::MORTGAGE->value => [AccountTypeEnum::INITIAL_BALANCE->value],
+ AccountTypeEnum::INITIAL_BALANCE->value => [AccountTypeEnum::ASSET->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
],
- TransactionTypeModel::RECONCILIATION => [
- AccountType::RECONCILIATION => [AccountType::ASSET],
- AccountType::ASSET => [AccountType::RECONCILIATION],
+ TransactionTypeEnum::RECONCILIATION->value => [
+ AccountTypeEnum::RECONCILIATION->value => [AccountTypeEnum::ASSET->value],
+ AccountTypeEnum::ASSET->value => [AccountTypeEnum::RECONCILIATION->value],
],
- TransactionTypeModel::LIABILITY_CREDIT => [
- AccountType::LOAN => [AccountType::LIABILITY_CREDIT],
- AccountType::DEBT => [AccountType::LIABILITY_CREDIT],
- AccountType::MORTGAGE => [AccountType::LIABILITY_CREDIT],
- AccountType::LIABILITY_CREDIT => [AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
+ TransactionTypeEnum::LIABILITY_CREDIT->value => [
+ AccountTypeEnum::LOAN->value => [AccountTypeEnum::LIABILITY_CREDIT->value],
+ AccountTypeEnum::DEBT->value => [AccountTypeEnum::LIABILITY_CREDIT->value],
+ AccountTypeEnum::MORTGAGE->value => [AccountTypeEnum::LIABILITY_CREDIT->value],
+ AccountTypeEnum::LIABILITY_CREDIT->value => [AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
],
],
// if you add fields to this array, don't forget to update the export routine (ExportDataGenerator).
- 'journal_meta_fields' => [
+ 'journal_meta_fields' => [
// sepa
'sepa_cc',
'sepa_ct_op',
@@ -889,28 +889,28 @@ return [
'recurrence_count',
'recurrence_date',
],
- 'webhooks' => [
+ 'webhooks' => [
'max_attempts' => env('WEBHOOK_MAX_ATTEMPTS', 3),
],
- 'can_have_virtual_amounts' => [AccountType::ASSET],
- 'can_have_opening_balance' => [AccountType::ASSET, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE],
- 'dynamic_creation_allowed' => [
- AccountType::EXPENSE,
- AccountType::REVENUE,
- AccountType::INITIAL_BALANCE,
- AccountType::RECONCILIATION,
- AccountType::LIABILITY_CREDIT,
+ 'can_have_virtual_amounts' => [AccountTypeEnum::ASSET->value],
+ 'can_have_opening_balance' => [AccountTypeEnum::ASSET->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
+ 'dynamic_creation_allowed' => [
+ AccountTypeEnum::EXPENSE->value,
+ AccountTypeEnum::REVENUE->value,
+ AccountTypeEnum::INITIAL_BALANCE->value,
+ AccountTypeEnum::RECONCILIATION->value,
+ AccountTypeEnum::LIABILITY_CREDIT->value,
],
- 'valid_asset_fields' => ['account_role', 'account_number', 'currency_id', 'BIC', 'include_net_worth'],
- 'valid_cc_fields' => ['account_role', 'cc_monthly_payment_date', 'cc_type', 'account_number', 'currency_id', 'BIC', 'include_net_worth'],
- 'valid_account_fields' => ['account_number', 'currency_id', 'BIC', 'interest', 'interest_period', 'include_net_worth', 'liability_direction'],
+ 'valid_asset_fields' => ['account_role', 'account_number', 'currency_id', 'BIC', 'include_net_worth'],
+ 'valid_cc_fields' => ['account_role', 'cc_monthly_payment_date', 'cc_type', 'account_number', 'currency_id', 'BIC', 'include_net_worth'],
+ 'valid_account_fields' => ['account_number', 'currency_id', 'BIC', 'interest', 'interest_period', 'include_net_worth', 'liability_direction'],
// dynamic date ranges are as follows:
- 'dynamic_date_ranges' => ['last7', 'last30', 'last90', 'last365', 'MTD', 'QTD', 'YTD'],
+ 'dynamic_date_ranges' => ['last7', 'last30', 'last90', 'last365', 'MTD', 'QTD', 'YTD'],
// only used in v1
- 'allowed_sort_parameters' => ['order', 'name', 'iban'],
+ 'allowed_sort_parameters' => ['order', 'name', 'iban'],
// preselected account lists possibilities:
- 'preselected_accounts' => ['all', 'assets', 'liabilities'],
+ 'preselected_accounts' => ['all', 'assets', 'liabilities'],
];
From f5c56e02da25dc178f4f691907cb2e0af0403b84 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 30 Nov 2024 05:42:59 +0100
Subject: [PATCH 003/167] API allows update/set of budget limit notes.
https://github.com/firefly-iii/firefly-iii/issues/5523
---
.../Models/BudgetLimit/StoreController.php | 9 +-
.../Models/BudgetLimit/StoreRequest.php | 2 +
.../Models/BudgetLimit/UpdateRequest.php | 9 +-
app/Models/Account.php | 2 +-
app/Models/BudgetLimit.php | 9 +
.../Budget/BudgetLimitRepository.php | 280 ++++++++++--------
.../Budget/BudgetLimitRepositoryInterface.php | 3 +
app/Transformers/BudgetLimitTransformer.php | 17 +-
8 files changed, 187 insertions(+), 144 deletions(-)
diff --git a/app/Api/V1/Controllers/Models/BudgetLimit/StoreController.php b/app/Api/V1/Controllers/Models/BudgetLimit/StoreController.php
index 6f899b19ce..6f4cd02427 100644
--- a/app/Api/V1/Controllers/Models/BudgetLimit/StoreController.php
+++ b/app/Api/V1/Controllers/Models/BudgetLimit/StoreController.php
@@ -69,16 +69,17 @@ class StoreController extends Controller
$data = $request->getAll();
$data['start_date'] = $data['start'];
$data['end_date'] = $data['end'];
+ $data['notes'] = $data['notes'];
$data['budget_id'] = $budget->id;
- $budgetLimit = $this->blRepository->store($data);
- $manager = $this->getManager();
+ $budgetLimit = $this->blRepository->store($data);
+ $manager = $this->getManager();
/** @var BudgetLimitTransformer $transformer */
- $transformer = app(BudgetLimitTransformer::class);
+ $transformer = app(BudgetLimitTransformer::class);
$transformer->setParameters($this->parameters);
- $resource = new Item($budgetLimit, $transformer, 'budget_limits');
+ $resource = new Item($budgetLimit, $transformer, 'budget_limits');
return response()->json($manager->createData($resource)->toArray())->header('Content-Type', self::CONTENT_TYPE);
}
diff --git a/app/Api/V1/Requests/Models/BudgetLimit/StoreRequest.php b/app/Api/V1/Requests/Models/BudgetLimit/StoreRequest.php
index 4fc0e8bf5b..48c77cf2a2 100644
--- a/app/Api/V1/Requests/Models/BudgetLimit/StoreRequest.php
+++ b/app/Api/V1/Requests/Models/BudgetLimit/StoreRequest.php
@@ -48,6 +48,7 @@ class StoreRequest extends FormRequest
'amount' => $this->convertString('amount'),
'currency_id' => $this->convertInteger('currency_id'),
'currency_code' => $this->convertString('currency_code'),
+ 'notes' => $this->stringWithNewlines('notes'),
];
}
@@ -62,6 +63,7 @@ class StoreRequest extends FormRequest
'amount' => ['required', new IsValidPositiveAmount()],
'currency_id' => 'numeric|exists:transaction_currencies,id',
'currency_code' => 'min:3|max:51|exists:transaction_currencies,code',
+ 'notes' => 'nullable|min:0|max:32768',
];
}
}
diff --git a/app/Api/V1/Requests/Models/BudgetLimit/UpdateRequest.php b/app/Api/V1/Requests/Models/BudgetLimit/UpdateRequest.php
index f93cebb012..08f2a160be 100644
--- a/app/Api/V1/Requests/Models/BudgetLimit/UpdateRequest.php
+++ b/app/Api/V1/Requests/Models/BudgetLimit/UpdateRequest.php
@@ -51,8 +51,12 @@ class UpdateRequest extends FormRequest
'amount' => ['amount', 'convertString'],
'currency_id' => ['currency_id', 'convertInteger'],
'currency_code' => ['currency_code', 'convertString'],
+ 'notes' => ['notes', 'stringWithNewlines'],
];
-
+ if(false === $this->has('notes')) {
+ // ignore notes, not submitted.
+ unset($fields['notes']);
+ }
return $this->getAllData($fields);
}
@@ -67,6 +71,7 @@ class UpdateRequest extends FormRequest
'amount' => ['nullable', new IsValidPositiveAmount()],
'currency_id' => 'numeric|exists:transaction_currencies,id',
'currency_code' => 'min:3|max:51|exists:transaction_currencies,code',
+ 'notes' => 'nullable|min:0|max:32768',
];
}
@@ -84,7 +89,7 @@ class UpdateRequest extends FormRequest
$start = new Carbon($data['start']);
$end = new Carbon($data['end']);
if ($end->isBefore($start)) {
- $validator->errors()->add('end', (string)trans('validation.date_after'));
+ $validator->errors()->add('end', (string) trans('validation.date_after'));
}
}
}
diff --git a/app/Models/Account.php b/app/Models/Account.php
index 39b5e1f8ed..fe523e2fe4 100644
--- a/app/Models/Account.php
+++ b/app/Models/Account.php
@@ -144,7 +144,7 @@ class Account extends Model
}
/**
- * Get all of the notes.
+ * Get all the notes.
*/
public function notes(): MorphMany
{
diff --git a/app/Models/BudgetLimit.php b/app/Models/BudgetLimit.php
index 22f3c0de2d..1f20c69482 100644
--- a/app/Models/BudgetLimit.php
+++ b/app/Models/BudgetLimit.php
@@ -31,6 +31,7 @@ use FireflyIII\Support\Models\ReturnsIntegerIdTrait;
use Illuminate\Database\Eloquent\Casts\Attribute;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsTo;
+use Illuminate\Database\Eloquent\Relations\MorphMany;
use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
/**
@@ -90,6 +91,14 @@ class BudgetLimit extends Model
return $this->belongsTo(TransactionCurrency::class);
}
+ /**
+ * Get all the notes.
+ */
+ public function notes(): MorphMany
+ {
+ return $this->morphMany(Note::class, 'noteable');
+ }
+
/**
* Get the amount
*/
diff --git a/app/Repositories/Budget/BudgetLimitRepository.php b/app/Repositories/Budget/BudgetLimitRepository.php
index 6921968dc3..f98b3da334 100644
--- a/app/Repositories/Budget/BudgetLimitRepository.php
+++ b/app/Repositories/Budget/BudgetLimitRepository.php
@@ -29,6 +29,7 @@ use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Factory\TransactionCurrencyFactory;
use FireflyIII\Models\Budget;
use FireflyIII\Models\BudgetLimit;
+use FireflyIII\Models\Note;
use FireflyIII\Models\TransactionCurrency;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
@@ -49,10 +50,10 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface
*/
public function budgeted(Carbon $start, Carbon $end, TransactionCurrency $currency, ?Collection $budgets = null): string
{
- $query = BudgetLimit::leftJoin('budgets', 'budgets.id', '=', 'budget_limits.budget_id')
+ $query = BudgetLimit::leftJoin('budgets', 'budgets.id', '=', 'budget_limits.budget_id')
// same complex where query as below.
- ->where(
+ ->where(
static function (Builder $q5) use ($start, $end): void {
$q5->where(
static function (Builder $q1) use ($start, $end): void {
@@ -62,30 +63,27 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface
$q2->where('budget_limits.end_date', '<=', $end->format('Y-m-d'));
}
)
- ->orWhere(
- static function (Builder $q3) use ($start, $end): void {
- $q3->where('budget_limits.start_date', '>=', $start->format('Y-m-d'));
- $q3->where('budget_limits.start_date', '<=', $end->format('Y-m-d'));
- }
- )
- ;
+ ->orWhere(
+ static function (Builder $q3) use ($start, $end): void {
+ $q3->where('budget_limits.start_date', '>=', $start->format('Y-m-d'));
+ $q3->where('budget_limits.start_date', '<=', $end->format('Y-m-d'));
+ }
+ );
}
)
- ->orWhere(
- static function (Builder $q4) use ($start, $end): void {
- // or start is before start AND end is after end.
- $q4->where('budget_limits.start_date', '<=', $start->format('Y-m-d'));
- $q4->where('budget_limits.end_date', '>=', $end->format('Y-m-d'));
- }
- )
- ;
+ ->orWhere(
+ static function (Builder $q4) use ($start, $end): void {
+ // or start is before start AND end is after end.
+ $q4->where('budget_limits.start_date', '<=', $start->format('Y-m-d'));
+ $q4->where('budget_limits.end_date', '>=', $end->format('Y-m-d'));
+ }
+ );
}
)
- ->where('budget_limits.transaction_currency_id', $currency->id)
- ->whereNull('budgets.deleted_at')
- ->where('budgets.active', true)
- ->where('budgets.user_id', $this->user->id)
- ;
+ ->where('budget_limits.transaction_currency_id', $currency->id)
+ ->whereNull('budgets.deleted_at')
+ ->where('budgets.active', true)
+ ->where('budgets.user_id', $this->user->id);
if (null !== $budgets && $budgets->count() > 0) {
$query->whereIn('budget_limits.budget_id', $budgets->pluck('id')->toArray());
}
@@ -137,19 +135,17 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface
// both are NULL:
if (null === $start && null === $end) {
return BudgetLimit::leftJoin('budgets', 'budgets.id', '=', 'budget_limits.budget_id')
- ->with(['budget'])
- ->where('budgets.user_id', $this->user->id)
- ->whereNull('budgets.deleted_at')
- ->get(['budget_limits.*'])
- ;
+ ->with(['budget'])
+ ->where('budgets.user_id', $this->user->id)
+ ->whereNull('budgets.deleted_at')
+ ->get(['budget_limits.*']);
}
// one of the two is NULL.
if (null === $start xor null === $end) {
$query = BudgetLimit::leftJoin('budgets', 'budgets.id', '=', 'budget_limits.budget_id')
- ->with(['budget'])
- ->whereNull('budgets.deleted_at')
- ->where('budgets.user_id', $this->user->id)
- ;
+ ->with(['budget'])
+ ->whereNull('budgets.deleted_at')
+ ->where('budgets.user_id', $this->user->id);
if (null !== $end) {
// end date must be before $end.
$query->where('end_date', '<=', $end->format('Y-m-d 00:00:00'));
@@ -164,39 +160,36 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface
// neither are NULL:
return BudgetLimit::leftJoin('budgets', 'budgets.id', '=', 'budget_limits.budget_id')
- ->with(['budget'])
- ->where('budgets.user_id', $this->user->id)
- ->whereNull('budgets.deleted_at')
- ->where(
- static function (Builder $q5) use ($start, $end): void {
- $q5->where(
- static function (Builder $q1) use ($start, $end): void {
- $q1->where(
- static function (Builder $q2) use ($start, $end): void {
- $q2->where('budget_limits.end_date', '>=', $start->format('Y-m-d'));
- $q2->where('budget_limits.end_date', '<=', $end->format('Y-m-d'));
- }
- )
- ->orWhere(
- static function (Builder $q3) use ($start, $end): void {
- $q3->where('budget_limits.start_date', '>=', $start->format('Y-m-d'));
- $q3->where('budget_limits.start_date', '<=', $end->format('Y-m-d'));
- }
- )
- ;
- }
- )
- ->orWhere(
- static function (Builder $q4) use ($start, $end): void {
- // or start is before start AND end is after end.
- $q4->where('budget_limits.start_date', '<=', $start->format('Y-m-d'));
- $q4->where('budget_limits.end_date', '>=', $end->format('Y-m-d'));
- }
- )
- ;
- }
- )->get(['budget_limits.*'])
- ;
+ ->with(['budget'])
+ ->where('budgets.user_id', $this->user->id)
+ ->whereNull('budgets.deleted_at')
+ ->where(
+ static function (Builder $q5) use ($start, $end): void {
+ $q5->where(
+ static function (Builder $q1) use ($start, $end): void {
+ $q1->where(
+ static function (Builder $q2) use ($start, $end): void {
+ $q2->where('budget_limits.end_date', '>=', $start->format('Y-m-d'));
+ $q2->where('budget_limits.end_date', '<=', $end->format('Y-m-d'));
+ }
+ )
+ ->orWhere(
+ static function (Builder $q3) use ($start, $end): void {
+ $q3->where('budget_limits.start_date', '>=', $start->format('Y-m-d'));
+ $q3->where('budget_limits.start_date', '<=', $end->format('Y-m-d'));
+ }
+ );
+ }
+ )
+ ->orWhere(
+ static function (Builder $q4) use ($start, $end): void {
+ // or start is before start AND end is after end.
+ $q4->where('budget_limits.start_date', '<=', $start->format('Y-m-d'));
+ $q4->where('budget_limits.end_date', '>=', $end->format('Y-m-d'));
+ }
+ );
+ }
+ )->get(['budget_limits.*']);
}
public function getBudgetLimits(Budget $budget, ?Carbon $start = null, ?Carbon $end = null): Collection
@@ -221,41 +214,38 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface
// when both dates are set:
return $budget->budgetlimits()
- ->where(
- static function (Builder $q5) use ($start, $end): void { // @phpstan-ignore-line
- $q5->where(
- static function (Builder $q1) use ($start, $end): void {
- // budget limit ends within period
- $q1->where(
- static function (Builder $q2) use ($start, $end): void {
- $q2->where('budget_limits.end_date', '>=', $start->format('Y-m-d 00:00:00'));
- $q2->where('budget_limits.end_date', '<=', $end->format('Y-m-d 23:59:59'));
- }
- )
- // budget limit start within period
- ->orWhere(
- static function (Builder $q3) use ($start, $end): void {
- $q3->where('budget_limits.start_date', '>=', $start->format('Y-m-d 00:00:00'));
- $q3->where('budget_limits.start_date', '<=', $end->format('Y-m-d 23:59:59'));
- }
- )
- ;
- }
- )
- ->orWhere(
- static function (Builder $q4) use ($start, $end): void {
- // or start is before start AND end is after end.
- $q4->where('budget_limits.start_date', '<=', $start->format('Y-m-d 23:59:59'));
- $q4->where('budget_limits.end_date', '>=', $end->format('Y-m-d 00:00:00'));
- }
- )
- ;
- }
- )->orderBy('budget_limits.start_date', 'DESC')->get(['budget_limits.*'])
- ;
+ ->where(
+ static function (Builder $q5) use ($start, $end): void { // @phpstan-ignore-line
+ $q5->where(
+ static function (Builder $q1) use ($start, $end): void {
+ // budget limit ends within period
+ $q1->where(
+ static function (Builder $q2) use ($start, $end): void {
+ $q2->where('budget_limits.end_date', '>=', $start->format('Y-m-d 00:00:00'));
+ $q2->where('budget_limits.end_date', '<=', $end->format('Y-m-d 23:59:59'));
+ }
+ )
+ // budget limit start within period
+ ->orWhere(
+ static function (Builder $q3) use ($start, $end): void {
+ $q3->where('budget_limits.start_date', '>=', $start->format('Y-m-d 00:00:00'));
+ $q3->where('budget_limits.start_date', '<=', $end->format('Y-m-d 23:59:59'));
+ }
+ );
+ }
+ )
+ ->orWhere(
+ static function (Builder $q4) use ($start, $end): void {
+ // or start is before start AND end is after end.
+ $q4->where('budget_limits.start_date', '<=', $start->format('Y-m-d 23:59:59'));
+ $q4->where('budget_limits.end_date', '>=', $end->format('Y-m-d 00:00:00'));
+ }
+ );
+ }
+ )->orderBy('budget_limits.start_date', 'DESC')->get(['budget_limits.*']);
}
- public function setUser(null|Authenticatable|User $user): void
+ public function setUser(null | Authenticatable | User $user): void
{
if ($user instanceof User) {
$this->user = $user;
@@ -269,52 +259,57 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface
{
// if no currency has been provided, use the user's default currency:
/** @var TransactionCurrencyFactory $factory */
- $factory = app(TransactionCurrencyFactory::class);
- $currency = $factory->find($data['currency_id'] ?? null, $data['currency_code'] ?? null);
+ $factory = app(TransactionCurrencyFactory::class);
+ $currency = $factory->find($data['currency_id'] ?? null, $data['currency_code'] ?? null);
if (null === $currency) {
$currency = app('amount')->getDefaultCurrencyByUserGroup($this->user->userGroup);
}
- $currency->enabled = true;
+ $currency->enabled = true;
$currency->save();
// find the budget:
- $budget = $this->user->budgets()->find((int) $data['budget_id']);
+ $budget = $this->user->budgets()->find((int) $data['budget_id']);
if (null === $budget) {
throw new FireflyException('200004: Budget does not exist.');
}
// find limit with same date range and currency.
- $limit = $budget->budgetlimits()
- ->where('budget_limits.start_date', $data['start_date']->format('Y-m-d'))
- ->where('budget_limits.end_date', $data['end_date']->format('Y-m-d'))
- ->where('budget_limits.transaction_currency_id', $currency->id)
- ->first(['budget_limits.*'])
- ;
+ $limit = $budget->budgetlimits()
+ ->where('budget_limits.start_date', $data['start_date']->format('Y-m-d'))
+ ->where('budget_limits.end_date', $data['end_date']->format('Y-m-d'))
+ ->where('budget_limits.transaction_currency_id', $currency->id)
+ ->first(['budget_limits.*']);
if (null !== $limit) {
throw new FireflyException('200027: Budget limit already exists.');
}
app('log')->debug('No existing budget limit, create a new one');
// or create one and return it.
- $limit = new BudgetLimit();
+ $limit = new BudgetLimit();
$limit->budget()->associate($budget);
$limit->start_date = $data['start_date']->format('Y-m-d');
$limit->end_date = $data['end_date']->format('Y-m-d');
$limit->amount = $data['amount'];
$limit->transaction_currency_id = $currency->id;
$limit->save();
+
+ $noteText = (string) ($data['notes'] ?? '');
+ if ('' !== $noteText) {
+ $this->setNoteText($limit, $noteText);
+ }
+
app('log')->debug(sprintf('Created new budget limit with ID #%d and amount %s', $limit->id, $data['amount']));
return $limit;
}
+
public function find(Budget $budget, TransactionCurrency $currency, Carbon $start, Carbon $end): ?BudgetLimit
{
return $budget->budgetlimits()
- ->where('transaction_currency_id', $currency->id)
- ->where('start_date', $start->format('Y-m-d'))
- ->where('end_date', $end->format('Y-m-d'))->first()
- ;
+ ->where('transaction_currency_id', $currency->id)
+ ->where('start_date', $start->format('Y-m-d'))
+ ->where('end_date', $end->format('Y-m-d'))->first();
}
/**
@@ -322,8 +317,8 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface
*/
public function update(BudgetLimit $budgetLimit, array $data): BudgetLimit
{
- $budgetLimit->amount = array_key_exists('amount', $data) ? $data['amount'] : $budgetLimit->amount;
- $budgetLimit->budget_id = array_key_exists('budget_id', $data) ? $data['budget_id'] : $budgetLimit->budget_id;
+ $budgetLimit->amount = array_key_exists('amount', $data) ? $data['amount'] : $budgetLimit->amount;
+ $budgetLimit->budget_id = array_key_exists('budget_id', $data) ? $data['budget_id'] : $budgetLimit->budget_id;
if (array_key_exists('start', $data)) {
$budgetLimit->start_date = $data['start']->startOfDay();
@@ -335,7 +330,7 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface
}
// if no currency has been provided, use the user's default currency:
- $currency = null;
+ $currency = null;
// update if relevant:
if (array_key_exists('currency_id', $data) || array_key_exists('currency_code', $data)) {
@@ -347,41 +342,43 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface
if (null === $currency) {
$currency = $budgetLimit->transactionCurrency ?? app('amount')->getDefaultCurrencyByUserGroup($this->user->userGroup);
}
- $currency->enabled = true;
+ $currency->enabled = true;
$currency->save();
$budgetLimit->transaction_currency_id = $currency->id;
$budgetLimit->save();
+ // update notes if they exist.
+ if(array_key_exists('notes', $data)) {
+ $this->setNoteText($budgetLimit, (string)$data['notes']);
+ }
+
return $budgetLimit;
}
public function updateLimitAmount(Budget $budget, Carbon $start, Carbon $end, string $amount): ?BudgetLimit
{
// count the limits:
- $limits = $budget->budgetlimits()
- ->where('budget_limits.start_date', $start->format('Y-m-d 00:00:00'))
- ->where('budget_limits.end_date', $end->format('Y-m-d 00:00:00'))
- ->count('budget_limits.*')
- ;
+ $limits = $budget->budgetlimits()
+ ->where('budget_limits.start_date', $start->format('Y-m-d 00:00:00'))
+ ->where('budget_limits.end_date', $end->format('Y-m-d 00:00:00'))
+ ->count('budget_limits.*');
app('log')->debug(sprintf('Found %d budget limits.', $limits));
// there might be a budget limit for these dates:
/** @var null|BudgetLimit $limit */
- $limit = $budget->budgetlimits()
- ->where('budget_limits.start_date', $start->format('Y-m-d 00:00:00'))
- ->where('budget_limits.end_date', $end->format('Y-m-d 00:00:00'))
- ->first(['budget_limits.*'])
- ;
+ $limit = $budget->budgetlimits()
+ ->where('budget_limits.start_date', $start->format('Y-m-d 00:00:00'))
+ ->where('budget_limits.end_date', $end->format('Y-m-d 00:00:00'))
+ ->first(['budget_limits.*']);
// if more than 1 limit found, delete the others:
if ($limits > 1 && null !== $limit) {
app('log')->debug(sprintf('Found more than 1, delete all except #%d', $limit->id));
$budget->budgetlimits()
- ->where('budget_limits.start_date', $start->format('Y-m-d 00:00:00'))
- ->where('budget_limits.end_date', $end->format('Y-m-d 00:00:00'))
- ->where('budget_limits.id', '!=', $limit->id)->delete()
- ;
+ ->where('budget_limits.start_date', $start->format('Y-m-d 00:00:00'))
+ ->where('budget_limits.end_date', $end->format('Y-m-d 00:00:00'))
+ ->where('budget_limits.id', '!=', $limit->id)->delete();
}
// delete if amount is zero.
@@ -403,7 +400,7 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface
}
app('log')->debug('No existing budget limit, create a new one');
// or create one and return it.
- $limit = new BudgetLimit();
+ $limit = new BudgetLimit();
$limit->budget()->associate($budget);
$limit->start_date = $start->startOfDay();
$limit->start_date_tz = $start->format('e');
@@ -415,4 +412,25 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface
return $limit;
}
+
+ #[\Override] public function getNoteText(BudgetLimit $budgetLimit): string
+ {
+ return (string) $budgetLimit->notes()->first()?->text;
+ }
+
+ #[\Override] public function setNoteText(BudgetLimit $budgetLimit, string $text): void
+ {
+ $dbNote = $budgetLimit->notes()->first();
+ if ('' !== $text) {
+ if (null === $dbNote) {
+ $dbNote = new Note();
+ $dbNote->noteable()->associate($budgetLimit);
+ }
+ $dbNote->text = trim($text);
+ $dbNote->save();
+
+ return;
+ }
+ $dbNote?->delete();
+ }
}
diff --git a/app/Repositories/Budget/BudgetLimitRepositoryInterface.php b/app/Repositories/Budget/BudgetLimitRepositoryInterface.php
index 9bb52abb15..12cbcd9da4 100644
--- a/app/Repositories/Budget/BudgetLimitRepositoryInterface.php
+++ b/app/Repositories/Budget/BudgetLimitRepositoryInterface.php
@@ -48,6 +48,9 @@ interface BudgetLimitRepositoryInterface
*/
public function destroyAll(): void;
+ public function getNoteText(BudgetLimit $budgetLimit): string;
+ public function setNoteText(BudgetLimit $budgetLimit, string $text): void;
+
/**
* Destroy a budget limit.
*/
diff --git a/app/Transformers/BudgetLimitTransformer.php b/app/Transformers/BudgetLimitTransformer.php
index ad8225ceec..d75440a8fd 100644
--- a/app/Transformers/BudgetLimitTransformer.php
+++ b/app/Transformers/BudgetLimitTransformer.php
@@ -25,6 +25,7 @@ declare(strict_types=1);
namespace FireflyIII\Transformers;
use FireflyIII\Models\BudgetLimit;
+use FireflyIII\Repositories\Budget\BudgetLimitRepositoryInterface;
use FireflyIII\Repositories\Budget\OperationsRepository;
use Illuminate\Support\Collection;
use League\Fractal\Resource\Item;
@@ -54,8 +55,10 @@ class BudgetLimitTransformer extends AbstractTransformer
*/
public function transform(BudgetLimit $budgetLimit): array
{
- $repository = app(OperationsRepository::class);
+ $repository = app(OperationsRepository::class);
+ $limitRepos = app(BudgetLimitRepositoryInterface::class);
$repository->setUser($budgetLimit->budget->user);
+ $limitRepos->setUser($budgetLimit->budget->user);
$expenses = $repository->sumExpenses(
$budgetLimit->start_date,
$budgetLimit->end_date,
@@ -65,6 +68,7 @@ class BudgetLimitTransformer extends AbstractTransformer
);
$currency = $budgetLimit->transactionCurrency;
$amount = $budgetLimit->amount;
+ $notes = $limitRepos->getNoteText($budgetLimit);
$currencyDecimalPlaces = 2;
$currencyId = null;
$currencyName = null;
@@ -78,16 +82,16 @@ class BudgetLimitTransformer extends AbstractTransformer
$currencySymbol = $currency->symbol;
$currencyDecimalPlaces = $currency->decimal_places;
}
- $amount = app('steam')->bcround($amount, $currencyDecimalPlaces);
+ $amount = app('steam')->bcround($amount, $currencyDecimalPlaces);
return [
- 'id' => (string)$budgetLimit->id,
+ 'id' => (string) $budgetLimit->id,
'created_at' => $budgetLimit->created_at->toAtomString(),
'updated_at' => $budgetLimit->updated_at->toAtomString(),
'start' => $budgetLimit->start_date->toAtomString(),
'end' => $budgetLimit->end_date->endOfDay()->toAtomString(),
- 'budget_id' => (string)$budgetLimit->budget_id,
- 'currency_id' => (string)$currencyId,
+ 'budget_id' => (string) $budgetLimit->budget_id,
+ 'currency_id' => (string) $currencyId,
'currency_code' => $currencyCode,
'currency_name' => $currencyName,
'currency_decimal_places' => $currencyDecimalPlaces,
@@ -95,10 +99,11 @@ class BudgetLimitTransformer extends AbstractTransformer
'amount' => $amount,
'period' => $budgetLimit->period,
'spent' => $expenses[$currencyId]['sum'] ?? '0',
+ 'notes' => '' === $notes ? null : $notes,
'links' => [
[
'rel' => 'self',
- 'uri' => '/budgets/limits/'.$budgetLimit->id,
+ 'uri' => '/budgets/limits/' . $budgetLimit->id,
],
],
];
From 9ad005e31fcabca44840c927c2772a1fbcc09937 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 30 Nov 2024 06:19:21 +0100
Subject: [PATCH 004/167] Add edit button for notes
https://github.com/firefly-iii/firefly-iii/issues/5523
---
.../Budget/BudgetLimitController.php | 95 ++++++++++++-------
.../Controllers/Budget/IndexController.php | 1 +
public/v1/js/ff/budgets/index.js | 20 ++++
resources/lang/en_US/firefly.php | 4 +
.../views/budgets/budget-limits/create.twig | 4 +
.../views/budgets/budget-limits/edit.twig | 28 ++++++
.../views/budgets/budget-limits/show.twig | 20 ++++
resources/views/budgets/index.twig | 11 ++-
routes/web.php | 8 +-
9 files changed, 154 insertions(+), 37 deletions(-)
create mode 100644 resources/views/budgets/budget-limits/edit.twig
create mode 100644 resources/views/budgets/budget-limits/show.twig
diff --git a/app/Http/Controllers/Budget/BudgetLimitController.php b/app/Http/Controllers/Budget/BudgetLimitController.php
index effd7ac2cb..c1dbe62020 100644
--- a/app/Http/Controllers/Budget/BudgetLimitController.php
+++ b/app/Http/Controllers/Budget/BudgetLimitController.php
@@ -63,7 +63,7 @@ class BudgetLimitController extends Controller
parent::__construct();
$this->middleware(
function ($request, $next) {
- app('view')->share('title', (string)trans('firefly.budgets'));
+ app('view')->share('title', (string) trans('firefly.budgets'));
app('view')->share('mainTitleIcon', 'fa-pie-chart');
$this->repository = app(BudgetRepositoryInterface::class);
$this->opsRepository = app(OperationsRepositoryInterface::class);
@@ -84,7 +84,7 @@ class BudgetLimitController extends Controller
$budgetLimits = $this->blRepository->getBudgetLimits($budget, $start, $end);
// remove already budgeted currencies with the same date range
- $currencies = $collection->filter(
+ $currencies = $collection->filter(
static function (TransactionCurrency $currency) use ($budgetLimits, $start, $end) {
/** @var BudgetLimit $limit */
foreach ($budgetLimits as $limit) {
@@ -101,6 +101,24 @@ class BudgetLimitController extends Controller
return view('budgets.budget-limits.create', compact('start', 'end', 'currencies', 'budget'));
}
+ /**
+ * @return Factory|View
+ */
+ public function show(BudgetLimit $budgetLimit)
+ {
+ $notes = $this->blRepository->getNoteText($budgetLimit);
+ return view('budgets.budget-limits.show', compact('budgetLimit', 'notes'));
+ }
+
+ /**
+ * @return Factory|View
+ */
+ public function edit(BudgetLimit $budgetLimit)
+ {
+ $notes = $this->blRepository->getNoteText($budgetLimit);
+ return view('budgets.budget-limits.edit', compact('budgetLimit', 'notes'));
+ }
+
/**
* @return Redirector|RedirectResponse
*/
@@ -117,23 +135,23 @@ class BudgetLimitController extends Controller
*
* @throws FireflyException
*/
- public function store(Request $request): JsonResponse|RedirectResponse
+ public function store(Request $request): JsonResponse | RedirectResponse
{
app('log')->debug('Going to store new budget-limit.', $request->all());
// first search for existing one and update it if necessary.
- $currency = $this->currencyRepos->find((int)$request->get('transaction_currency_id'));
- $budget = $this->repository->find((int)$request->get('budget_id'));
+ $currency = $this->currencyRepos->find((int) $request->get('transaction_currency_id'));
+ $budget = $this->repository->find((int) $request->get('budget_id'));
if (null === $currency || null === $budget) {
throw new FireflyException('No valid currency or budget.');
}
- $start = Carbon::createFromFormat('Y-m-d', $request->get('start'));
- $end = Carbon::createFromFormat('Y-m-d', $request->get('end'));
+ $start = Carbon::createFromFormat('Y-m-d', $request->get('start'));
+ $end = Carbon::createFromFormat('Y-m-d', $request->get('end'));
if (null === $start || null === $end) {
return response()->json([]);
}
- $amount = (string)$request->get('amount');
+ $amount = (string) $request->get('amount');
$start->startOfDay();
$end->startOfDay();
@@ -143,7 +161,7 @@ class BudgetLimitController extends Controller
app('log')->debug(sprintf('Start: %s, end: %s', $start->format('Y-m-d'), $end->format('Y-m-d')));
- $limit = $this->blRepository->find($budget, $currency, $start, $end);
+ $limit = $this->blRepository->find($budget, $currency, $start, $end);
// sanity check on amount:
if (0 === bccomp($amount, '0')) {
@@ -154,7 +172,7 @@ class BudgetLimitController extends Controller
// return empty=ish array:
return response()->json([]);
}
- if ((int)$amount > 268435456) { // intentional cast to integer
+ if ((int) $amount > 268435456) { // intentional cast to integer
$amount = '268435456';
}
if (-1 === bccomp($amount, '0')) {
@@ -169,41 +187,47 @@ class BudgetLimitController extends Controller
$limit = $this->blRepository->store(
[
'budget_id' => $request->get('budget_id'),
- 'currency_id' => (int)$request->get('transaction_currency_id'),
+ 'currency_id' => (int) $request->get('transaction_currency_id'),
'start_date' => $start,
'end_date' => $end,
'amount' => $amount,
]
);
}
+ // parse notes, if any.
+ $notes = (string) $request->get('notes');
+ $this->blRepository->setNoteText($limit, $notes);
if ($request->expectsJson()) {
- $array = $limit->toArray();
+ $array = $limit->toArray();
// add some extra metadata:
- $spentArr = $this->opsRepository->sumExpenses($limit->start_date, $limit->end_date, null, new Collection([$budget]), $currency);
- $array['spent'] = $spentArr[$currency->id]['sum'] ?? '0';
- $array['left_formatted'] = app('amount')->formatAnything($limit->transactionCurrency, bcadd($array['spent'], $array['amount']));
- $array['amount_formatted'] = app('amount')->formatAnything($limit->transactionCurrency, $limit['amount']);
- $array['days_left'] = (string)$this->activeDaysLeft($start, $end);
+ $spentArr = $this->opsRepository->sumExpenses($limit->start_date, $limit->end_date, null, new Collection([$budget]), $currency);
+ $array['spent'] = $spentArr[$currency->id]['sum'] ?? '0';
+ $array['left_formatted'] = app('amount')->formatAnything($limit->transactionCurrency, bcadd($array['spent'], $array['amount']));
+ $array['amount_formatted'] = app('amount')->formatAnything($limit->transactionCurrency, $limit['amount']);
+ $array['days_left'] = (string) $this->activeDaysLeft($start, $end);
// left per day:
- $array['left_per_day'] = 0 === bccomp('0', $array['days_left']) ? bcadd($array['spent'], $array['amount']) : bcdiv(bcadd($array['spent'], $array['amount']), $array['days_left']);
+ $array['left_per_day'] = 0 === bccomp('0', $array['days_left']) ? bcadd($array['spent'], $array['amount']) : bcdiv(bcadd($array['spent'], $array['amount']), $array['days_left']);
// left per day formatted.
$array['left_per_day_formatted'] = app('amount')->formatAnything($limit->transactionCurrency, $array['left_per_day']);
+ // notes:
+ $array['notes'] = $this->blRepository->getNoteText($limit);
+
return response()->json($array);
}
return redirect(route('budgets.index'));
}
- public function update(Request $request, BudgetLimit $budgetLimit): JsonResponse
+ public function update(Request $request, BudgetLimit $budgetLimit): JsonResponse|RedirectResponse
{
- $amount = (string)$request->get('amount');
+ $amount = (string) $request->get('amount');
if ('' === $amount) {
$amount = '0';
}
- if ((int)$amount > 268435456) { // 268 million, intentional integer
+ if ((int) $amount > 268435456) { // 268 million, intentional integer
$amount = '268435456';
}
// sanity check on amount:
@@ -211,7 +235,7 @@ class BudgetLimitController extends Controller
$budgetId = $budgetLimit->budget_id;
$currency = $budgetLimit->transactionCurrency;
$this->blRepository->destroyBudgetLimit($budgetLimit);
- $array = [
+ $array = [
'budget_id' => $budgetId,
'left_formatted' => app('amount')->formatAnything($currency, '0'),
'left_per_day_formatted' => app('amount')->formatAnything($currency, '0'),
@@ -224,29 +248,36 @@ class BudgetLimitController extends Controller
if (-1 === bccomp($amount, '0')) {
$amount = bcmul($amount, '-1');
}
+ $notes = (string)$request->get('notes');
+ if(strlen($notes) > 32768) {
+ $notes = substr($notes, 0, 32768);
+ }
- $limit = $this->blRepository->update($budgetLimit, ['amount' => $amount]);
+
+ $limit = $this->blRepository->update($budgetLimit, ['amount' => $amount,'notes' => $notes]);
app('preferences')->mark();
- $array = $limit->toArray();
+ $array = $limit->toArray();
- $spentArr = $this->opsRepository->sumExpenses(
+ $spentArr = $this->opsRepository->sumExpenses(
$limit->start_date,
$limit->end_date,
null,
new Collection([$budgetLimit->budget]),
$budgetLimit->transactionCurrency
);
- $daysLeft = $this->activeDaysLeft($limit->start_date, $limit->end_date);
- $array['spent'] = $spentArr[$budgetLimit->transactionCurrency->id]['sum'] ?? '0';
- $array['left_formatted'] = app('amount')->formatAnything($limit->transactionCurrency, bcadd($array['spent'], $array['amount']));
- $array['amount_formatted'] = app('amount')->formatAnything($limit->transactionCurrency, $limit['amount']);
- $array['days_left'] = (string)$daysLeft;
- $array['left_per_day'] = 0 === $daysLeft ? bcadd($array['spent'], $array['amount']) : bcdiv(bcadd($array['spent'], $array['amount']), $array['days_left']);
+ $daysLeft = $this->activeDaysLeft($limit->start_date, $limit->end_date);
+ $array['spent'] = $spentArr[$budgetLimit->transactionCurrency->id]['sum'] ?? '0';
+ $array['left_formatted'] = app('amount')->formatAnything($limit->transactionCurrency, bcadd($array['spent'], $array['amount']));
+ $array['amount_formatted'] = app('amount')->formatAnything($limit->transactionCurrency, $limit['amount']);
+ $array['days_left'] = (string) $daysLeft;
+ $array['left_per_day'] = 0 === $daysLeft ? bcadd($array['spent'], $array['amount']) : bcdiv(bcadd($array['spent'], $array['amount']), $array['days_left']);
// left per day formatted.
$array['amount'] = app('steam')->bcround($limit['amount'], $limit->transactionCurrency->decimal_places);
$array['left_per_day_formatted'] = app('amount')->formatAnything($limit->transactionCurrency, $array['left_per_day']);
-
+ if ('true' === $request->get('redirect')) {
+ return redirect(route('budgets.index'));
+ }
return response()->json($array);
}
}
diff --git a/app/Http/Controllers/Budget/IndexController.php b/app/Http/Controllers/Budget/IndexController.php
index fd182e9212..5fde689d96 100644
--- a/app/Http/Controllers/Budget/IndexController.php
+++ b/app/Http/Controllers/Budget/IndexController.php
@@ -213,6 +213,7 @@ class IndexController extends Controller
$array['budgeted'][] = [
'id' => $limit->id,
'amount' => $amount,
+ 'notes' => $this->blRepository->getNoteText($limit),
'start_date' => $limit->start_date->isoFormat($this->monthAndDayFormat),
'end_date' => $limit->end_date->isoFormat($this->monthAndDayFormat),
'in_range' => $limit->start_date->isSameDay($start) && $limit->end_date->isSameDay($end),
diff --git a/public/v1/js/ff/budgets/index.js b/public/v1/js/ff/budgets/index.js
index b6d702fa95..63444d096b 100644
--- a/public/v1/js/ff/budgets/index.js
+++ b/public/v1/js/ff/budgets/index.js
@@ -35,6 +35,8 @@ $(function () {
$('.budget_amount').on('change', updateBudgetedAmount);
$('.create_bl').on('click', createBudgetLimit);
+ $('.edit_bl').on('click', editBudgetLimit);
+ $('.show_bl').on('click', showBudgetLimit);
$('.delete_bl').on('click', deleteBudgetLimit);
@@ -216,6 +218,24 @@ function createBudgetLimit(e) {
return false;
}
+function editBudgetLimit(e) {
+ var button = $(e.currentTarget);
+ var budgetLimitId = button.data('id');
+ $('#defaultModal').empty().load(editBudgetLimitUrl.replace('REPLACEME', budgetLimitId.toString()), function () {
+ $('#defaultModal').modal('show');
+ });
+ return false;
+}
+
+function showBudgetLimit(e) {
+ var button = $(e.currentTarget);
+ var budgetLimitId = button.data('id');
+ $('#defaultModal').empty().load(showBudgetLimitUrl.replace('REPLACEME', budgetLimitId.toString()), function () {
+ $('#defaultModal').modal('show');
+ });
+ return false;
+}
+
function deleteBudgetLimit(e) {
e.preventDefault();
var button = $(e.currentTarget);
diff --git a/resources/lang/en_US/firefly.php b/resources/lang/en_US/firefly.php
index e472b7484a..aa395cd3da 100644
--- a/resources/lang/en_US/firefly.php
+++ b/resources/lang/en_US/firefly.php
@@ -2068,6 +2068,10 @@ return [
'opt_group_l_Mortgage' => 'Liability: Mortgage',
'opt_group_l_Credit card' => 'Liability: Credit card',
'notes' => 'Notes',
+ 'view_notes' => 'View notes',
+ 'set_budget_limit_notes' => 'View the notes for this budgeted amount',
+ 'edit_bl_notes' => 'Edit notes',
+ 'update_bl_notes' => 'Update notes',
'unknown_journal_error' => 'Could not store the transaction. Please check the log files.',
'attachment_not_found' => 'This attachment could not be found.',
'journal_link_bill' => 'This transaction is linked to bill :name. To remove the connection, uncheck the checkbox. Use rules to connect it to another bill.',
diff --git a/resources/views/budgets/budget-limits/create.twig b/resources/views/budgets/budget-limits/create.twig
index ce0c05d06a..112bd739e7 100644
--- a/resources/views/budgets/budget-limits/create.twig
+++ b/resources/views/budgets/budget-limits/create.twig
@@ -25,6 +25,10 @@
+
+
+ {{ trans('firefly.field_supports_markdown')|raw }}
+
@@ -444,6 +451,8 @@
var createBudgetLimitUrl = "{{ route('budget-limits.create', ['REPLACEME', start.format('Y-m-d'), end.format('Y-m-d')]) }}";
var storeBudgetLimitUrl = "{{ route('budget-limits.store') }}";
var updateBudgetLimitUrl = "{{ route('budget-limits.update', ['REPLACEME']) }}";
+ var showBudgetLimitUrl = "{{ route('budget-limits.show', ['REPLACEME']) }}";
+ var editBudgetLimitUrl = "{{ route('budget-limits.edit', ['REPLACEME']) }}";
var deleteBudgetLimitUrl = "{{ route('budget-limits.delete', ['REPLACEME']) }}";
var totalBudgetedUrl = "{{ route('json.budget.total-budgeted', ['REPLACEME', start.format('Y-m-d'), end.format('Y-m-d')]) }}";
diff --git a/routes/web.php b/routes/web.php
index e5a9b8c84f..a702e49163 100644
--- a/routes/web.php
+++ b/routes/web.php
@@ -304,10 +304,10 @@ Route::group(
Route::group(
['middleware' => 'user-full-auth', 'namespace' => 'FireflyIII\Http\Controllers', 'prefix' => 'budget-limits', 'as' => 'budget-limits.'],
static function (): void {
- Route::get('create/{budget}/{start_date}/{end_date}', ['uses' => 'Budget\BudgetLimitController@create', 'as' => 'create'])
- ->where(['start_date' => DATEFORMAT])
- ->where(['end_date' => DATEFORMAT])
- ;
+ Route::get('create/{budget}/{start_date}/{end_date}', ['uses' => 'Budget\BudgetLimitController@create', 'as' => 'create'])->where(['start_date' => DATEFORMAT])->where(['end_date' => DATEFORMAT]);
+ Route::get('edit/{budgetLimit}', ['uses' => 'Budget\BudgetLimitController@edit', 'as' => 'edit']);
+ Route::get('show/{budgetLimit}', ['uses' => 'Budget\BudgetLimitController@show', 'as' => 'show']);
+
Route::post('store', ['uses' => 'Budget\BudgetLimitController@store', 'as' => 'store']);
Route::post('delete/{budgetLimit}', ['uses' => 'Budget\BudgetLimitController@delete', 'as' => 'delete']);
From 92190bbc54bf681891d5d739da678e1bf38311f8 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 30 Nov 2024 15:57:11 +0100
Subject: [PATCH 005/167] Rename fields in piggy bank.
---
.../Autocomplete/PiggyBankController.php | 2 +-
.../Commands/Correction/CorrectAmounts.php | 4 +-
app/Handlers/Observer/PiggyBankObserver.php | 10 +-
.../Controllers/PiggyBank/IndexController.php | 1 +
app/Models/PiggyBank.php | 22 ++--
app/Models/PiggyBankRepetition.php | 2 +-
.../2021_08_28_073733_user_groups.php | 1 +
.../2024_11_30_075826_multi_piggy.php | 103 ++++++++++++++++++
8 files changed, 127 insertions(+), 18 deletions(-)
create mode 100644 database/migrations/2024_11_30_075826_multi_piggy.php
diff --git a/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php b/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php
index 3373d6c708..1c29c51bec 100644
--- a/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php
+++ b/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php
@@ -105,7 +105,7 @@ class PiggyBankController extends Controller
/** @var PiggyBank $piggy */
foreach ($piggies as $piggy) {
$currency = $this->accountRepository->getAccountCurrency($piggy->account) ?? $defaultCurrency;
- $currentAmount = $this->piggyRepository->getRepetition($piggy)->currentamount ?? '0';
+ $currentAmount = $this->piggyRepository->getRepetition($piggy)->current_amount ?? '0';
$objectGroup = $piggy->objectGroups()->first();
$response[] = [
'id' => (string)$piggy->id,
diff --git a/app/Console/Commands/Correction/CorrectAmounts.php b/app/Console/Commands/Correction/CorrectAmounts.php
index ad30463120..73ff3b3309 100644
--- a/app/Console/Commands/Correction/CorrectAmounts.php
+++ b/app/Console/Commands/Correction/CorrectAmounts.php
@@ -173,7 +173,7 @@ class CorrectAmounts extends Command
/** @var PiggyBankRepetition $item */
foreach ($set as $item) {
- $item->currentamount = app('steam')->positive($item->currentamount);
+ $item->currentamount = app('steam')->positive($item->current_amount);
$item->save();
}
$this->friendlyInfo(sprintf('Corrected %d piggy bank repetition amount(s).', $count));
@@ -191,7 +191,7 @@ class CorrectAmounts extends Command
/** @var PiggyBank $item */
foreach ($set as $item) {
- $item->targetamount = app('steam')->positive($item->targetamount);
+ $item->targetamount = app('steam')->positive($item->target_amount);
$item->save();
}
$this->friendlyInfo(sprintf('Corrected %d piggy bank amount(s).', $count));
diff --git a/app/Handlers/Observer/PiggyBankObserver.php b/app/Handlers/Observer/PiggyBankObserver.php
index 5bd961f0e5..2857f7c2b7 100644
--- a/app/Handlers/Observer/PiggyBankObserver.php
+++ b/app/Handlers/Observer/PiggyBankObserver.php
@@ -37,11 +37,11 @@ class PiggyBankObserver
app('log')->debug('Observe "created" of a piggy bank.');
$repetition = new PiggyBankRepetition();
$repetition->piggyBank()->associate($piggyBank);
- $repetition->startdate = $piggyBank->startdate;
- $repetition->startdate_tz = $piggyBank->startdate->format('e');
- $repetition->targetdate = $piggyBank->targetdate;
- $repetition->targetdate_tz = $piggyBank->targetdate?->format('e');
- $repetition->currentamount = '0';
+ $repetition->start_date = $piggyBank->startdate;
+ $repetition->start_date_tz = $piggyBank->startdate->format('e');
+ $repetition->target_date = $piggyBank->targetdate;
+ $repetition->target_date_tz = $piggyBank->targetdate?->format('e');
+ $repetition->current_amount = '0';
$repetition->save();
}
diff --git a/app/Http/Controllers/PiggyBank/IndexController.php b/app/Http/Controllers/PiggyBank/IndexController.php
index 72396eb20d..9c3578550e 100644
--- a/app/Http/Controllers/PiggyBank/IndexController.php
+++ b/app/Http/Controllers/PiggyBank/IndexController.php
@@ -27,6 +27,7 @@ namespace FireflyIII\Http\Controllers\PiggyBank;
use Carbon\Carbon;
use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Http\Controllers\Controller;
+use FireflyIII\Models\Account;
use FireflyIII\Models\PiggyBank;
use FireflyIII\Repositories\ObjectGroup\OrganisesObjectGroups;
use FireflyIII\Repositories\PiggyBank\PiggyBankRepositoryInterface;
diff --git a/app/Models/PiggyBank.php b/app/Models/PiggyBank.php
index abef05764f..0edfa05b9e 100644
--- a/app/Models/PiggyBank.php
+++ b/app/Models/PiggyBank.php
@@ -27,6 +27,7 @@ use FireflyIII\Support\Models\ReturnsIntegerIdTrait;
use Illuminate\Database\Eloquent\Casts\Attribute;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsTo;
+use Illuminate\Database\Eloquent\Relations\BelongsToMany;
use Illuminate\Database\Eloquent\Relations\HasMany;
use Illuminate\Database\Eloquent\Relations\MorphMany;
use Illuminate\Database\Eloquent\Relations\MorphToMany;
@@ -46,17 +47,15 @@ class PiggyBank extends Model
'created_at' => 'datetime',
'updated_at' => 'datetime',
'deleted_at' => 'datetime',
- 'startdate' => 'date',
- 'targetdate' => 'date',
+ 'start_date' => 'date',
+ 'target_date' => 'date',
'order' => 'int',
'active' => 'boolean',
'encrypted' => 'boolean',
- 'targetamount' => 'string',
+ 'target_amount' => 'string',
];
- protected $fillable = ['name', 'account_id', 'order', 'targetamount', 'startdate', 'startdate_tz', 'targetdate', 'targetdate_tz', 'active'];
-
- protected $hidden = ['targetamount_encrypted', 'encrypted'];
+ protected $fillable = ['name', 'account_id', 'order', 'target_amount', 'start_date', 'start_date_tz', 'target_date', 'target_date_tz', 'active'];
/**
* Route binder. Converts the key in the URL to the specified object (or throw 404).
@@ -110,6 +109,11 @@ class PiggyBank extends Model
return $this->hasMany(PiggyBankEvent::class);
}
+ public function accounts(): BelongsToMany
+ {
+ return $this->belongsToMany(Account::class);
+ }
+
public function piggyBankRepetitions(): HasMany
{
return $this->hasMany(PiggyBankRepetition::class);
@@ -118,9 +122,9 @@ class PiggyBank extends Model
/**
* @param mixed $value
*/
- public function setTargetamountAttribute($value): void
+ public function setTargetAmountAttribute($value): void
{
- $this->attributes['targetamount'] = (string)$value;
+ $this->attributes['target_amount'] = (string)$value;
}
protected function accountId(): Attribute
@@ -140,7 +144,7 @@ class PiggyBank extends Model
/**
* Get the max amount
*/
- protected function targetamount(): Attribute
+ protected function targetAmount(): Attribute
{
return Attribute::make(
get: static fn ($value) => (string)$value,
diff --git a/app/Models/PiggyBankRepetition.php b/app/Models/PiggyBankRepetition.php
index 38008361dd..eaa42bed7d 100644
--- a/app/Models/PiggyBankRepetition.php
+++ b/app/Models/PiggyBankRepetition.php
@@ -47,7 +47,7 @@ class PiggyBankRepetition extends Model
'virtual_balance' => 'string',
];
- protected $fillable = ['piggy_bank_id', 'startdate', 'startdate_tz', 'targetdate', 'targetdate_tz', 'currentamount'];
+ protected $fillable = ['piggy_bank_id', 'start_date', 'start_date_tz', 'target_date', 'target_date_tz', 'current_amount'];
public function piggyBank(): BelongsTo
{
diff --git a/database/migrations/2021_08_28_073733_user_groups.php b/database/migrations/2021_08_28_073733_user_groups.php
index 21a25beed4..1111ddc671 100644
--- a/database/migrations/2021_08_28_073733_user_groups.php
+++ b/database/migrations/2021_08_28_073733_user_groups.php
@@ -42,6 +42,7 @@ class UserGroups extends Migration
'categories',
'recurrences',
'object_groups',
+ 'preferences',
'rule_groups',
'rules',
'tags',
diff --git a/database/migrations/2024_11_30_075826_multi_piggy.php b/database/migrations/2024_11_30_075826_multi_piggy.php
new file mode 100644
index 0000000000..d1675663f2
--- /dev/null
+++ b/database/migrations/2024_11_30_075826_multi_piggy.php
@@ -0,0 +1,103 @@
+dropForeign('piggy_banks_account_id_foreign');
+ });
+ Schema::table('piggy_banks', static function (Blueprint $table) {
+ // 2. make column nullable.
+ $table->unsignedInteger('account_id')->nullable()->change();
+ });
+ Schema::table('piggy_banks', static function (Blueprint $table) {
+ // 3. add currency
+ $table->integer('transaction_currency_id', false, true)->after('account_id');
+ $table->foreign('transaction_currency_id','unique_currency')->references('id')->on('transaction_currencies')->onDelete('cascade');
+ });
+ Schema::table('piggy_banks', static function (Blueprint $table) {
+ // 4. rename columns
+ $table->renameColumn('targetamount', 'target_amount');
+ $table->renameColumn('startdate', 'start_date');
+ $table->renameColumn('targetdate', 'target_date');
+ $table->renameColumn('startdate_tz', 'start_date_tz');
+ $table->renameColumn('targetdate_tz', 'target_date_tz');
+ });
+ Schema::table('piggy_banks', static function (Blueprint $table) {
+ // 5. add new index
+ $table->foreign('account_id')->references('id')->on('accounts')->onDelete('set null');
+ });
+
+ // rename some fields in piggy bank reps.
+ Schema::table('piggy_bank_repetitions', static function (Blueprint $table) {
+ // 6. rename columns
+ $table->renameColumn('currentamount', 'current_amount');
+ $table->renameColumn('startdate', 'start_date');
+ $table->renameColumn('targetdate', 'target_date');
+ $table->renameColumn('startdate_tz', 'start_date_tz');
+ $table->renameColumn('targetdate_tz', 'target_date_tz');
+ });
+
+ // create table account_piggy_bank
+ Schema::create('account_piggy_bank', static function (Blueprint $table) {
+ $table->id();
+ $table->integer('account_id', false, true);
+ $table->integer('piggy_bank_id',false, true);
+ $table->decimal('current_amount', 32, 12)->default('0');
+ $table->foreign('account_id')->references('id')->on('accounts')->onDelete('cascade');
+ $table->foreign('piggy_bank_id')->references('id')->on('piggy_banks')->onDelete('cascade');
+ $table->unique(['account_id', 'piggy_bank_id'],'unique_piggy_save');
+ });
+
+ }
+
+ /**
+ * Reverse the migrations.
+ */
+ public function down(): void
+ {
+ Schema::table('piggy_banks', static function (Blueprint $table) {
+ // 1. drop account index again.
+ $table->dropForeign('piggy_banks_account_id_foreign');
+
+ // rename columns again.
+ $table->renameColumn('target_amount', 'targetamount');
+ $table->renameColumn('start_date', 'startdate');
+ $table->renameColumn('target_date', 'targetdate');
+ $table->renameColumn('start_date_tz', 'startdate_tz');
+ $table->renameColumn('target_date_tz', 'targetdate_tz');
+
+ // 3. drop currency again + index
+ $table->dropForeign('unique_currency');
+ $table->dropColumn('transaction_currency_id');
+
+ // 2. make column non-nullable.
+ $table->unsignedInteger('account_id')->change();
+
+ // 5. add new index
+ $table->foreign('account_id')->references('id')->on('accounts')->onDelete('cascade');
+ });
+
+ // rename some fields in piggy bank reps.
+ Schema::table('piggy_bank_repetitions', static function (Blueprint $table) {
+ // 6. rename columns
+ $table->renameColumn('current_amount', 'currentamount');
+ $table->renameColumn('start_date', 'startdate');
+ $table->renameColumn('target_date', 'targetdate');
+ $table->renameColumn('start_date_tz', 'startdate_tz');
+ $table->renameColumn('target_date_tz', 'targetdate_tz');
+ });
+
+ Schema::dropIfExists('account_piggy_bank');
+ }
+};
From 21a6927279f25ab41b3462d10c7e9d74e4325da1 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 30 Nov 2024 16:02:30 +0100
Subject: [PATCH 006/167] Rename fields for piggy bank
---
.../Autocomplete/PiggyBankController.php | 2 +-
.../Commands/Correction/CorrectAmounts.php | 4 +-
app/Console/Commands/Tools/ApplyRules.php | 4 +-
app/Handlers/Observer/PiggyBankObserver.php | 8 ++--
.../Controllers/Chart/PiggyBankController.php | 2 +-
.../Controllers/Json/FrontpageController.php | 6 +--
.../PiggyBank/AmountController.php | 8 ++--
.../Controllers/PiggyBank/EditController.php | 8 ++--
app/Models/PiggyBankRepetition.php | 20 ++++-----
.../PiggyBank/ModifiesPiggyBanks.php | 42 +++++++++----------
.../PiggyBank/PiggyBankRepository.php | 22 +++++-----
app/Support/Export/ExportDataGenerator.php | 8 ++--
.../Actions/UpdatePiggybank.php | 6 +--
app/Transformers/PiggyBankTransformer.php | 8 ++--
app/Transformers/V2/PiggyBankTransformer.php | 10 ++---
15 files changed, 79 insertions(+), 79 deletions(-)
diff --git a/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php b/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php
index 1c29c51bec..cf29aa037a 100644
--- a/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php
+++ b/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php
@@ -114,7 +114,7 @@ class PiggyBankController extends Controller
'%s (%s / %s)',
$piggy->name,
app('amount')->formatAnything($currency, $currentAmount, false),
- app('amount')->formatAnything($currency, $piggy->targetamount, false),
+ app('amount')->formatAnything($currency, $piggy->target_amount, false),
),
'currency_id' => (string)$currency->id,
'currency_name' => $currency->name,
diff --git a/app/Console/Commands/Correction/CorrectAmounts.php b/app/Console/Commands/Correction/CorrectAmounts.php
index 73ff3b3309..639c96edec 100644
--- a/app/Console/Commands/Correction/CorrectAmounts.php
+++ b/app/Console/Commands/Correction/CorrectAmounts.php
@@ -173,7 +173,7 @@ class CorrectAmounts extends Command
/** @var PiggyBankRepetition $item */
foreach ($set as $item) {
- $item->currentamount = app('steam')->positive($item->current_amount);
+ $item->current_amount = app('steam')->positive($item->current_amount);
$item->save();
}
$this->friendlyInfo(sprintf('Corrected %d piggy bank repetition amount(s).', $count));
@@ -191,7 +191,7 @@ class CorrectAmounts extends Command
/** @var PiggyBank $item */
foreach ($set as $item) {
- $item->targetamount = app('steam')->positive($item->target_amount);
+ $item->target_amount = app('steam')->positive($item->target_amount);
$item->save();
}
$this->friendlyInfo(sprintf('Corrected %d piggy bank amount(s).', $count));
diff --git a/app/Console/Commands/Tools/ApplyRules.php b/app/Console/Commands/Tools/ApplyRules.php
index 5e6e64552f..023864e1aa 100644
--- a/app/Console/Commands/Tools/ApplyRules.php
+++ b/app/Console/Commands/Tools/ApplyRules.php
@@ -128,7 +128,7 @@ class ApplyRules extends Command
$ruleEngine->addOperator(['type' => 'account_id', 'value' => $list]);
// add the date as a filter:
- $ruleEngine->addOperator(['type' => 'date_after', 'value' => $this->startDate->format('Y-m-d')]);
+ $ruleEngine->addOperator(['type' => 'date_after', 'value' => $this->start_date->format('Y-m-d')]);
$ruleEngine->addOperator(['type' => 'date_before', 'value' => $this->endDate->format('Y-m-d')]);
// start running rules.
@@ -296,7 +296,7 @@ class ApplyRules extends Command
[$inputEnd, $inputStart] = [$inputStart, $inputEnd];
}
- $this->startDate = $inputStart;
+ $this->start_date = $inputStart;
$this->endDate = $inputEnd;
}
diff --git a/app/Handlers/Observer/PiggyBankObserver.php b/app/Handlers/Observer/PiggyBankObserver.php
index 2857f7c2b7..40bde63a1a 100644
--- a/app/Handlers/Observer/PiggyBankObserver.php
+++ b/app/Handlers/Observer/PiggyBankObserver.php
@@ -37,10 +37,10 @@ class PiggyBankObserver
app('log')->debug('Observe "created" of a piggy bank.');
$repetition = new PiggyBankRepetition();
$repetition->piggyBank()->associate($piggyBank);
- $repetition->start_date = $piggyBank->startdate;
- $repetition->start_date_tz = $piggyBank->startdate->format('e');
- $repetition->target_date = $piggyBank->targetdate;
- $repetition->target_date_tz = $piggyBank->targetdate?->format('e');
+ $repetition->start_date = $piggyBank->start_date;
+ $repetition->start_date_tz = $piggyBank->start_date->format('e');
+ $repetition->target_date = $piggyBank->target_date;
+ $repetition->target_date_tz = $piggyBank->target_date?->format('e');
$repetition->current_amount = '0';
$repetition->save();
}
diff --git a/app/Http/Controllers/Chart/PiggyBankController.php b/app/Http/Controllers/Chart/PiggyBankController.php
index 4bf27e2748..7bbfd0aae0 100644
--- a/app/Http/Controllers/Chart/PiggyBankController.php
+++ b/app/Http/Controllers/Chart/PiggyBankController.php
@@ -75,7 +75,7 @@ class PiggyBankController extends Controller
$locale = app('steam')->getLocale();
// get first event or start date of piggy bank or today
- $startDate = $piggyBank->startdate ?? today(config('app.timezone'));
+ $startDate = $piggyBank->start_date ?? today(config('app.timezone'));
/** @var null|PiggyBankEvent $firstEvent */
$firstEvent = $set->first();
diff --git a/app/Http/Controllers/Json/FrontpageController.php b/app/Http/Controllers/Json/FrontpageController.php
index a8ab134e96..959c1ce4e6 100644
--- a/app/Http/Controllers/Json/FrontpageController.php
+++ b/app/Http/Controllers/Json/FrontpageController.php
@@ -50,15 +50,15 @@ class FrontpageController extends Controller
if (1 === bccomp($amount, '0')) {
// percentage!
$pct = 0;
- if (0 !== bccomp($piggyBank->targetamount, '0')) {
- $pct = (int)bcmul(bcdiv($amount, $piggyBank->targetamount), '100');
+ if (0 !== bccomp($piggyBank->target_amount, '0')) {
+ $pct = (int)bcmul(bcdiv($amount, $piggyBank->target_amount), '100');
}
$entry = [
'id' => $piggyBank->id,
'name' => $piggyBank->name,
'amount' => $amount,
- 'target' => $piggyBank->targetamount,
+ 'target' => $piggyBank->target_amount,
'percentage' => $pct,
];
diff --git a/app/Http/Controllers/PiggyBank/AmountController.php b/app/Http/Controllers/PiggyBank/AmountController.php
index 28085daa06..d14446d291 100644
--- a/app/Http/Controllers/PiggyBank/AmountController.php
+++ b/app/Http/Controllers/PiggyBank/AmountController.php
@@ -72,8 +72,8 @@ class AmountController extends Controller
$leftOnAccount = $this->piggyRepos->leftOnAccount($piggyBank, today(config('app.timezone')));
$savedSoFar = $this->piggyRepos->getCurrentAmount($piggyBank);
$maxAmount = $leftOnAccount;
- if (0 !== bccomp($piggyBank->targetamount, '0')) {
- $leftToSave = bcsub($piggyBank->targetamount, $savedSoFar);
+ if (0 !== bccomp($piggyBank->target_amount, '0')) {
+ $leftToSave = bcsub($piggyBank->target_amount, $savedSoFar);
$maxAmount = min($leftOnAccount, $leftToSave);
}
$currency = $this->accountRepos->getAccountCurrency($piggyBank->account) ?? app('amount')->getDefaultCurrency();
@@ -94,8 +94,8 @@ class AmountController extends Controller
$savedSoFar = $this->piggyRepos->getCurrentAmount($piggyBank);
$maxAmount = $leftOnAccount;
- if (0 !== bccomp($piggyBank->targetamount, '0')) {
- $leftToSave = bcsub($piggyBank->targetamount, $savedSoFar);
+ if (0 !== bccomp($piggyBank->target_amount, '0')) {
+ $leftToSave = bcsub($piggyBank->target_amount, $savedSoFar);
$maxAmount = min($leftOnAccount, $leftToSave);
}
$currency = $this->accountRepos->getAccountCurrency($piggyBank->account) ?? app('amount')->getDefaultCurrency();
diff --git a/app/Http/Controllers/PiggyBank/EditController.php b/app/Http/Controllers/PiggyBank/EditController.php
index c0a2de083e..6df3ec3101 100644
--- a/app/Http/Controllers/PiggyBank/EditController.php
+++ b/app/Http/Controllers/PiggyBank/EditController.php
@@ -77,8 +77,8 @@ class EditController extends Controller
$subTitleIcon = 'fa-pencil';
$note = $piggyBank->notes()->first();
// Flash some data to fill the form.
- $targetDate = $piggyBank->targetdate?->format('Y-m-d');
- $startDate = $piggyBank->startdate?->format('Y-m-d');
+ $targetDate = $piggyBank->target_date?->format('Y-m-d');
+ $startDate = $piggyBank->start_date?->format('Y-m-d');
$currency = $this->accountRepository->getAccountCurrency($piggyBank->account);
if (null === $currency) {
$currency = app('amount')->getDefaultCurrency();
@@ -87,13 +87,13 @@ class EditController extends Controller
$preFilled = [
'name' => $piggyBank->name,
'account_id' => $piggyBank->account_id,
- 'targetamount' => app('steam')->bcround($piggyBank->targetamount, $currency->decimal_places),
+ 'targetamount' => app('steam')->bcround($piggyBank->target_amount, $currency->decimal_places),
'targetdate' => $targetDate,
'startdate' => $startDate,
'object_group' => null !== $piggyBank->objectGroups->first() ? $piggyBank->objectGroups->first()->title : '',
'notes' => null === $note ? '' : $note->text,
];
- if (0 === bccomp($piggyBank->targetamount, '0')) {
+ if (0 === bccomp($piggyBank->target_amount, '0')) {
$preFilled['targetamount'] = '';
}
session()->flash('preFilled', $preFilled);
diff --git a/app/Models/PiggyBankRepetition.php b/app/Models/PiggyBankRepetition.php
index eaa42bed7d..378af8edb7 100644
--- a/app/Models/PiggyBankRepetition.php
+++ b/app/Models/PiggyBankRepetition.php
@@ -42,8 +42,8 @@ class PiggyBankRepetition extends Model
= [
'created_at' => 'datetime',
'updated_at' => 'datetime',
- 'startdate' => SeparateTimezoneCaster::class,
- 'targetdate' => SeparateTimezoneCaster::class,
+ 'start_date' => SeparateTimezoneCaster::class,
+ 'target_date' => SeparateTimezoneCaster::class,
'virtual_balance' => 'string',
];
@@ -56,7 +56,7 @@ class PiggyBankRepetition extends Model
public function scopeOnDates(EloquentBuilder $query, Carbon $start, Carbon $target): EloquentBuilder
{
- return $query->where('startdate', $start->format('Y-m-d'))->where('targetdate', $target->format('Y-m-d'));
+ return $query->where('start_date', $start->format('Y-m-d'))->where('target_date', $target->format('Y-m-d'));
}
/**
@@ -66,14 +66,14 @@ class PiggyBankRepetition extends Model
{
return $query->where(
static function (EloquentBuilder $q) use ($date): void {
- $q->where('startdate', '<=', $date->format('Y-m-d 00:00:00'));
- $q->orWhereNull('startdate');
+ $q->where('start_date', '<=', $date->format('Y-m-d 00:00:00'));
+ $q->orWhereNull('start_date');
}
)
->where(
static function (EloquentBuilder $q) use ($date): void {
- $q->where('targetdate', '>=', $date->format('Y-m-d 00:00:00'));
- $q->orWhereNull('targetdate');
+ $q->where('target_date', '>=', $date->format('Y-m-d 00:00:00'));
+ $q->orWhereNull('target_date');
}
)
;
@@ -82,15 +82,15 @@ class PiggyBankRepetition extends Model
/**
* @param mixed $value
*/
- public function setCurrentamountAttribute($value): void
+ public function setCurrentAmountAttribute($value): void
{
- $this->attributes['currentamount'] = (string)$value;
+ $this->attributes['current_amount'] = (string)$value;
}
/**
* Get the amount
*/
- protected function currentamount(): Attribute
+ protected function currentAmount(): Attribute
{
return Attribute::make(
get: static fn ($value) => (string)$value,
diff --git a/app/Repositories/PiggyBank/ModifiesPiggyBanks.php b/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
index df3e98c10e..c5f9293c2e 100644
--- a/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
+++ b/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
@@ -59,7 +59,7 @@ trait ModifiesPiggyBanks
if (null === $repetition) {
return false;
}
- $repetition->currentamount = bcsub($repetition->currentamount, $amount);
+ $repetition->current_amount = bcsub($repetition->current_amount, $amount);
$repetition->save();
app('log')->debug('addAmount [a]: Trigger change for negative amount.');
@@ -74,8 +74,8 @@ trait ModifiesPiggyBanks
if (null === $repetition) {
return false;
}
- $currentAmount = $repetition->currentamount ?? '0';
- $repetition->currentamount = bcadd($currentAmount, $amount);
+ $currentAmount = $repetition->current_amount ?? '0';
+ $repetition->current_amount = bcadd($currentAmount, $amount);
$repetition->save();
app('log')->debug('addAmount [b]: Trigger change for positive amount.');
@@ -88,11 +88,11 @@ trait ModifiesPiggyBanks
{
$today = today(config('app.timezone'));
$leftOnAccount = $this->leftOnAccount($piggyBank, $today);
- $savedSoFar = $this->getRepetition($piggyBank)->currentamount;
+ $savedSoFar = $this->getRepetition($piggyBank)->current_amount;
$maxAmount = $leftOnAccount;
$leftToSave = null;
- if (0 !== bccomp($piggyBank->targetamount, '0')) {
- $leftToSave = bcsub($piggyBank->targetamount, $savedSoFar);
+ if (0 !== bccomp($piggyBank->target_amount, '0')) {
+ $leftToSave = bcsub($piggyBank->target_amount, $savedSoFar);
$maxAmount = 1 === bccomp($leftOnAccount, $leftToSave) ? $leftToSave : $leftOnAccount;
}
@@ -114,7 +114,7 @@ trait ModifiesPiggyBanks
if (null === $repetition) {
return false;
}
- $savedSoFar = $repetition->currentamount;
+ $savedSoFar = $repetition->current_amount;
return bccomp($amount, $savedSoFar) <= 0;
}
@@ -143,12 +143,12 @@ trait ModifiesPiggyBanks
if (null === $repetition) {
return $piggyBank;
}
- $max = $piggyBank->targetamount;
- if (1 === bccomp($amount, $max) && 0 !== bccomp($piggyBank->targetamount, '0')) {
+ $max = $piggyBank->target_amount;
+ if (1 === bccomp($amount, $max) && 0 !== bccomp($piggyBank->target_amount, '0')) {
$amount = $max;
}
- $difference = bcsub($amount, $repetition->currentamount);
- $repetition->currentamount = $amount;
+ $difference = bcsub($amount, $repetition->current_amount);
+ $repetition->current_amount = $amount;
$repetition->save();
if (-1 === bccomp($difference, '0')) {
@@ -213,7 +213,7 @@ trait ModifiesPiggyBanks
// repetition is auto created.
$repetition = $this->getRepetition($piggyBank);
if (null !== $repetition && array_key_exists('current_amount', $data) && '' !== $data['current_amount']) {
- $repetition->currentamount = $data['current_amount'];
+ $repetition->current_amount = $data['current_amount'];
$repetition->save();
}
@@ -318,13 +318,13 @@ trait ModifiesPiggyBanks
// if the piggy bank is now smaller than the current relevant rep,
// remove money from the rep.
$repetition = $this->getRepetition($piggyBank);
- if (null !== $repetition && $repetition->currentamount > $piggyBank->targetamount && 0 !== bccomp($piggyBank->targetamount, '0')) {
- $difference = bcsub($piggyBank->targetamount, $repetition->currentamount);
+ if (null !== $repetition && $repetition->current_amount > $piggyBank->target_amount && 0 !== bccomp($piggyBank->target_amount, '0')) {
+ $difference = bcsub($piggyBank->target_amount, $repetition->current_amount);
// an amount will be removed, create "negative" event:
event(new ChangedAmount($piggyBank, $difference, null, null));
- $repetition->currentamount = $piggyBank->targetamount;
+ $repetition->current_amount = $piggyBank->target_amount;
$repetition->save();
}
@@ -370,18 +370,18 @@ trait ModifiesPiggyBanks
$piggyBank->account_id = (int)$data['account_id'];
}
if (array_key_exists('targetamount', $data) && '' !== $data['targetamount']) {
- $piggyBank->targetamount = $data['targetamount'];
+ $piggyBank->target_amount = $data['targetamount'];
}
if (array_key_exists('targetamount', $data) && '' === $data['targetamount']) {
- $piggyBank->targetamount = '0';
+ $piggyBank->target_amount = '0';
}
if (array_key_exists('targetdate', $data) && '' !== $data['targetdate']) {
- $piggyBank->targetdate = $data['targetdate'];
- $piggyBank->targetdate_tz = $data['targetdate']?->format('e');
+ $piggyBank->target_date = $data['targetdate'];
+ $piggyBank->target_date_tz = $data['targetdate']?->format('e');
}
if (array_key_exists('startdate', $data)) {
- $piggyBank->startdate = $data['startdate'];
- $piggyBank->startdate_tz = $data['targetdate']?->format('e');
+ $piggyBank->start_date = $data['startdate'];
+ $piggyBank->start_date_tz = $data['targetdate']?->format('e');
}
$piggyBank->save();
diff --git a/app/Repositories/PiggyBank/PiggyBankRepository.php b/app/Repositories/PiggyBank/PiggyBankRepository.php
index 99d19353a9..b31571b043 100644
--- a/app/Repositories/PiggyBank/PiggyBankRepository.php
+++ b/app/Repositories/PiggyBank/PiggyBankRepository.php
@@ -120,7 +120,7 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
return '0';
}
- return $rep->currentamount;
+ return $rep->current_amount;
}
public function getRepetition(PiggyBank $piggyBank): ?PiggyBankRepetition
@@ -200,10 +200,10 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
}
app('log')->debug(sprintf('The currency is %s and the amount is %s', $currency->code, $amount));
- $room = bcsub($piggyBank->targetamount, $repetition->currentamount);
- $compare = bcmul($repetition->currentamount, '-1');
+ $room = bcsub($piggyBank->target_amount, $repetition->current_amount);
+ $compare = bcmul($repetition->current_amount, '-1');
- if (0 === bccomp($piggyBank->targetamount, '0')) {
+ if (0 === bccomp($piggyBank->target_amount, '0')) {
// amount is zero? then the "room" is positive amount of we wish to add or remove.
$room = app('steam')->positive($amount);
app('log')->debug(sprintf('Room is now %s', $room));
@@ -223,7 +223,7 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
// amount is negative and $currentamount is smaller than $amount
if (-1 === bccomp($amount, '0') && 1 === bccomp($compare, $amount)) {
- app('log')->debug(sprintf('Max amount to remove is %f', $repetition->currentamount));
+ app('log')->debug(sprintf('Max amount to remove is %f', $repetition->current_amount));
app('log')->debug(sprintf('Cannot remove %f from piggy bank #%d ("%s")', $amount, $piggyBank->id, $piggyBank->name));
app('log')->debug(sprintf('New amount is %f', $compare));
@@ -267,7 +267,7 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
/** @var PiggyBank $piggy */
foreach ($set as $piggy) {
- $currentAmount = $this->getRepetition($piggy)->currentamount ?? '0';
+ $currentAmount = $this->getRepetition($piggy)->current_amount ?? '0';
$piggy->name = $piggy->name.' ('.app('amount')->formatAnything($currency, $currentAmount, false).')';
}
@@ -298,11 +298,11 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
if (null === $repetition) {
return $savePerMonth;
}
- if (null !== $piggyBank->targetdate && $repetition->currentamount < $piggyBank->targetamount) {
+ if (null !== $piggyBank->target_date && $repetition->current_amount < $piggyBank->target_amount) {
$now = today(config('app.timezone'));
- $startDate = null !== $piggyBank->startdate && $piggyBank->startdate->gte($now) ? $piggyBank->startdate : $now;
- $diffInMonths = (int)$startDate->diffInMonths($piggyBank->targetdate);
- $remainingAmount = bcsub($piggyBank->targetamount, $repetition->currentamount);
+ $startDate = null !== $piggyBank->start_date && $piggyBank->start_date->gte($now) ? $piggyBank->start_date : $now;
+ $diffInMonths = (int)$startDate->diffInMonths($piggyBank->target_date);
+ $remainingAmount = bcsub($piggyBank->target_amount, $repetition->current_amount);
// more than 1 month to go and still need money to save:
if ($diffInMonths > 0 && 1 === bccomp($remainingAmount, '0')) {
@@ -332,7 +332,7 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
foreach ($piggies as $current) {
$repetition = $this->getRepetition($current);
if (null !== $repetition) {
- $balance = bcsub($balance, $repetition->currentamount);
+ $balance = bcsub($balance, $repetition->current_amount);
}
}
diff --git a/app/Support/Export/ExportDataGenerator.php b/app/Support/Export/ExportDataGenerator.php
index 2ac986eb7f..7fb74e610b 100644
--- a/app/Support/Export/ExportDataGenerator.php
+++ b/app/Support/Export/ExportDataGenerator.php
@@ -456,10 +456,10 @@ class ExportDataGenerator
$piggy->account->accountType->type,
$piggy->name,
$currency?->code,
- $piggy->targetamount,
- $repetition?->currentamount,
- $piggy->startdate?->format('Y-m-d'),
- $piggy->targetdate?->format('Y-m-d'),
+ $piggy->target_amount,
+ $repetition?->current_amount,
+ $piggy->start_date?->format('Y-m-d'),
+ $piggy->target_date?->format('Y-m-d'),
$piggy->order,
$piggy->active,
];
diff --git a/app/TransactionRules/Actions/UpdatePiggybank.php b/app/TransactionRules/Actions/UpdatePiggybank.php
index 3e90a79ad9..1e748c1926 100644
--- a/app/TransactionRules/Actions/UpdatePiggybank.php
+++ b/app/TransactionRules/Actions/UpdatePiggybank.php
@@ -178,15 +178,15 @@ class UpdatePiggybank implements ActionInterface
$repository->setUser($journal->user);
// how much can we add to the piggy bank?
- if (0 !== bccomp($piggyBank->targetamount, '0')) {
- $toAdd = bcsub($piggyBank->targetamount, $repository->getCurrentAmount($piggyBank));
+ if (0 !== bccomp($piggyBank->target_amount, '0')) {
+ $toAdd = bcsub($piggyBank->target_amount, $repository->getCurrentAmount($piggyBank));
app('log')->debug(sprintf('Max amount to add to piggy bank is %s, amount is %s', $toAdd, $amount));
// update amount to fit:
$amount = -1 === bccomp($amount, $toAdd) ? $amount : $toAdd;
app('log')->debug(sprintf('Amount is now %s', $amount));
}
- if (0 === bccomp($piggyBank->targetamount, '0')) {
+ if (0 === bccomp($piggyBank->target_amount, '0')) {
app('log')->debug('Target amount is zero, can add anything.');
}
diff --git a/app/Transformers/PiggyBankTransformer.php b/app/Transformers/PiggyBankTransformer.php
index aaccf20c63..4cc10cc466 100644
--- a/app/Transformers/PiggyBankTransformer.php
+++ b/app/Transformers/PiggyBankTransformer.php
@@ -84,18 +84,18 @@ class PiggyBankTransformer extends AbstractTransformer
// Amounts, depending on 0.0 state of target amount
$percentage = null;
- $targetAmount = $piggyBank->targetamount;
+ $targetAmount = $piggyBank->target_amount;
$leftToSave = null;
$savePerMonth = null;
if (0 !== bccomp($targetAmount, '0')) { // target amount is not 0.00
- $leftToSave = bcsub($piggyBank->targetamount, $currentAmount);
+ $leftToSave = bcsub($piggyBank->target_amount, $currentAmount);
$percentage = (int)bcmul(bcdiv($currentAmount, $targetAmount), '100');
$targetAmount = app('steam')->bcround($targetAmount, $currency->decimal_places);
$leftToSave = app('steam')->bcround($leftToSave, $currency->decimal_places);
$savePerMonth = app('steam')->bcround($this->piggyRepos->getSuggestedMonthlyAmount($piggyBank), $currency->decimal_places);
}
- $startDate = $piggyBank->startdate?->format('Y-m-d');
- $targetDate = $piggyBank->targetdate?->format('Y-m-d');
+ $startDate = $piggyBank->start_date?->format('Y-m-d');
+ $targetDate = $piggyBank->target_date?->format('Y-m-d');
return [
'id' => (string)$piggyBank->id,
diff --git a/app/Transformers/V2/PiggyBankTransformer.php b/app/Transformers/V2/PiggyBankTransformer.php
index b1d3abada7..30ebe367a7 100644
--- a/app/Transformers/V2/PiggyBankTransformer.php
+++ b/app/Transformers/V2/PiggyBankTransformer.php
@@ -119,7 +119,7 @@ class PiggyBankTransformer extends AbstractTransformer
/** @var PiggyBankRepetition $repetition */
foreach ($repetitions as $repetition) {
$this->repetitions[$repetition->piggy_bank_id] = [
- 'amount' => $repetition->currentamount,
+ 'amount' => $repetition->current_amount,
];
}
@@ -178,14 +178,14 @@ class PiggyBankTransformer extends AbstractTransformer
$nativeLeftToSave = null;
$savePerMonth = null;
$nativeSavePerMonth = null;
- $startDate = $piggyBank->startdate?->format('Y-m-d');
- $targetDate = $piggyBank->targetdate?->format('Y-m-d');
+ $startDate = $piggyBank->start_date?->format('Y-m-d');
+ $targetDate = $piggyBank->target_date?->format('Y-m-d');
$accountId = $piggyBank->account_id;
$accountName = $this->accounts[$accountId]['name'] ?? null;
$currency = $this->currencies[$accountId] ?? $this->default;
$currentAmount = app('steam')->bcround($this->repetitions[$piggyBank->id]['amount'] ?? '0', $currency->decimal_places);
$nativeCurrentAmount = $this->converter->convert($this->default, $currency, today(), $currentAmount);
- $targetAmount = $piggyBank->targetamount;
+ $targetAmount = $piggyBank->target_amount;
$nativeTargetAmount = $this->converter->convert($this->default, $currency, today(), $targetAmount);
$note = $this->notes[$piggyBank->id] ?? null;
$group = $this->groups[$piggyBank->id] ?? null;
@@ -194,7 +194,7 @@ class PiggyBankTransformer extends AbstractTransformer
$leftToSave = bcsub($targetAmount, $currentAmount);
$nativeLeftToSave = $this->converter->convert($this->default, $currency, today(), $leftToSave);
$percentage = (int)bcmul(bcdiv($currentAmount, $targetAmount), '100');
- $savePerMonth = $this->getSuggestedMonthlyAmount($currentAmount, $targetAmount, $piggyBank->startdate, $piggyBank->targetdate);
+ $savePerMonth = $this->getSuggestedMonthlyAmount($currentAmount, $targetAmount, $piggyBank->start_date, $piggyBank->target_date);
$nativeSavePerMonth = $this->converter->convert($this->default, $currency, today(), $savePerMonth);
}
$this->converter->summarize();
From f2fab5d4eef9040f0145f5a330f3576e1be8eb11 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 1 Dec 2024 06:48:15 +0100
Subject: [PATCH 007/167] Update code for piggy banks.
---
.../Commands/Correction/CorrectAmounts.php | 4 +-
.../Commands/System/ForceDecimalSize.php | 4 +-
.../Upgrade/UpgradeMultiPiggyBanks.php | 118 ++++++++++++++++++
.../Commands/Upgrade/UpgradeSkeleton.php.stub | 1 -
app/Handlers/Observer/PiggyBankObserver.php | 19 +--
5 files changed, 132 insertions(+), 14 deletions(-)
create mode 100644 app/Console/Commands/Upgrade/UpgradeMultiPiggyBanks.php
diff --git a/app/Console/Commands/Correction/CorrectAmounts.php b/app/Console/Commands/Correction/CorrectAmounts.php
index 639c96edec..10e65e07be 100644
--- a/app/Console/Commands/Correction/CorrectAmounts.php
+++ b/app/Console/Commands/Correction/CorrectAmounts.php
@@ -163,7 +163,7 @@ class CorrectAmounts extends Command
private function fixRepetitions(): void
{
- $set = PiggyBankRepetition::where('currentamount', '<', 0)->get();
+ $set = PiggyBankRepetition::where('current_amount', '<', 0)->get();
$count = $set->count();
if (0 === $count) {
$this->friendlyPositive('All piggy bank repetition amounts are positive.');
@@ -181,7 +181,7 @@ class CorrectAmounts extends Command
private function fixPiggyBanks(): void
{
- $set = PiggyBank::where('targetamount', '<', 0)->get();
+ $set = PiggyBank::where('target_amount', '<', 0)->get();
$count = $set->count();
if (0 === $count) {
$this->friendlyPositive('All piggy bank amounts are positive.');
diff --git a/app/Console/Commands/System/ForceDecimalSize.php b/app/Console/Commands/System/ForceDecimalSize.php
index 426e7fbcbd..9f3c42a12c 100644
--- a/app/Console/Commands/System/ForceDecimalSize.php
+++ b/app/Console/Commands/System/ForceDecimalSize.php
@@ -83,8 +83,8 @@ class ForceDecimalSize extends Command
'currency_exchange_rates' => ['rate', 'user_rate'],
'limit_repetitions' => ['amount'],
'piggy_bank_events' => ['amount'],
- 'piggy_bank_repetitions' => ['currentamount'],
- 'piggy_banks' => ['targetamount'],
+ 'piggy_bank_repetitions' => ['current_amount'],
+ 'piggy_banks' => ['target_amount'],
'recurrences_transactions' => ['amount', 'foreign_amount'],
'transactions' => ['amount', 'foreign_amount'],
];
diff --git a/app/Console/Commands/Upgrade/UpgradeMultiPiggyBanks.php b/app/Console/Commands/Upgrade/UpgradeMultiPiggyBanks.php
new file mode 100644
index 0000000000..f987a0b3d5
--- /dev/null
+++ b/app/Console/Commands/Upgrade/UpgradeMultiPiggyBanks.php
@@ -0,0 +1,118 @@
+isExecuted() && true !== $this->option('force')) {
+ $this->friendlyInfo('This command has already been executed.');
+
+ return 0;
+ }
+ $this->upgradePiggyBanks();
+ $this->friendlyInfo('Upgraded all piggy banks.');
+
+ $this->markAsExecuted();
+
+ return 0;
+ }
+
+ /**
+ * @return bool
+ */
+ private function isExecuted(): bool
+ {
+ $configVar = app('fireflyconfig')->get(self::CONFIG_NAME, false);
+ if (null !== $configVar) {
+ return (bool) $configVar->data;
+ }
+
+ return false;
+ }
+
+
+ /**
+ *
+ */
+ private function markAsExecuted(): void
+ {
+ app('fireflyconfig')->set(self::CONFIG_NAME, true);
+ }
+
+ private function upgradePiggyBanks(): void
+ {
+ $this->repository = app(PiggyBankRepositoryInterface::class);
+ $this->accountRepository = app(AccountRepositoryInterface::class);
+ $set = PiggyBank::whereNotNull('account_id')->get();
+ Log::debug(sprintf('Will update %d piggy banks(s).', $set->count()));
+ /** @var PiggyBank $piggyBank */
+ foreach ($set as $piggyBank) {
+ $this->upgradePiggyBank($piggyBank);
+ }
+ }
+
+ private function upgradePiggyBank(PiggyBank $piggyBank): void
+ {
+ $this->repository->setUser($piggyBank->account->user);
+ $this->accountRepository->setUser($piggyBank->account->user);
+ $repetition = $this->repository->getRepetition($piggyBank);
+ $currency = $this->accountRepository->getAccountCurrency($piggyBank->account) ?? app('amount')->getDefaultCurrencyByUserGroup($piggyBank->account->user->userGroup);
+
+ // update piggy bank to have a currency.
+ $piggyBank->transaction_currency_id = $currency->id;
+ $piggyBank->save();
+
+ // store current amount in account association.
+ $piggyBank->accounts()->sync([$piggyBank->account->id => ['current_amount' => $repetition->current_amount]]);
+ $piggyBank->account_id = null;
+ $piggyBank->save();
+
+ // remove all repetitions (no longer used)
+ $piggyBank->piggyBankRepetitions()->delete();
+
+ }
+}
diff --git a/app/Console/Commands/Upgrade/UpgradeSkeleton.php.stub b/app/Console/Commands/Upgrade/UpgradeSkeleton.php.stub
index d2f5b627c0..5d2dba01f5 100644
--- a/app/Console/Commands/Upgrade/UpgradeSkeleton.php.stub
+++ b/app/Console/Commands/Upgrade/UpgradeSkeleton.php.stub
@@ -6,7 +6,6 @@ use Illuminate\Console\Command;
/**
* Class UpgradeSkeleton.
- * TODO DONT FORGET TO ADD THIS TO THE DOCKER BUILD
*/
class UpgradeSkeleton extends Command
{
diff --git a/app/Handlers/Observer/PiggyBankObserver.php b/app/Handlers/Observer/PiggyBankObserver.php
index 40bde63a1a..74eb37b211 100644
--- a/app/Handlers/Observer/PiggyBankObserver.php
+++ b/app/Handlers/Observer/PiggyBankObserver.php
@@ -34,15 +34,16 @@ class PiggyBankObserver
{
public function created(PiggyBank $piggyBank): void
{
- app('log')->debug('Observe "created" of a piggy bank.');
- $repetition = new PiggyBankRepetition();
- $repetition->piggyBank()->associate($piggyBank);
- $repetition->start_date = $piggyBank->start_date;
- $repetition->start_date_tz = $piggyBank->start_date->format('e');
- $repetition->target_date = $piggyBank->target_date;
- $repetition->target_date_tz = $piggyBank->target_date?->format('e');
- $repetition->current_amount = '0';
- $repetition->save();
+ app('log')->debug('Observe "created" of a piggy bank. DO NOTHING.');
+
+// $repetition = new PiggyBankRepetition();
+// $repetition->piggyBank()->associate($piggyBank);
+// $repetition->start_date = $piggyBank->start_date;
+// $repetition->start_date_tz = $piggyBank->start_date->format('e');
+// $repetition->target_date = $piggyBank->target_date;
+// $repetition->target_date_tz = $piggyBank->target_date?->format('e');
+// $repetition->current_amount = '0';
+// $repetition->save();
}
/**
From cdf1ebf3f709d29ddc9319ca74eebe1039a21d26 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 1 Dec 2024 18:16:48 +0100
Subject: [PATCH 008/167] Better ability to store piggy banks.
---
.../Autocomplete/PiggyBankController.php | 6 +-
.../V1/Controllers/Data/PurgeController.php | 20 +--
.../Models/Account/ListController.php | 2 +-
.../Models/PiggyBank/ListController.php | 33 +++++
.../Models/PiggyBank/StoreRequest.php | 96 ++++++++++---
app/Factory/PiggyBankFactory.php | 129 ++++++++++++++++++
.../Controllers/PiggyBank/IndexController.php | 2 +-
app/Models/PiggyBank.php | 8 +-
.../Currency/CurrencyRepository.php | 5 +
.../Currency/CurrencyRepositoryInterface.php | 2 +
.../PiggyBank/ModifiesPiggyBanks.php | 87 ++----------
.../PiggyBank/PiggyBankRepository.php | 9 +-
.../PiggyBankRepositoryInterface.php | 17 ++-
app/Validation/FireflyValidator.php | 11 +-
config/firefly.php | 3 +
resources/lang/en_US/validation.php | 1 +
routes/api.php | 1 +
17 files changed, 297 insertions(+), 135 deletions(-)
diff --git a/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php b/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php
index cf29aa037a..5a757dd35f 100644
--- a/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php
+++ b/app/Api/V1/Controllers/Autocomplete/PiggyBankController.php
@@ -68,12 +68,11 @@ class PiggyBankController extends Controller
{
$data = $request->getData();
$piggies = $this->piggyRepository->searchPiggyBank($data['query'], $this->parameters->get('limit'));
- $defaultCurrency = app('amount')->getDefaultCurrency();
$response = [];
/** @var PiggyBank $piggy */
foreach ($piggies as $piggy) {
- $currency = $this->accountRepository->getAccountCurrency($piggy->account) ?? $defaultCurrency;
+ $currency = $piggy->transactionCurrency;
$objectGroup = $piggy->objectGroups()->first();
$response[] = [
'id' => (string)$piggy->id,
@@ -99,12 +98,11 @@ class PiggyBankController extends Controller
{
$data = $request->getData();
$piggies = $this->piggyRepository->searchPiggyBank($data['query'], $this->parameters->get('limit'));
- $defaultCurrency = app('amount')->getDefaultCurrency();
$response = [];
/** @var PiggyBank $piggy */
foreach ($piggies as $piggy) {
- $currency = $this->accountRepository->getAccountCurrency($piggy->account) ?? $defaultCurrency;
+ $currency = $piggy->transactionCurrency;
$currentAmount = $this->piggyRepository->getRepetition($piggy)->current_amount ?? '0';
$objectGroup = $piggy->objectGroups()->first();
$response[] = [
diff --git a/app/Api/V1/Controllers/Data/PurgeController.php b/app/Api/V1/Controllers/Data/PurgeController.php
index 8d076b62cf..d80b60315b 100644
--- a/app/Api/V1/Controllers/Data/PurgeController.php
+++ b/app/Api/V1/Controllers/Data/PurgeController.php
@@ -36,6 +36,7 @@ use FireflyIII\Models\RuleGroup;
use FireflyIII\Models\Tag;
use FireflyIII\Models\TransactionGroup;
use FireflyIII\Models\TransactionJournal;
+use FireflyIII\Repositories\PiggyBank\PiggyBankRepositoryInterface;
use FireflyIII\User;
use Illuminate\Http\JsonResponse;
@@ -63,14 +64,17 @@ class PurgeController extends Controller
Bill::whereUserId($user->id)->onlyTrashed()->forceDelete();
// piggies
- $set = PiggyBank::leftJoin('accounts', 'accounts.id', 'piggy_banks.account_id')
- ->where('accounts.user_id', $user->id)->onlyTrashed()->get(['piggy_banks.*'])
- ;
-
- /** @var PiggyBank $piggy */
- foreach ($set as $piggy) {
- $piggy->forceDelete();
- }
+ $repository = app(PiggyBankRepositoryInterface::class);
+ $repository->setUser($user);
+ $repository->purgeAll();
+// $set = PiggyBank::leftJoin('accounts', 'accounts.id', 'piggy_banks.account_id')
+// ->where('accounts.user_id', $user->id)->onlyTrashed()->get(['piggy_banks.*'])
+// ;
+//
+// /** @var PiggyBank $piggy */
+// foreach ($set as $piggy) {
+// $piggy->forceDelete();
+// }
// rule group
RuleGroup::whereUserId($user->id)->onlyTrashed()->forceDelete();
diff --git a/app/Api/V1/Controllers/Models/Account/ListController.php b/app/Api/V1/Controllers/Models/Account/ListController.php
index c85456f901..b2d4e39d90 100644
--- a/app/Api/V1/Controllers/Models/Account/ListController.php
+++ b/app/Api/V1/Controllers/Models/Account/ListController.php
@@ -111,7 +111,7 @@ class ListController extends Controller
// types to get, page size:
$pageSize = $this->parameters->get('limit');
- // get list of budgets. Count it and split it.
+ // get list of piggy banks. Count it and split it.
$collection = $this->repository->getPiggyBanks($account);
$count = $collection->count();
$piggyBanks = $collection->slice(($this->parameters->get('page') - 1) * $pageSize, $pageSize);
diff --git a/app/Api/V1/Controllers/Models/PiggyBank/ListController.php b/app/Api/V1/Controllers/Models/PiggyBank/ListController.php
index 3c3ac1672b..8fda63be8e 100644
--- a/app/Api/V1/Controllers/Models/PiggyBank/ListController.php
+++ b/app/Api/V1/Controllers/Models/PiggyBank/ListController.php
@@ -28,6 +28,7 @@ use FireflyIII\Api\V1\Controllers\Controller;
use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Models\PiggyBank;
use FireflyIII\Repositories\PiggyBank\PiggyBankRepositoryInterface;
+use FireflyIII\Transformers\AccountTransformer;
use FireflyIII\Transformers\AttachmentTransformer;
use FireflyIII\Transformers\PiggyBankEventTransformer;
use Illuminate\Http\JsonResponse;
@@ -118,4 +119,36 @@ class ListController extends Controller
return response()->json($manager->createData($resource)->toArray())->header('Content-Type', self::CONTENT_TYPE);
}
+
+ /**
+ * This endpoint is documented at:
+ * https://api-docs.firefly-iii.org/?urls.primaryName=2.0.0%20(v1)#/piggy_banks/listAccountByPiggyBank
+ *
+ * List single resource.
+ *
+ * @throws FireflyException
+ */
+ public function accounts(PiggyBank $piggyBank): JsonResponse
+ {
+ // types to get, page size:
+ $pageSize = $this->parameters->get('limit');
+ $manager = $this->getManager();
+
+ $collection = $piggyBank->accounts;
+ $count = $collection->count();
+ $events = $collection->slice(($this->parameters->get('page') - 1) * $pageSize, $pageSize);
+
+ // make paginator:
+ $paginator = new LengthAwarePaginator($events, $count, $pageSize, $this->parameters->get('page'));
+ $paginator->setPath(route('api.v1.piggy-banks.accounts', [$piggyBank->id]).$this->buildParams());
+
+ /** @var AccountTransformer $transformer */
+ $transformer = app(AccountTransformer::class);
+ $transformer->setParameters($this->parameters);
+
+ $resource = new FractalCollection($events, $transformer, 'accounts');
+ $resource->setPaginator(new IlluminatePaginatorAdapter($paginator));
+
+ return response()->json($manager->createData($resource)->toArray())->header('Content-Type', self::CONTENT_TYPE);
+ }
}
diff --git a/app/Api/V1/Requests/Models/PiggyBank/StoreRequest.php b/app/Api/V1/Requests/Models/PiggyBank/StoreRequest.php
index 8adc656a65..d73abc7b8c 100644
--- a/app/Api/V1/Requests/Models/PiggyBank/StoreRequest.php
+++ b/app/Api/V1/Requests/Models/PiggyBank/StoreRequest.php
@@ -24,10 +24,13 @@ declare(strict_types=1);
namespace FireflyIII\Api\V1\Requests\Models\PiggyBank;
+use FireflyIII\Repositories\Account\AccountRepositoryInterface;
use FireflyIII\Rules\IsValidPositiveAmount;
use FireflyIII\Support\Request\ChecksLogin;
use FireflyIII\Support\Request\ConvertsDataTypes;
use Illuminate\Foundation\Http\FormRequest;
+use Illuminate\Support\Facades\Log;
+use Illuminate\Validation\Validator;
/**
* Class StoreRequest
@@ -42,19 +45,20 @@ class StoreRequest extends FormRequest
*/
public function getAll(): array
{
- $fields = [
+ $fields = [
'order' => ['order', 'convertInteger'],
];
- $data = $this->getAllData($fields);
- $data['name'] = $this->convertString('name');
- $data['account_id'] = $this->convertInteger('account_id');
- $data['targetamount'] = $this->convertString('target_amount');
- $data['current_amount'] = $this->convertString('current_amount');
- $data['startdate'] = $this->getCarbonDate('start_date');
- $data['targetdate'] = $this->getCarbonDate('target_date');
- $data['notes'] = $this->stringWithNewlines('notes');
- $data['object_group_id'] = $this->convertInteger('object_group_id');
- $data['object_group_title'] = $this->convertString('object_group_title');
+ $data = $this->getAllData($fields);
+ $data['name'] = $this->convertString('name');
+ $data['accounts'] = $this->parseAccounts($this->get('accounts'));
+ $data['target_amount'] = $this->convertString('target_amount');
+ $data['start_date'] = $this->getCarbonDate('start_date');
+ $data['target_date'] = $this->getCarbonDate('target_date');
+ $data['notes'] = $this->stringWithNewlines('notes');
+ $data['object_group_id'] = $this->convertInteger('object_group_id');
+ $data['transaction_currency_id'] = $this->convertInteger('transaction_currency_id');
+ $data['transaction_currency_code'] = $this->convertString('transaction_currency_code');
+ $data['object_group_title'] = $this->convertString('object_group_title');
return $data;
}
@@ -65,15 +69,67 @@ class StoreRequest extends FormRequest
public function rules(): array
{
return [
- 'name' => 'required|min:1|max:255|uniquePiggyBankForUser',
- 'current_amount' => ['nullable', new IsValidPositiveAmount()],
- 'account_id' => 'required|numeric|belongsToUser:accounts,id',
- 'object_group_id' => 'numeric|belongsToUser:object_groups,id',
- 'object_group_title' => ['min:1', 'max:255'],
- 'target_amount' => ['required', new IsValidPositiveAmount()],
- 'start_date' => 'date|nullable',
- 'target_date' => 'date|nullable|after:start_date',
- 'notes' => 'max:65000',
+ 'name' => 'required|min:1|max:255|uniquePiggyBankForUser',
+ 'accounts' => 'required',
+ 'accounts.*' => 'array|required',
+ 'accounts.*.account_id' => 'required|numeric|belongsToUser:accounts,id',
+ 'accounts.*.current_amount' => ['numeric', new IsValidPositiveAmount()],
+ 'object_group_id' => 'numeric|belongsToUser:object_groups,id',
+ 'object_group_title' => ['min:1', 'max:255'],
+ 'target_amount' => ['required', new IsValidPositiveAmount()],
+ 'start_date' => 'date|nullable',
+ 'transaction_currency_id' => 'exists:transaction_currencies,id',
+ 'transaction_currency_code' => 'exists:transaction_currencies,code',
+ 'target_date' => 'date|nullable|after:start_date',
+ 'notes' => 'max:65000',
];
}
+
+ /**
+ * Can only store money on liabilities and asset accouns.
+ */
+ public function withValidator(Validator $validator): void
+ {
+ $validator->after(
+ function (Validator $validator): void {
+ // validate start before end only if both are there.
+ $data = $validator->getData();
+ if (array_key_exists('accounts', $data) && is_array($data['accounts'])) {
+ $repository = app(AccountRepositoryInterface::class);
+ $types = config('firefly.piggy_bank_account_types');
+ foreach ($data['accounts'] as $index => $array) {
+ $accountId = (int) ($array['account_id'] ?? 0);
+ $account = $repository->find($accountId);
+ if (null !== $account) {
+ $type = $account->accountType->type;
+ if (!in_array($type, $types, true)) {
+ $validator->errors()->add(sprintf('accounts.%d', $index), trans('validation.invalid_account_type'));
+ }
+ }
+ }
+ }
+ }
+ );
+ if ($validator->fails()) {
+ Log::channel('audit')->error(sprintf('Validation errors in %s', __CLASS__), $validator->errors()->toArray());
+ }
+ }
+
+ private function parseAccounts(mixed $array): array
+ {
+ if (!is_array($array)) {
+ return [];
+ }
+ $return = [];
+ foreach ($array as $entry) {
+ if (!is_array($entry)) {
+ continue;
+ }
+ $return[] = [
+ 'account_id' => $this->integerFromValue((string)($entry['account_id'] ?? '0')),
+ 'current_amount' => $this->clearString($entry['current_amount'] ?? '0'),
+ ];
+ }
+ return $return;
+ }
}
diff --git a/app/Factory/PiggyBankFactory.php b/app/Factory/PiggyBankFactory.php
index 505c92d0da..df9b54bc46 100644
--- a/app/Factory/PiggyBankFactory.php
+++ b/app/Factory/PiggyBankFactory.php
@@ -23,8 +23,14 @@ declare(strict_types=1);
namespace FireflyIII\Factory;
+use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Models\PiggyBank;
+use FireflyIII\Models\TransactionCurrency;
+use FireflyIII\Repositories\Account\AccountRepositoryInterface;
+use FireflyIII\Repositories\Currency\CurrencyRepositoryInterface;
+use FireflyIII\Repositories\PiggyBank\PiggyBankRepositoryInterface;
use FireflyIII\User;
+use Illuminate\Database\QueryException;
/**
* Class PiggyBankFactory
@@ -32,6 +38,72 @@ use FireflyIII\User;
class PiggyBankFactory
{
private User $user;
+ private CurrencyRepositoryInterface $currencyRepository;
+ private AccountRepositoryInterface $accountRepository;
+ private PiggyBankRepositoryInterface $piggyBankRepository;
+
+ /**
+ * Store a piggy bank or come back with an exception.
+ *
+ * @param array $data
+ *
+ * @return PiggyBank
+ */
+ public function store(array $data): PiggyBank {
+ $this->currencyRepository = app(CurrencyRepositoryInterface::class);
+ $this->accountRepository = app(AccountRepositoryInterface::class);
+ $this->piggyBankRepository = app(PiggyBankRepositoryInterface::class);
+ $this->currencyRepository->setUser($this->user);
+ $this->accountRepository->setUser($this->user);
+ $this->piggyBankRepository->setUser($this->user);
+ $piggyBankData =$data;
+
+ // unset some fields
+ unset($piggyBankData['object_group_title'],$piggyBankData['transaction_currency_code'],$piggyBankData['transaction_currency_id'],$piggyBankData['accounts'], $piggyBankData['object_group_id'], $piggyBankData['notes']);
+
+ // validate amount:
+ if (array_key_exists('target_amount', $piggyBankData) && '' === (string)$piggyBankData['target_amount']) {
+ $piggyBankData['target_amount'] = '0';
+ }
+
+ $piggyBankData['start_date_tz'] = $piggyBankData['start_date']?->format('e');
+ $piggyBankData['target_date_tz'] = $piggyBankData['target_date']?->format('e');
+ $piggyBankData['account_id'] = null;
+ $piggyBankData['transaction_currency_id'] = $this->getCurrency($data)->id;
+ $piggyBankData['order'] = 131337;
+
+ try {
+ /** @var PiggyBank $piggyBank */
+ $piggyBank = PiggyBank::create($piggyBankData);
+ } catch (QueryException $e) {
+ app('log')->error(sprintf('Could not store piggy bank: %s', $e->getMessage()), $piggyBankData);
+
+ throw new FireflyException('400005: Could not store new piggy bank.', 0, $e);
+ }
+ $piggyBank = $this->setOrder($piggyBank, $data);
+ $this->linkToAccountIds($piggyBank, $data['accounts']);
+ $this->piggyBankRepository->updateNote($piggyBank, $data['notes']);
+
+ $objectGroupTitle = $data['object_group_title'] ?? '';
+ if ('' !== $objectGroupTitle) {
+ $objectGroup = $this->findOrCreateObjectGroup($objectGroupTitle);
+ if (null !== $objectGroup) {
+ $piggyBank->objectGroups()->sync([$objectGroup->id]);
+ $piggyBank->save();
+ }
+ }
+ // try also with ID
+ $objectGroupId = (int)($data['object_group_id'] ?? 0);
+ if (0 !== $objectGroupId) {
+ $objectGroup = $this->findObjectGroupById($objectGroupId);
+ if (null !== $objectGroup) {
+ $piggyBank->objectGroups()->sync([$objectGroup->id]);
+ $piggyBank->save();
+ }
+ }
+
+ return $piggyBank;
+ }
public function find(?int $piggyBankId, ?string $piggyBankName): ?PiggyBank
{
@@ -70,4 +142,61 @@ class PiggyBankFactory
{
$this->user = $user;
}
+
+ private function getCurrency(array $data): TransactionCurrency {
+ // currency:
+ $defaultCurrency = app('amount')->getDefaultCurrency();
+ $currency = null;
+ if (array_key_exists('transaction_currency_code', $data)) {
+ $currency = $this->currencyRepository->findByCode((string)($data['transaction_currency_code'] ?? ''));
+ }
+ if (array_key_exists('transaction_currency_id', $data)) {
+ $currency = $this->currencyRepository->find((int)($data['transaction_currency_id'] ?? 0));
+ }
+ $currency ??= $defaultCurrency;
+ return $currency;
+ }
+
+ private function setOrder(PiggyBank $piggyBank, array $data): PiggyBank {
+ $this->resetOrder();
+ $order = $this->getMaxOrder() + 1;
+ if (array_key_exists('order', $data)) {
+ $order = $data['order'];
+ }
+ $piggyBank->order = $order;
+ $piggyBank->save();
+ return $piggyBank;
+
+ }
+
+ private function resetOrder(): void
+ {
+ $set = $this->user->piggyBanks()->orderBy('piggy_banks.order', 'ASC')->get(['piggy_banks.*']);
+ $current = 1;
+ foreach ($set as $piggyBank) {
+ if ($piggyBank->order !== $current) {
+ app('log')->debug(sprintf('Piggy bank #%d ("%s") was at place %d but should be on %d', $piggyBank->id, $piggyBank->name, $piggyBank->order, $current));
+ $piggyBank->order = $current;
+ $piggyBank->save();
+ }
+ ++$current;
+ }
+ }
+
+
+ private function getMaxOrder(): int
+ {
+ return (int)$this->user->piggyBanks()->max('piggy_banks.order');
+ }
+
+ private function linkToAccountIds(PiggyBank $piggyBank, array $accounts): void {
+ /** @var array $info */
+ foreach($accounts as $info) {
+ $account = $this->accountRepository->find((int)($info['account_id'] ?? 0));
+ if(null === $account) {
+ continue;
+ }
+ $piggyBank->accounts()->syncWithoutDetaching([$account->id, ['current_amount' => $info['current_amount'] ?? '0']]);
+ }
+ }
}
diff --git a/app/Http/Controllers/PiggyBank/IndexController.php b/app/Http/Controllers/PiggyBank/IndexController.php
index 9c3578550e..9c08ebdf25 100644
--- a/app/Http/Controllers/PiggyBank/IndexController.php
+++ b/app/Http/Controllers/PiggyBank/IndexController.php
@@ -79,7 +79,7 @@ class IndexController extends Controller
public function index()
{
$this->cleanupObjectGroups();
- $this->piggyRepos->resetOrder();
+ //$this->piggyRepos->resetOrder();
$collection = $this->piggyRepos->getPiggyBanks();
$accounts = [];
diff --git a/app/Models/PiggyBank.php b/app/Models/PiggyBank.php
index 0edfa05b9e..911566e628 100644
--- a/app/Models/PiggyBank.php
+++ b/app/Models/PiggyBank.php
@@ -55,7 +55,7 @@ class PiggyBank extends Model
'target_amount' => 'string',
];
- protected $fillable = ['name', 'account_id', 'order', 'target_amount', 'start_date', 'start_date_tz', 'target_date', 'target_date_tz', 'active'];
+ protected $fillable = ['name', 'account_id', 'order', 'target_amount', 'start_date', 'start_date_tz', 'target_date', 'target_date_tz', 'active','transaction_currency_id'];
/**
* Route binder. Converts the key in the URL to the specified object (or throw 404).
@@ -67,9 +67,9 @@ class PiggyBank extends Model
if (auth()->check()) {
$piggyBankId = (int)$value;
$piggyBank = self::where('piggy_banks.id', $piggyBankId)
- ->leftJoin('accounts', 'accounts.id', '=', 'piggy_banks.account_id')
- ->where('accounts.user_id', auth()->user()->id)->first(['piggy_banks.*'])
- ;
+ ->leftJoin('account_piggy_bank','account_piggy_bank.piggy_bank_id', '=', 'piggy_banks.id')
+ ->leftJoin('accounts', 'accounts.id', '=', 'account_piggy_bank.account_id')
+ ->where('accounts.user_id', auth()->user()->id)->first(['piggy_banks.*']);
if (null !== $piggyBank) {
return $piggyBank;
}
diff --git a/app/Repositories/Currency/CurrencyRepository.php b/app/Repositories/Currency/CurrencyRepository.php
index 5ca4924769..97cb7ba79f 100644
--- a/app/Repositories/Currency/CurrencyRepository.php
+++ b/app/Repositories/Currency/CurrencyRepository.php
@@ -105,4 +105,9 @@ class CurrencyRepository implements CurrencyRepositoryInterface
$this->user = $user;
}
}
+
+ #[\Override] public function find(int $currencyId): ?TransactionCurrency
+ {
+ return TransactionCurrency::find($currencyId);
+ }
}
diff --git a/app/Repositories/Currency/CurrencyRepositoryInterface.php b/app/Repositories/Currency/CurrencyRepositoryInterface.php
index e714977abb..b5fb7d7acb 100644
--- a/app/Repositories/Currency/CurrencyRepositoryInterface.php
+++ b/app/Repositories/Currency/CurrencyRepositoryInterface.php
@@ -42,6 +42,8 @@ interface CurrencyRepositoryInterface
*/
public function findByCode(string $currencyCode): ?TransactionCurrency;
+ public function find(int $currencyId): ?TransactionCurrency;
+
/**
* Returns the complete set of transactions but needs
* no user object.
diff --git a/app/Repositories/PiggyBank/ModifiesPiggyBanks.php b/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
index c5f9293c2e..998fed9b23 100644
--- a/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
+++ b/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
@@ -26,11 +26,14 @@ namespace FireflyIII\Repositories\PiggyBank;
use FireflyIII\Events\Model\PiggyBank\ChangedAmount;
use FireflyIII\Exceptions\FireflyException;
+use FireflyIII\Factory\PiggyBankFactory;
use FireflyIII\Models\Note;
use FireflyIII\Models\PiggyBank;
use FireflyIII\Models\PiggyBankRepetition;
+use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Models\TransactionJournal;
use FireflyIII\Repositories\ObjectGroup\CreatesObjectGroups;
+use FireflyIII\Support\Facades\Amount;
use Illuminate\Database\QueryException;
/**
@@ -178,82 +181,11 @@ trait ModifiesPiggyBanks
*/
public function store(array $data): PiggyBank
{
- $order = $this->getMaxOrder() + 1;
- if (array_key_exists('order', $data)) {
- $order = $data['order'];
- }
- $data['order'] = 31337; // very high when creating.
- $piggyData = $data;
- // unset fields just in case.
- unset($piggyData['object_group_title'], $piggyData['object_group_id'], $piggyData['notes'], $piggyData['current_amount']);
-
- // validate amount:
- if (array_key_exists('targetamount', $piggyData) && '' === (string)$piggyData['targetamount']) {
- $piggyData['targetamount'] = '0';
- }
-
- $piggyData['startdate_tz'] = $piggyData['startdate']?->format('e');
- $piggyData['targetdate_tz'] = $piggyData['targetdate']?->format('e');
-
- try {
- /** @var PiggyBank $piggyBank */
- $piggyBank = PiggyBank::create($piggyData);
- } catch (QueryException $e) {
- app('log')->error(sprintf('Could not store piggy bank: %s', $e->getMessage()), $piggyData);
-
- throw new FireflyException('400005: Could not store new piggy bank.', 0, $e);
- }
-
- // reset order then set order:
- $this->resetOrder();
- $this->setOrder($piggyBank, $order);
-
- $this->updateNote($piggyBank, $data['notes']);
-
- // repetition is auto created.
- $repetition = $this->getRepetition($piggyBank);
- if (null !== $repetition && array_key_exists('current_amount', $data) && '' !== $data['current_amount']) {
- $repetition->current_amount = $data['current_amount'];
- $repetition->save();
- }
-
- $objectGroupTitle = $data['object_group_title'] ?? '';
- if ('' !== $objectGroupTitle) {
- $objectGroup = $this->findOrCreateObjectGroup($objectGroupTitle);
- if (null !== $objectGroup) {
- $piggyBank->objectGroups()->sync([$objectGroup->id]);
- $piggyBank->save();
- }
- }
- // try also with ID
- $objectGroupId = (int)($data['object_group_id'] ?? 0);
- if (0 !== $objectGroupId) {
- $objectGroup = $this->findObjectGroupById($objectGroupId);
- if (null !== $objectGroup) {
- $piggyBank->objectGroups()->sync([$objectGroup->id]);
- $piggyBank->save();
- }
- }
-
- return $piggyBank;
+ $factory = new PiggyBankFactory();
+ $factory->setUser($this->user);
+ return $factory->store($data);
}
- /**
- * Correct order of piggies in case of issues.
- */
- public function resetOrder(): void
- {
- $set = $this->user->piggyBanks()->orderBy('piggy_banks.order', 'ASC')->get(['piggy_banks.*']);
- $current = 1;
- foreach ($set as $piggyBank) {
- if ($piggyBank->order !== $current) {
- app('log')->debug(sprintf('Piggy bank #%d ("%s") was at place %d but should be on %d', $piggyBank->id, $piggyBank->name, $piggyBank->order, $current));
- $piggyBank->order = $current;
- $piggyBank->save();
- }
- ++$current;
- }
- }
public function setOrder(PiggyBank $piggyBank, int $newOrder): bool
{
@@ -282,13 +214,12 @@ trait ModifiesPiggyBanks
return true;
}
- private function updateNote(PiggyBank $piggyBank, string $note): bool
+ public function updateNote(PiggyBank $piggyBank, string $note): void
{
if ('' === $note) {
$dbNote = $piggyBank->notes()->first();
$dbNote?->delete();
-
- return true;
+ return ;
}
$dbNote = $piggyBank->notes()->first();
if (null === $dbNote) {
@@ -297,8 +228,6 @@ trait ModifiesPiggyBanks
}
$dbNote->text = trim($note);
$dbNote->save();
-
- return true;
}
public function update(PiggyBank $piggyBank, array $data): PiggyBank
diff --git a/app/Repositories/PiggyBank/PiggyBankRepository.php b/app/Repositories/PiggyBank/PiggyBankRepository.php
index b31571b043..1e9658d290 100644
--- a/app/Repositories/PiggyBank/PiggyBankRepository.php
+++ b/app/Repositories/PiggyBank/PiggyBankRepository.php
@@ -240,10 +240,6 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
}
}
- public function getMaxOrder(): int
- {
- return (int)$this->user->piggyBanks()->max('piggy_banks.order');
- }
/**
* Return note for piggy bank.
@@ -351,4 +347,9 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
return $search->take($limit)->get();
}
+
+ #[\Override] public function purgeAll(): void
+ {
+ throw new FireflyException('TODO Not implemented');
+ }
}
diff --git a/app/Repositories/PiggyBank/PiggyBankRepositoryInterface.php b/app/Repositories/PiggyBank/PiggyBankRepositoryInterface.php
index 7c1e12becc..dfe534f4cf 100644
--- a/app/Repositories/PiggyBank/PiggyBankRepositoryInterface.php
+++ b/app/Repositories/PiggyBank/PiggyBankRepositoryInterface.php
@@ -52,6 +52,8 @@ interface PiggyBankRepositoryInterface
public function destroyAll(): void;
+ public function purgeAll(): void;
+
public function find(int $piggyBankId): ?PiggyBank;
/**
@@ -78,10 +80,7 @@ interface PiggyBankRepositoryInterface
*/
public function getExactAmount(PiggyBank $piggyBank, PiggyBankRepetition $repetition, TransactionJournal $journal): string;
- /**
- * Highest order of all piggy banks.
- */
- public function getMaxOrder(): int;
+ public function updateNote(PiggyBank $piggyBank, string $note): void;
/**
* Return note for piggy bank.
@@ -114,10 +113,10 @@ interface PiggyBankRepositoryInterface
public function removeObjectGroup(PiggyBank $piggyBank): PiggyBank;
- /**
- * Correct order of piggies in case of issues.
- */
- public function resetOrder(): void;
+// /**
+// * Correct order of piggies in case of issues.
+// */
+// public function resetOrder(): void;
/**
* Search for piggy banks.
@@ -133,7 +132,7 @@ interface PiggyBankRepositoryInterface
*/
public function setOrder(PiggyBank $piggyBank, int $newOrder): bool;
- public function setUser(null|Authenticatable|User $user): void;
+ public function setUser(null | Authenticatable | User $user): void;
/**
* Store new piggy bank.
diff --git a/app/Validation/FireflyValidator.php b/app/Validation/FireflyValidator.php
index 95553306ff..136bc2f9a5 100644
--- a/app/Validation/FireflyValidator.php
+++ b/app/Validation/FireflyValidator.php
@@ -27,6 +27,7 @@ use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Models\Account;
use FireflyIII\Models\AccountMeta;
use FireflyIII\Models\AccountType;
+use FireflyIII\Models\PiggyBank;
use FireflyIII\Models\TransactionType;
use FireflyIII\Models\Webhook;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
@@ -812,15 +813,15 @@ class FireflyValidator extends Validator
public function validateUniquePiggyBankForUser($attribute, $value, $parameters): bool
{
$exclude = $parameters[0] ?? null;
- $query = \DB::table('piggy_banks')->whereNull('piggy_banks.deleted_at')
- ->leftJoin('accounts', 'accounts.id', '=', 'piggy_banks.account_id')->where('accounts.user_id', auth()->user()->id)
- ;
+ $query = PiggyBank
+ ::leftJoin('account_piggy_bank','account_piggy_bank.piggy_bank_id', '=', 'piggy_banks.id')
+ ->leftJoin('accounts', 'accounts.id', '=', 'account_piggy_bank.account_id')
+ ->where('accounts.user_id', auth()->user()->id);
if (null !== $exclude) {
$query->where('piggy_banks.id', '!=', (int) $exclude);
}
$query->where('piggy_banks.name', $value);
-
- return null === $query->first(['piggy_banks.*']);
+ return 0 === $query->get(['piggy_banks.*'])->count();
}
/**
diff --git a/config/firefly.php b/config/firefly.php
index 2b651de7d9..c13ef5ecbe 100644
--- a/config/firefly.php
+++ b/config/firefly.php
@@ -913,4 +913,7 @@ return [
// preselected account lists possibilities:
'preselected_accounts' => ['all', 'assets', 'liabilities'],
+
+ // allowed to store a piggy bank in:
+ 'piggy_bank_account_types' => [AccountTypeEnum::ASSET->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value],
];
diff --git a/resources/lang/en_US/validation.php b/resources/lang/en_US/validation.php
index bdf68a07fd..9f6dc2fe54 100644
--- a/resources/lang/en_US/validation.php
+++ b/resources/lang/en_US/validation.php
@@ -25,6 +25,7 @@
declare(strict_types=1);
return [
+ 'invalid_account_type' => 'A piggy bank can only be linked to asset accounts and liabilities',
'filter_must_be_in' => 'Filter ":filter" must be one of: :values',
'filter_not_string' => 'Filter ":filter" is expected to be a string of text',
'bad_api_filter' => 'This API endpoint does not support ":filter" as a filter.',
diff --git a/routes/api.php b/routes/api.php
index 750450b257..ec16affdd9 100644
--- a/routes/api.php
+++ b/routes/api.php
@@ -615,6 +615,7 @@ Route::group(
Route::get('{piggyBank}/events', ['uses' => 'ListController@piggyBankEvents', 'as' => 'events']);
Route::get('{piggyBank}/attachments', ['uses' => 'ListController@attachments', 'as' => 'attachments']);
+ Route::get('{piggyBank}/accounts', ['uses' => 'ListController@accounts', 'as' => 'accounts']);
}
);
From d740814f8845c9007479602bcffa0912770b05f3 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 1 Dec 2024 18:32:05 +0100
Subject: [PATCH 009/167] API works for multi-account piggies, the rest throws
an exception
---
.../Models/PiggyBank/ShowController.php | 2 +-
.../Integrity/AddTimezonesToDates.php | 4 +-
app/Models/PiggyBank.php | 5 ++
.../PiggyBank/ModifiesPiggyBanks.php | 1 +
.../PiggyBank/PiggyBankRepository.php | 74 +++++++++----------
app/Transformers/PiggyBankTransformer.php | 58 +++++++++------
app/Transformers/V2/PiggyBankTransformer.php | 1 +
app/User.php | 8 --
8 files changed, 82 insertions(+), 71 deletions(-)
diff --git a/app/Api/V1/Controllers/Models/PiggyBank/ShowController.php b/app/Api/V1/Controllers/Models/PiggyBank/ShowController.php
index 2005bc4de5..442b47cb38 100644
--- a/app/Api/V1/Controllers/Models/PiggyBank/ShowController.php
+++ b/app/Api/V1/Controllers/Models/PiggyBank/ShowController.php
@@ -72,7 +72,7 @@ class ShowController extends Controller
// types to get, page size:
$pageSize = $this->parameters->get('limit');
- // get list of budgets. Count it and split it.
+ // get list of piggy banks. Count it and split it.
$collection = $this->repository->getPiggyBanks();
$count = $collection->count();
$piggyBanks = $collection->slice(($this->parameters->get('page') - 1) * $pageSize, $pageSize);
diff --git a/app/Console/Commands/Integrity/AddTimezonesToDates.php b/app/Console/Commands/Integrity/AddTimezonesToDates.php
index 7dafa505c4..cd347bd274 100644
--- a/app/Console/Commands/Integrity/AddTimezonesToDates.php
+++ b/app/Console/Commands/Integrity/AddTimezonesToDates.php
@@ -67,8 +67,8 @@ class AddTimezonesToDates extends Command
CurrencyExchangeRate::class => ['date'], // done
InvitedUser::class => ['expires'],
PiggyBankEvent::class => ['date'],
- PiggyBankRepetition::class => ['startdate', 'targetdate'],
- PiggyBank::class => ['startdate', 'targetdate'], // done
+ PiggyBankRepetition::class => ['start_date', 'target_date'],
+ PiggyBank::class => ['start_date', 'target_date'], // done
Recurrence::class => ['first_date', 'repeat_until', 'latest_date'],
Tag::class => ['date'],
TransactionJournal::class => ['date'],
diff --git a/app/Models/PiggyBank.php b/app/Models/PiggyBank.php
index 911566e628..d5a936cf31 100644
--- a/app/Models/PiggyBank.php
+++ b/app/Models/PiggyBank.php
@@ -78,6 +78,11 @@ class PiggyBank extends Model
throw new NotFoundHttpException();
}
+ public function transactionCurrency(): BelongsTo
+ {
+ return $this->belongsTo(TransactionCurrency::class);
+ }
+
public function account(): BelongsTo
{
return $this->belongsTo(Account::class);
diff --git a/app/Repositories/PiggyBank/ModifiesPiggyBanks.php b/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
index 998fed9b23..09169ef898 100644
--- a/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
+++ b/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
@@ -45,6 +45,7 @@ trait ModifiesPiggyBanks
public function addAmountToRepetition(PiggyBankRepetition $repetition, string $amount, TransactionJournal $journal): void
{
+ throw new FireflyException('[a] Piggy bank repetitions are EOL.');
app('log')->debug(sprintf('addAmountToRepetition: %s', $amount));
if (-1 === bccomp($amount, '0')) {
app('log')->debug('Remove amount.');
diff --git a/app/Repositories/PiggyBank/PiggyBankRepository.php b/app/Repositories/PiggyBank/PiggyBankRepository.php
index 1e9658d290..ce32ca3269 100644
--- a/app/Repositories/PiggyBank/PiggyBankRepository.php
+++ b/app/Repositories/PiggyBank/PiggyBankRepository.php
@@ -94,7 +94,7 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
public function getAttachments(PiggyBank $piggyBank): Collection
{
- $set = $piggyBank->attachments()->get();
+ $set = $piggyBank->attachments()->get();
/** @var \Storage $disk */
$disk = \Storage::disk('upload');
@@ -115,16 +115,18 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
*/
public function getCurrentAmount(PiggyBank $piggyBank): string
{
- $rep = $this->getRepetition($piggyBank);
- if (null === $rep) {
- return '0';
+ $sum = '0';
+ foreach ($piggyBank->accounts as $account) {
+ $amount = (string) $account->pivot->current_amount;
+ $amount = '' === $amount ? '0' : $amount;
+ $sum = bcadd($sum, $amount);
}
-
- return $rep->current_amount;
+ return $sum;
}
public function getRepetition(PiggyBank $piggyBank): ?PiggyBankRepetition
{
+ throw new FireflyException('[b] Piggy bank repetitions are EOL.');
return $piggyBank->piggyBankRepetitions()->first();
}
@@ -140,17 +142,18 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
*/
public function getExactAmount(PiggyBank $piggyBank, PiggyBankRepetition $repetition, TransactionJournal $journal): string
{
+ throw new FireflyException('[c] Piggy bank repetitions are EOL.');
app('log')->debug(sprintf('Now in getExactAmount(%d, %d, %d)', $piggyBank->id, $repetition->id, $journal->id));
- $operator = null;
- $currency = null;
+ $operator = null;
+ $currency = null;
/** @var JournalRepositoryInterface $journalRepost */
- $journalRepost = app(JournalRepositoryInterface::class);
+ $journalRepost = app(JournalRepositoryInterface::class);
$journalRepost->setUser($this->user);
/** @var AccountRepositoryInterface $accountRepos */
- $accountRepos = app(AccountRepositoryInterface::class);
+ $accountRepos = app(AccountRepositoryInterface::class);
$accountRepos->setUser($this->user);
$defaultCurrency = app('amount')->getDefaultCurrencyByUserGroup($this->user->userGroup);
@@ -159,10 +162,10 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
app('log')->debug(sprintf('Piggy bank #%d currency is %s', $piggyBank->id, $piggyBankCurrency->code));
/** @var Transaction $source */
- $source = $journal->transactions()->with(['account'])->where('amount', '<', 0)->first();
+ $source = $journal->transactions()->with(['account'])->where('amount', '<', 0)->first();
/** @var Transaction $destination */
- $destination = $journal->transactions()->with(['account'])->where('amount', '>', 0)->first();
+ $destination = $journal->transactions()->with(['account'])->where('amount', '>', 0)->first();
// matches source, which means amount will be removed from piggy:
if ($source->account_id === $piggyBank->account_id) {
@@ -184,12 +187,12 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
}
// currency of the account + the piggy bank currency are almost the same.
// which amount from the transaction matches?
- $amount = null;
- if ((int)$source->transaction_currency_id === $currency->id) {
+ $amount = null;
+ if ((int) $source->transaction_currency_id === $currency->id) {
app('log')->debug('Use normal amount');
$amount = app('steam')->{$operator}($source->amount); // @phpstan-ignore-line
}
- if ((int)$source->foreign_currency_id === $currency->id) {
+ if ((int) $source->foreign_currency_id === $currency->id) {
app('log')->debug('Use foreign amount');
$amount = app('steam')->{$operator}($source->foreign_amount); // @phpstan-ignore-line
}
@@ -200,8 +203,8 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
}
app('log')->debug(sprintf('The currency is %s and the amount is %s', $currency->code, $amount));
- $room = bcsub($piggyBank->target_amount, $repetition->current_amount);
- $compare = bcmul($repetition->current_amount, '-1');
+ $room = bcsub($piggyBank->target_amount, $repetition->current_amount);
+ $compare = bcmul($repetition->current_amount, '-1');
if (0 === bccomp($piggyBank->target_amount, '0')) {
// amount is zero? then the "room" is positive amount of we wish to add or remove.
@@ -230,10 +233,10 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
return $compare;
}
- return (string)$amount;
+ return (string) $amount;
}
- public function setUser(null|Authenticatable|User $user): void
+ public function setUser(null | Authenticatable | User $user): void
{
if ($user instanceof User) {
$this->user = $user;
@@ -249,7 +252,7 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
/** @var null|Note $note */
$note = $piggyBank->notes()->first();
- return (string)$note?->text;
+ return (string) $note?->text;
}
/**
@@ -259,12 +262,12 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
{
$currency = app('amount')->getDefaultCurrency();
- $set = $this->getPiggyBanks();
+ $set = $this->getPiggyBanks();
/** @var PiggyBank $piggy */
foreach ($set as $piggy) {
$currentAmount = $this->getRepetition($piggy)->current_amount ?? '0';
- $piggy->name = $piggy->name.' ('.app('amount')->formatAnything($currency, $currentAmount, false).')';
+ $piggy->name = $piggy->name . ' (' . app('amount')->formatAnything($currency, $currentAmount, false) . ')';
}
return $set;
@@ -272,16 +275,17 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
public function getPiggyBanks(): Collection
{
- return $this->user // @phpstan-ignore-line (phpstan does not recognize objectGroups)
- ->piggyBanks()
+ return PiggyBank
+ ::leftJoin('account_piggy_bank', 'account_piggy_bank.piggy_bank_id', '=', 'piggy_banks.id')
+ ->leftJoin('accounts', 'accounts.id', '=', 'account_piggy_bank.account_id')
+ ->where('accounts.user_id', auth()->user()->id)
->with(
[
'account',
'objectGroups',
]
)
- ->orderBy('order', 'ASC')->get()
- ;
+ ->orderBy('piggy_banks.order', 'ASC')->get();
}
/**
@@ -289,20 +293,17 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
*/
public function getSuggestedMonthlyAmount(PiggyBank $piggyBank): string
{
- $savePerMonth = '0';
- $repetition = $this->getRepetition($piggyBank);
- if (null === $repetition) {
- return $savePerMonth;
- }
- if (null !== $piggyBank->target_date && $repetition->current_amount < $piggyBank->target_amount) {
+ $savePerMonth = '0';
+ $currentAmount = $this->getCurrentAmount($piggyBank);
+ if (null !== $piggyBank->target_date && $currentAmount < $piggyBank->target_amount) {
$now = today(config('app.timezone'));
$startDate = null !== $piggyBank->start_date && $piggyBank->start_date->gte($now) ? $piggyBank->start_date : $now;
- $diffInMonths = (int)$startDate->diffInMonths($piggyBank->target_date);
- $remainingAmount = bcsub($piggyBank->target_amount, $repetition->current_amount);
+ $diffInMonths = (int) $startDate->diffInMonths($piggyBank->target_date);
+ $remainingAmount = bcsub($piggyBank->target_amount, $currentAmount);
// more than 1 month to go and still need money to save:
if ($diffInMonths > 0 && 1 === bccomp($remainingAmount, '0')) {
- $savePerMonth = bcdiv($remainingAmount, (string)$diffInMonths);
+ $savePerMonth = bcdiv($remainingAmount, (string) $diffInMonths);
}
// less than 1 month to go but still need money to save:
@@ -342,8 +343,7 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
$search->whereLike('piggy_banks.name', sprintf('%%%s%%', $query));
}
$search->orderBy('piggy_banks.order', 'ASC')
- ->orderBy('piggy_banks.name', 'ASC')
- ;
+ ->orderBy('piggy_banks.name', 'ASC');
return $search->take($limit)->get();
}
diff --git a/app/Transformers/PiggyBankTransformer.php b/app/Transformers/PiggyBankTransformer.php
index 4cc10cc466..701c816257 100644
--- a/app/Transformers/PiggyBankTransformer.php
+++ b/app/Transformers/PiggyBankTransformer.php
@@ -54,25 +54,22 @@ class PiggyBankTransformer extends AbstractTransformer
*/
public function transform(PiggyBank $piggyBank): array
{
- $account = $piggyBank->account;
+ $user = $piggyBank->accounts()->first()->user;
// set up repositories
- $this->accountRepos->setUser($account->user);
- $this->piggyRepos->setUser($account->user);
-
- // get currency from account, or use default.
- $currency = $this->accountRepos->getAccountCurrency($account) ?? app('amount')->getDefaultCurrencyByUserGroup($account->user->userGroup);
+ $this->accountRepos->setUser($user);
+ $this->piggyRepos->setUser($user);
// note
- $notes = $this->piggyRepos->getNoteText($piggyBank);
- $notes = '' === $notes ? null : $notes;
+ $notes = $this->piggyRepos->getNoteText($piggyBank);
+ $notes = '' === $notes ? null : $notes;
$objectGroupId = null;
$objectGroupOrder = null;
$objectGroupTitle = null;
/** @var null|ObjectGroup $objectGroup */
- $objectGroup = $piggyBank->objectGroups->first();
+ $objectGroup = $piggyBank->objectGroups->first();
if (null !== $objectGroup) {
$objectGroupId = $objectGroup->id;
$objectGroupOrder = $objectGroup->order;
@@ -80,31 +77,33 @@ class PiggyBankTransformer extends AbstractTransformer
}
// get currently saved amount:
- $currentAmount = app('steam')->bcround($this->piggyRepos->getCurrentAmount($piggyBank), $currency->decimal_places);
+ $currency = $piggyBank->transactionCurrency;
+ $currentAmount = app('steam')->bcround($this->piggyRepos->getCurrentAmount($piggyBank), $currency->decimal_places);
// Amounts, depending on 0.0 state of target amount
- $percentage = null;
- $targetAmount = $piggyBank->target_amount;
- $leftToSave = null;
- $savePerMonth = null;
+ $percentage = null;
+ $targetAmount = $piggyBank->target_amount;
+ $leftToSave = null;
+ $savePerMonth = null;
if (0 !== bccomp($targetAmount, '0')) { // target amount is not 0.00
$leftToSave = bcsub($piggyBank->target_amount, $currentAmount);
- $percentage = (int)bcmul(bcdiv($currentAmount, $targetAmount), '100');
+ $percentage = (int) bcmul(bcdiv($currentAmount, $targetAmount), '100');
$targetAmount = app('steam')->bcround($targetAmount, $currency->decimal_places);
$leftToSave = app('steam')->bcround($leftToSave, $currency->decimal_places);
$savePerMonth = app('steam')->bcround($this->piggyRepos->getSuggestedMonthlyAmount($piggyBank), $currency->decimal_places);
}
- $startDate = $piggyBank->start_date?->format('Y-m-d');
- $targetDate = $piggyBank->target_date?->format('Y-m-d');
+ $startDate = $piggyBank->start_date?->format('Y-m-d');
+ $targetDate = $piggyBank->target_date?->format('Y-m-d');
return [
- 'id' => (string)$piggyBank->id,
+ 'id' => (string) $piggyBank->id,
'created_at' => $piggyBank->created_at->toAtomString(),
'updated_at' => $piggyBank->updated_at->toAtomString(),
- 'account_id' => (string)$piggyBank->account_id,
- 'account_name' => $piggyBank->account->name,
+ 'accounts' => $this->renderAccounts($piggyBank),
+ //'account_id' => (string)$piggyBank->account_id,
+ //'account_name' => $piggyBank->account->name,
'name' => $piggyBank->name,
- 'currency_id' => (string)$currency->id,
+ 'currency_id' => (string) $currency->id,
'currency_code' => $currency->code,
'currency_symbol' => $currency->symbol,
'currency_decimal_places' => $currency->decimal_places,
@@ -118,15 +117,28 @@ class PiggyBankTransformer extends AbstractTransformer
'order' => $piggyBank->order,
'active' => true,
'notes' => $notes,
- 'object_group_id' => null !== $objectGroupId ? (string)$objectGroupId : null,
+ 'object_group_id' => null !== $objectGroupId ? (string) $objectGroupId : null,
'object_group_order' => $objectGroupOrder,
'object_group_title' => $objectGroupTitle,
'links' => [
[
'rel' => 'self',
- 'uri' => '/piggy_banks/'.$piggyBank->id,
+ 'uri' => '/piggy_banks/' . $piggyBank->id,
],
],
];
}
+
+ private function renderAccounts(PiggyBank $piggyBank): array
+ {
+ $return = [];
+ foreach ($piggyBank->accounts as $account) {
+ $return[] = [
+ 'id' => $account->id,
+ 'name' => $account->name,
+ // TODO add balance, add left to save.
+ ];
+ }
+ return $return;
+ }
}
diff --git a/app/Transformers/V2/PiggyBankTransformer.php b/app/Transformers/V2/PiggyBankTransformer.php
index 30ebe367a7..8dfb88b69c 100644
--- a/app/Transformers/V2/PiggyBankTransformer.php
+++ b/app/Transformers/V2/PiggyBankTransformer.php
@@ -115,6 +115,7 @@ class PiggyBankTransformer extends AbstractTransformer
// grab repetitions (for current amount):
$repetitions = PiggyBankRepetition::whereIn('piggy_bank_id', $piggyBanks)->get();
+ throw new FireflyException('[d] Piggy bank repetitions are EOL.');
/** @var PiggyBankRepetition $repetition */
foreach ($repetitions as $repetition) {
diff --git a/app/User.php b/app/User.php
index deb0b896ab..3e44cb1e43 100644
--- a/app/User.php
+++ b/app/User.php
@@ -332,14 +332,6 @@ class User extends Authenticatable
return $this->hasMany(ObjectGroup::class);
}
- /**
- * Link to piggy banks.
- */
- public function piggyBanks(): HasManyThrough
- {
- return $this->hasManyThrough(PiggyBank::class, Account::class);
- }
-
/**
* Link to preferences.
*/
From 4819b5ac5d08e6461d522f47a5f4ec049fbd2237 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Wed, 4 Dec 2024 06:38:47 +0100
Subject: [PATCH 010/167] More code for multi account piggy banks.
---
app/Factory/PiggyBankFactory.php | 15 +-
.../Controllers/PiggyBank/IndexController.php | 159 ++++++++++++------
app/Models/PiggyBank.php | 2 +-
.../PiggyBank/PiggyBankRepository.php | 10 +-
.../PiggyBankRepositoryInterface.php | 5 +-
app/Transformers/PiggyBankTransformer.php | 3 +-
6 files changed, 131 insertions(+), 63 deletions(-)
diff --git a/app/Factory/PiggyBankFactory.php b/app/Factory/PiggyBankFactory.php
index df9b54bc46..7f9def7600 100644
--- a/app/Factory/PiggyBankFactory.php
+++ b/app/Factory/PiggyBankFactory.php
@@ -169,9 +169,20 @@ class PiggyBankFactory
}
- private function resetOrder(): void
+ public function resetOrder(): void
{
- $set = $this->user->piggyBanks()->orderBy('piggy_banks.order', 'ASC')->get(['piggy_banks.*']);
+ // TODO duplicate code
+ $set = PiggyBank
+ ::leftJoin('account_piggy_bank', 'account_piggy_bank.piggy_bank_id', '=', 'piggy_banks.id')
+ ->leftJoin('accounts', 'accounts.id', '=', 'account_piggy_bank.account_id')
+ ->where('accounts.user_id', $this->user->id)
+ ->with(
+ [
+ 'account',
+ 'objectGroups',
+ ]
+ )
+ ->orderBy('piggy_banks.order', 'ASC')->get(['piggy_banks.*']);
$current = 1;
foreach ($set as $piggyBank) {
if ($piggyBank->order !== $current) {
diff --git a/app/Http/Controllers/PiggyBank/IndexController.php b/app/Http/Controllers/PiggyBank/IndexController.php
index 9c08ebdf25..eca160f505 100644
--- a/app/Http/Controllers/PiggyBank/IndexController.php
+++ b/app/Http/Controllers/PiggyBank/IndexController.php
@@ -36,6 +36,7 @@ use FireflyIII\Transformers\PiggyBankTransformer;
use Illuminate\Contracts\View\Factory;
use Illuminate\Http\JsonResponse;
use Illuminate\Http\Request;
+use Illuminate\Support\Collection;
use Illuminate\View\View;
use Symfony\Component\HttpFoundation\ParameterBag;
@@ -57,7 +58,7 @@ class IndexController extends Controller
$this->middleware(
function ($request, $next) {
- app('view')->share('title', (string)trans('firefly.piggyBanks'));
+ app('view')->share('title', (string) trans('firefly.piggyBanks'));
app('view')->share('mainTitleIcon', 'fa-bullseye');
$this->piggyRepos = app(PiggyBankRepositoryInterface::class);
@@ -79,63 +80,26 @@ class IndexController extends Controller
public function index()
{
$this->cleanupObjectGroups();
- //$this->piggyRepos->resetOrder();
- $collection = $this->piggyRepos->getPiggyBanks();
- $accounts = [];
+ $this->piggyRepos->resetOrder();
+ $collection = $this->piggyRepos->getPiggyBanks();
/** @var Carbon $end */
- $end = session('end', today(config('app.timezone'))->endOfMonth());
+ $end = session('end', today(config('app.timezone'))->endOfMonth());
// transform piggies using the transformer:
- $parameters = new ParameterBag();
+ $parameters = new ParameterBag();
$parameters->set('end', $end);
- // make piggy bank groups:
- $piggyBanks = [];
-
- /** @var PiggyBankTransformer $transformer */
- $transformer = app(PiggyBankTransformer::class);
- $transformer->setParameters(new ParameterBag());
/** @var AccountTransformer $accountTransformer */
$accountTransformer = app(AccountTransformer::class);
$accountTransformer->setParameters($parameters);
- /** @var PiggyBank $piggy */
- foreach ($collection as $piggy) {
- $array = $transformer->transform($piggy);
- $groupOrder = (int)$array['object_group_order'];
- // make group array if necessary:
- $piggyBanks[$groupOrder] ??= [
- 'object_group_id' => $array['object_group_id'] ?? 0,
- 'object_group_title' => $array['object_group_title'] ?? trans('firefly.default_group_title_name'),
- 'piggy_banks' => [],
- ];
-
- $account = $accountTransformer->transform($piggy->account);
- $accountId = (int)$account['id'];
- $array['attachments'] = $this->piggyRepos->getAttachments($piggy);
- if (!array_key_exists($accountId, $accounts)) {
- // create new:
- $accounts[$accountId] = $account;
-
- // add some interesting details:
- $accounts[$accountId]['left'] = $accounts[$accountId]['current_balance'];
- $accounts[$accountId]['saved'] = 0;
- $accounts[$accountId]['target'] = 0;
- $accounts[$accountId]['to_save'] = 0;
- }
-
- // calculate new interesting fields:
- $accounts[$accountId]['left'] -= $array['current_amount'];
- $accounts[$accountId]['saved'] += $array['current_amount'];
- $accounts[$accountId]['target'] += $array['target_amount'];
- $accounts[$accountId]['to_save'] += ($array['target_amount'] - $array['current_amount']);
- $array['account_name'] = $account['name'];
- $piggyBanks[$groupOrder]['piggy_banks'][] = $array;
- }
- // do a bunch of summaries.
- $piggyBanks = $this->makeSums($piggyBanks);
+ // data
+ $piggyBanks = $this->groupPiggyBanks($collection);
+ $accounts = $this->collectAccounts($collection);
+ $accounts = $this->mergeAccountsAndPiggies($piggyBanks, $accounts);
+ $piggyBanks = $this->makeSums($piggyBanks);
ksort($piggyBanks);
@@ -148,7 +112,7 @@ class IndexController extends Controller
foreach ($piggyBanks as $groupOrder => $group) {
$groupId = $group['object_group_id'];
foreach ($group['piggy_banks'] as $piggy) {
- $currencyId = $piggy['currency_id'];
+ $currencyId = $piggy['currency_id'];
$sums[$groupId][$currencyId] ??= [
'target' => '0',
'saved' => '0',
@@ -163,10 +127,10 @@ class IndexController extends Controller
// current_amount
// left_to_save
// save_per_month
- $sums[$groupId][$currencyId]['target'] = bcadd($sums[$groupId][$currencyId]['target'], (string)$piggy['target_amount']);
- $sums[$groupId][$currencyId]['saved'] = bcadd($sums[$groupId][$currencyId]['saved'], (string)$piggy['current_amount']);
- $sums[$groupId][$currencyId]['left_to_save'] = bcadd($sums[$groupId][$currencyId]['left_to_save'], (string)$piggy['left_to_save']);
- $sums[$groupId][$currencyId]['save_per_month'] = bcadd($sums[$groupId][$currencyId]['save_per_month'], (string)$piggy['save_per_month']);
+ $sums[$groupId][$currencyId]['target'] = bcadd($sums[$groupId][$currencyId]['target'], (string) $piggy['target_amount']);
+ $sums[$groupId][$currencyId]['saved'] = bcadd($sums[$groupId][$currencyId]['saved'], (string) $piggy['current_amount']);
+ $sums[$groupId][$currencyId]['left_to_save'] = bcadd($sums[$groupId][$currencyId]['left_to_save'], (string) $piggy['left_to_save']);
+ $sums[$groupId][$currencyId]['save_per_month'] = bcadd($sums[$groupId][$currencyId]['save_per_month'], (string) $piggy['save_per_month']);
}
}
foreach ($piggyBanks as $groupOrder => $group) {
@@ -182,8 +146,8 @@ class IndexController extends Controller
*/
public function setOrder(Request $request, PiggyBank $piggyBank): JsonResponse
{
- $objectGroupTitle = (string)$request->get('objectGroupTitle');
- $newOrder = (int)$request->get('order');
+ $objectGroupTitle = (string) $request->get('objectGroupTitle');
+ $newOrder = (int) $request->get('order');
$this->piggyRepos->setOrder($piggyBank, $newOrder);
if ('' !== $objectGroupTitle) {
$this->piggyRepos->setObjectGroup($piggyBank, $objectGroupTitle);
@@ -194,4 +158,91 @@ class IndexController extends Controller
return response()->json(['data' => 'OK']);
}
+
+ private function groupPiggyBanks(Collection $collection): array
+ {
+ /** @var PiggyBankTransformer $transformer */
+ $transformer = app(PiggyBankTransformer::class);
+ $transformer->setParameters(new ParameterBag());
+ $piggyBanks = [];
+ /** @var PiggyBank $piggy */
+ foreach ($collection as $piggy) {
+ $array = $transformer->transform($piggy);
+ $groupOrder = (int) $array['object_group_order'];
+ $piggyBanks[$groupOrder] ??= [
+ 'object_group_id' => $array['object_group_id'] ?? 0,
+ 'object_group_title' => $array['object_group_title'] ?? trans('firefly.default_group_title_name'),
+ 'piggy_banks' => [],
+ ];
+ $array['attachments'] = $this->piggyRepos->getAttachments($piggy);
+
+ // sum the total amount for the index.
+ $piggyBanks[$groupOrder]['piggy_banks'][] = $array;
+ }
+ return $piggyBanks;
+ }
+
+ private function collectAccounts(Collection $collection): array
+ {
+ /** @var Carbon $end */
+ $end = session('end', today(config('app.timezone'))->endOfMonth());
+
+ // transform piggies using the transformer:
+ $parameters = new ParameterBag();
+ $parameters->set('end', $end);
+
+ /** @var AccountTransformer $accountTransformer */
+ $accountTransformer = app(AccountTransformer::class);
+ $accountTransformer->setParameters($parameters);
+
+ $return = [];
+ /** @var PiggyBank $piggy */
+ foreach ($collection as $piggy) {
+ $accounts = $piggy->accounts;
+ /** @var Account $account */
+ foreach ($accounts as $account) {
+ $array = $accountTransformer->transform($account);
+ $accountId = (int) $array['id'];
+ if (!array_key_exists($accountId, $return)) {
+ $return[$accountId] = $array;
+
+ // add some interesting details:
+ $return[$accountId]['left'] = $return[$accountId]['current_balance'];
+ $return[$accountId]['saved'] = '0';
+ $return[$accountId]['target'] = '0';
+ $return[$accountId]['to_save'] = '0';
+ }
+
+ // calculate new interesting fields:
+// $return[$accountId]['left'] -= $array['current_amount'];
+// $return[$accountId]['saved'] += $array['current_amount'];
+// $return[$accountId]['target'] += $array['target_amount'];
+// $return[$accountId]['to_save'] += ($array['target_amount'] - $array['current_amount']);
+// $return['account_name'] = $account['name'];
+
+ }
+ }
+ return $return;
+ }
+
+ private function mergeAccountsAndPiggies(array $piggyBanks, array $accounts): array
+ {
+ /** @var array $piggyBank */
+ foreach ($piggyBanks as $group) {
+ foreach ($group['piggy_banks'] as $piggyBank) {
+ // loop all accounts in this piggy bank subtract the current amount from "left to save" in the $accounts array.
+ /** @var array $piggyAccount */
+ foreach ($piggyBank['accounts'] as $piggyAccount) {
+ $accountId = $piggyAccount['id'];
+ if (array_key_exists($accountId, $accounts)) {
+ $accounts[$accountId]['left'] = bcsub($accounts[$accountId]['left'], $piggyAccount['current_amount']);
+ $accounts[$accountId]['saved'] = bcadd($accounts[$accountId]['saved'], $piggyAccount['current_amount']);
+ $accounts[$accountId]['target'] = bcadd($accounts[$accountId]['target'], $piggyBank['target_amount']);
+ $accounts[$accountId]['to_save'] = bcadd($accounts[$accountId]['to_save'], bcsub($piggyBank['target_amount'], $piggyAccount['current_amount']));
+ }
+ }
+ }
+ }
+ return $accounts;
+ }
}
diff --git a/app/Models/PiggyBank.php b/app/Models/PiggyBank.php
index d5a936cf31..fa797977fc 100644
--- a/app/Models/PiggyBank.php
+++ b/app/Models/PiggyBank.php
@@ -116,7 +116,7 @@ class PiggyBank extends Model
public function accounts(): BelongsToMany
{
- return $this->belongsToMany(Account::class);
+ return $this->belongsToMany(Account::class)->withPivot('current_amount');
}
public function piggyBankRepetitions(): HasMany
diff --git a/app/Repositories/PiggyBank/PiggyBankRepository.php b/app/Repositories/PiggyBank/PiggyBankRepository.php
index ce32ca3269..cf73589b94 100644
--- a/app/Repositories/PiggyBank/PiggyBankRepository.php
+++ b/app/Repositories/PiggyBank/PiggyBankRepository.php
@@ -25,6 +25,7 @@ namespace FireflyIII\Repositories\PiggyBank;
use Carbon\Carbon;
use FireflyIII\Exceptions\FireflyException;
+use FireflyIII\Factory\PiggyBankFactory;
use FireflyIII\Models\Attachment;
use FireflyIII\Models\Note;
use FireflyIII\Models\PiggyBank;
@@ -285,7 +286,7 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
'objectGroups',
]
)
- ->orderBy('piggy_banks.order', 'ASC')->get();
+ ->orderBy('piggy_banks.order', 'ASC')->get(['piggy_banks.*']);
}
/**
@@ -352,4 +353,11 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
{
throw new FireflyException('TODO Not implemented');
}
+
+ #[\Override] public function resetOrder(): void
+ {
+ $factory = new PiggyBankFactory();
+ $factory->setUser($this->user);
+ $factory->resetOrder();
+ }
}
diff --git a/app/Repositories/PiggyBank/PiggyBankRepositoryInterface.php b/app/Repositories/PiggyBank/PiggyBankRepositoryInterface.php
index dfe534f4cf..b2c13d5764 100644
--- a/app/Repositories/PiggyBank/PiggyBankRepositoryInterface.php
+++ b/app/Repositories/PiggyBank/PiggyBankRepositoryInterface.php
@@ -113,10 +113,7 @@ interface PiggyBankRepositoryInterface
public function removeObjectGroup(PiggyBank $piggyBank): PiggyBank;
-// /**
-// * Correct order of piggies in case of issues.
-// */
-// public function resetOrder(): void;
+ public function resetOrder(): void;
/**
* Search for piggy banks.
diff --git a/app/Transformers/PiggyBankTransformer.php b/app/Transformers/PiggyBankTransformer.php
index 701c816257..ae15958fbe 100644
--- a/app/Transformers/PiggyBankTransformer.php
+++ b/app/Transformers/PiggyBankTransformer.php
@@ -132,10 +132,11 @@ class PiggyBankTransformer extends AbstractTransformer
private function renderAccounts(PiggyBank $piggyBank): array
{
$return = [];
- foreach ($piggyBank->accounts as $account) {
+ foreach ($piggyBank->accounts()->get() as $account) {
$return[] = [
'id' => $account->id,
'name' => $account->name,
+ 'current_amount' => $account->pivot->current_amount,
// TODO add balance, add left to save.
];
}
From ea4be9dd0cc4927e1551df9c729779af414a6702 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Fri, 6 Dec 2024 08:10:31 +0100
Subject: [PATCH 011/167] Expand forms and improve validation for multi-account
piggy banks
---
.../Models/PiggyBank/StoreRequest.php | 49 ++++++++++++++++---
app/Factory/PiggyBankFactory.php | 16 +++---
.../PiggyBank/CreateController.php | 5 +-
app/Http/Requests/PiggyBankStoreRequest.php | 29 +++++++----
app/Models/AccountType.php | 26 +++++-----
.../PiggyBank/ModifiesPiggyBanks.php | 4 +-
.../PiggyBank/PiggyBankRepository.php | 4 +-
.../Support/RecurringTransactionTrait.php | 6 +--
app/Support/Form/AccountForm.php | 18 ++++++-
app/Support/Form/FormSupport.php | 19 +++++++
config/twigbridge.php | 1 +
resources/lang/en_US/firefly.php | 1 +
resources/lang/en_US/form.php | 7 +--
resources/lang/en_US/validation.php | 2 +
resources/views/form/multi-select.twig | 10 ++++
resources/views/piggy-banks/create.twig | 9 ++--
16 files changed, 149 insertions(+), 57 deletions(-)
create mode 100644 resources/views/form/multi-select.twig
diff --git a/app/Api/V1/Requests/Models/PiggyBank/StoreRequest.php b/app/Api/V1/Requests/Models/PiggyBank/StoreRequest.php
index d73abc7b8c..2566cfe8ba 100644
--- a/app/Api/V1/Requests/Models/PiggyBank/StoreRequest.php
+++ b/app/Api/V1/Requests/Models/PiggyBank/StoreRequest.php
@@ -24,8 +24,11 @@ declare(strict_types=1);
namespace FireflyIII\Api\V1\Requests\Models\PiggyBank;
+use FireflyIII\Exceptions\FireflyException;
+use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
use FireflyIII\Rules\IsValidPositiveAmount;
+use FireflyIII\Rules\IsValidZeroOrMoreAmount;
use FireflyIII\Support\Request\ChecksLogin;
use FireflyIII\Support\Request\ConvertsDataTypes;
use Illuminate\Foundation\Http\FormRequest;
@@ -73,27 +76,30 @@ class StoreRequest extends FormRequest
'accounts' => 'required',
'accounts.*' => 'array|required',
'accounts.*.account_id' => 'required|numeric|belongsToUser:accounts,id',
- 'accounts.*.current_amount' => ['numeric', new IsValidPositiveAmount()],
+ 'accounts.*.current_amount' => ['numeric', new IsValidZeroOrMoreAmount()],
'object_group_id' => 'numeric|belongsToUser:object_groups,id',
'object_group_title' => ['min:1', 'max:255'],
- 'target_amount' => ['required', new IsValidPositiveAmount()],
+ 'target_amount' => ['required', new IsValidZeroOrMoreAmount()],
'start_date' => 'date|nullable',
- 'transaction_currency_id' => 'exists:transaction_currencies,id',
- 'transaction_currency_code' => 'exists:transaction_currencies,code',
+ 'transaction_currency_id' => 'exists:transaction_currencies,id|required_without:transaction_currency_code',
+ 'transaction_currency_code' => 'exists:transaction_currencies,code|required_without:transaction_currency_id',
'target_date' => 'date|nullable|after:start_date',
'notes' => 'max:65000',
];
}
/**
- * Can only store money on liabilities and asset accouns.
+ * Can only store money on liabilities and asset accounts.
*/
public function withValidator(Validator $validator): void
{
$validator->after(
function (Validator $validator): void {
// validate start before end only if both are there.
- $data = $validator->getData();
+ $data = $validator->getData();
+ $currency = $this->getCurrencyFromData($data);
+ $targetAmount = (string) ($data['target_amount'] ?? '0');
+ $currentAmount = '0';
if (array_key_exists('accounts', $data) && is_array($data['accounts'])) {
$repository = app(AccountRepositoryInterface::class);
$types = config('firefly.piggy_bank_account_types');
@@ -101,6 +107,13 @@ class StoreRequest extends FormRequest
$accountId = (int) ($array['account_id'] ?? 0);
$account = $repository->find($accountId);
if (null !== $account) {
+ // check currency here.
+ $accountCurrency = $repository->getAccountCurrency($account);
+ $isMultiCurrency = $repository->getMetaValue($account, 'is_multi_currency');
+ $currentAmount = bcadd($currentAmount, (string)($array['current_amount'] ?? '0'));
+ if ($accountCurrency->id !== $currency->id && 'true' !== $isMultiCurrency) {
+ $validator->errors()->add(sprintf('accounts.%d', $index), trans('validation.invalid_account_currency'));
+ }
$type = $account->accountType->type;
if (!in_array($type, $types, true)) {
$validator->errors()->add(sprintf('accounts.%d', $index), trans('validation.invalid_account_type'));
@@ -108,6 +121,9 @@ class StoreRequest extends FormRequest
}
}
}
+ if(bccomp($targetAmount, $currentAmount) === -1 && bccomp($targetAmount, '0') === 1) {
+ $validator->errors()->add('target_amount', trans('validation.current_amount_too_much'));
+ }
}
);
if ($validator->fails()) {
@@ -126,10 +142,27 @@ class StoreRequest extends FormRequest
continue;
}
$return[] = [
- 'account_id' => $this->integerFromValue((string)($entry['account_id'] ?? '0')),
- 'current_amount' => $this->clearString($entry['current_amount'] ?? '0'),
+ 'account_id' => $this->integerFromValue((string) ($entry['account_id'] ?? '0')),
+ 'current_amount' => $this->clearString((string) ($entry['current_amount'] ?? '0')),
];
}
return $return;
}
+
+ private function getCurrencyFromData(array $data): TransactionCurrency
+ {
+ if (array_key_exists('transaction_currency_code', $data) && '' !== (string) $data['transaction_currency_code']) {
+ $currency = TransactionCurrency::whereCode($data['transaction_currency_code'])->first();
+ if (null !== $currency) {
+ return $currency;
+ }
+ }
+ if (array_key_exists('transaction_currency_id', $data) && '' !== (string) $data['transaction_currency_id']) {
+ $currency = TransactionCurrency::find((int) $data['transaction_currency_id']);
+ if (null !== $currency) {
+ return $currency;
+ }
+ }
+ throw new FireflyException('Unexpected empty currency.');
+ }
}
diff --git a/app/Factory/PiggyBankFactory.php b/app/Factory/PiggyBankFactory.php
index 7f9def7600..cd41ee1deb 100644
--- a/app/Factory/PiggyBankFactory.php
+++ b/app/Factory/PiggyBankFactory.php
@@ -37,7 +37,11 @@ use Illuminate\Database\QueryException;
*/
class PiggyBankFactory
{
- private User $user;
+ public User $user {
+ set(User $value) {
+ $this->user = $value;
+ }
+ }
private CurrencyRepositoryInterface $currencyRepository;
private AccountRepositoryInterface $accountRepository;
private PiggyBankRepositoryInterface $piggyBankRepository;
@@ -138,11 +142,6 @@ class PiggyBankFactory
return $this->user->piggyBanks()->where('piggy_banks.name', $name)->first();
}
- public function setUser(User $user): void
- {
- $this->user = $user;
- }
-
private function getCurrency(array $data): TransactionCurrency {
// currency:
$defaultCurrency = app('amount')->getDefaultCurrency();
@@ -197,7 +196,8 @@ class PiggyBankFactory
private function getMaxOrder(): int
{
- return (int)$this->user->piggyBanks()->max('piggy_banks.order');
+ return (int) $this->piggyBankRepository->getPiggyBanks()->max('order');
+
}
private function linkToAccountIds(PiggyBank $piggyBank, array $accounts): void {
@@ -207,7 +207,7 @@ class PiggyBankFactory
if(null === $account) {
continue;
}
- $piggyBank->accounts()->syncWithoutDetaching([$account->id, ['current_amount' => $info['current_amount'] ?? '0']]);
+ $piggyBank->accounts()->syncWithoutDetaching([$account->id => ['current_amount' => $info['current_amount'] ?? '0']]);
}
}
}
diff --git a/app/Http/Controllers/PiggyBank/CreateController.php b/app/Http/Controllers/PiggyBank/CreateController.php
index 92aac833d9..a0626b5c3b 100644
--- a/app/Http/Controllers/PiggyBank/CreateController.php
+++ b/app/Http/Controllers/PiggyBank/CreateController.php
@@ -92,10 +92,11 @@ class CreateController extends Controller
public function store(PiggyBankStoreRequest $request)
{
$data = $request->getPiggyBankData();
- if (null === $data['startdate']) {
- $data['startdate'] = today(config('app.timezone'));
+ if (null === $data['start_date']) {
+ $data['start_date'] = today(config('app.timezone'));
}
$piggyBank = $this->piggyRepos->store($data);
+ var_dump($data);exit;
session()->flash('success', (string)trans('firefly.stored_piggy_bank', ['name' => $piggyBank->name]));
app('preferences')->mark();
diff --git a/app/Http/Requests/PiggyBankStoreRequest.php b/app/Http/Requests/PiggyBankStoreRequest.php
index 94087fedb8..467cfe607e 100644
--- a/app/Http/Requests/PiggyBankStoreRequest.php
+++ b/app/Http/Requests/PiggyBankStoreRequest.php
@@ -43,15 +43,21 @@ class PiggyBankStoreRequest extends FormRequest
*/
public function getPiggyBankData(): array
{
- return [
+ $data = [
'name' => $this->convertString('name'),
- 'startdate' => $this->getCarbonDate('startdate'),
- 'account_id' => $this->convertInteger('account_id'),
- 'targetamount' => $this->convertString('targetamount'),
- 'targetdate' => $this->getCarbonDate('targetdate'),
+ 'start_date' => $this->getCarbonDate('start_date'),
+ //'account_id' => $this->convertInteger('account_id'),
+ 'accounts' => $this->get('accounts'),
+ 'target_amount' => $this->convertString('target_amount'),
+ 'target_date' => $this->getCarbonDate('target_date'),
'notes' => $this->stringWithNewlines('notes'),
'object_group_title' => $this->convertString('object_group'),
];
+ if(!is_array($data['accounts'])) {
+ $data['accounts'] = [];
+ }
+
+ return $data;
}
/**
@@ -61,10 +67,11 @@ class PiggyBankStoreRequest extends FormRequest
{
return [
'name' => 'required|min:1|max:255|uniquePiggyBankForUser',
- 'account_id' => 'required|belongsToUser:accounts',
- 'targetamount' => ['nullable', new IsValidPositiveAmount()],
- 'startdate' => 'date',
- 'targetdate' => 'date|nullable',
+ 'accounts' => 'required|array',
+ 'accounts.*' => 'required|belongsToUser:accounts',
+ 'target_amount' => ['nullable', new IsValidPositiveAmount()],
+ 'start_date' => 'date',
+ 'target_date' => 'date|nullable',
'order' => 'integer|min:1',
'object_group' => 'min:0|max:255',
'notes' => 'min:1|max:32768|nullable',
@@ -73,6 +80,10 @@ class PiggyBankStoreRequest extends FormRequest
public function withValidator(Validator $validator): void
{
+ // need to have more than one account.
+ // accounts need to have the same currency or be multi-currency(?).
+
+
if ($validator->fails()) {
Log::channel('audit')->error(sprintf('Validation errors in %s', __CLASS__), $validator->errors()->toArray());
}
diff --git a/app/Models/AccountType.php b/app/Models/AccountType.php
index 0ef77adcc2..c8bc76b399 100644
--- a/app/Models/AccountType.php
+++ b/app/Models/AccountType.php
@@ -35,46 +35,46 @@ class AccountType extends Model
{
use ReturnsIntegerIdTrait;
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string ASSET = 'Asset account';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string BENEFICIARY = 'Beneficiary account';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string CASH = 'Cash account';
#[\Deprecated] /** @deprecated */
public const string CREDITCARD = 'Credit card';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string DEBT = 'Debt';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string DEFAULT = 'Default account';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string EXPENSE = 'Expense account';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string IMPORT = 'Import account';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string INITIAL_BALANCE = 'Initial balance account';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string LIABILITY_CREDIT = 'Liability credit account';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string LOAN = 'Loan';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string MORTGAGE = 'Mortgage';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string RECONCILIATION = 'Reconciliation account';
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const string REVENUE = 'Revenue account';
protected $casts
diff --git a/app/Repositories/PiggyBank/ModifiesPiggyBanks.php b/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
index 09169ef898..f37bc9e1a2 100644
--- a/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
+++ b/app/Repositories/PiggyBank/ModifiesPiggyBanks.php
@@ -182,8 +182,8 @@ trait ModifiesPiggyBanks
*/
public function store(array $data): PiggyBank
{
- $factory = new PiggyBankFactory();
- $factory->setUser($this->user);
+ $factory = new PiggyBankFactory();
+ $factory->user = $this->user;
return $factory->store($data);
}
diff --git a/app/Repositories/PiggyBank/PiggyBankRepository.php b/app/Repositories/PiggyBank/PiggyBankRepository.php
index cf73589b94..bd8c78de52 100644
--- a/app/Repositories/PiggyBank/PiggyBankRepository.php
+++ b/app/Repositories/PiggyBank/PiggyBankRepository.php
@@ -356,8 +356,8 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface
#[\Override] public function resetOrder(): void
{
- $factory = new PiggyBankFactory();
- $factory->setUser($this->user);
+ $factory = new PiggyBankFactory();
+ $factory->user = $this->user;
$factory->resetOrder();
}
}
diff --git a/app/Services/Internal/Support/RecurringTransactionTrait.php b/app/Services/Internal/Support/RecurringTransactionTrait.php
index 438563c98b..1ca7f701c2 100644
--- a/app/Services/Internal/Support/RecurringTransactionTrait.php
+++ b/app/Services/Internal/Support/RecurringTransactionTrait.php
@@ -283,9 +283,9 @@ trait RecurringTransactionTrait
protected function updatePiggyBank(RecurrenceTransaction $transaction, int $piggyId): void
{
/** @var PiggyBankFactory $factory */
- $factory = app(PiggyBankFactory::class);
- $factory->setUser($transaction->recurrence->user);
- $piggyBank = $factory->find($piggyId, null);
+ $factory = app(PiggyBankFactory::class);
+ $factory->user = $transaction->recurrence->user;
+ $piggyBank = $factory->find($piggyId, null);
if (null !== $piggyBank) {
/** @var null|RecurrenceMeta $entry */
$entry = $transaction->recurrenceTransactionMeta()->where('name', 'piggy_bank_id')->first();
diff --git a/app/Support/Form/AccountForm.php b/app/Support/Form/AccountForm.php
index b7bc140a79..8034bf93e6 100644
--- a/app/Support/Form/AccountForm.php
+++ b/app/Support/Form/AccountForm.php
@@ -24,6 +24,7 @@ declare(strict_types=1);
namespace FireflyIII\Support\Form;
+use FireflyIII\Enums\AccountTypeEnum;
use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Models\Account;
use FireflyIII\Models\AccountType;
@@ -141,12 +142,25 @@ class AccountForm
*/
public function assetAccountList(string $name, $value = null, ?array $options = null): string
{
- $types = [AccountType::ASSET, AccountType::DEFAULT];
+ $types = [AccountTypeEnum::ASSET->value, AccountTypeEnum::DEFAULT->value];
$grouped = $this->getAccountsGrouped($types);
return $this->select($name, $grouped, $value, $options);
}
+ /**
+ * Basic list of asset accounts.
+ *
+ * @param mixed $value
+ */
+ public function assetLiabilityMultiAccountList(string $name, $value = null, ?array $options = null): string
+ {
+ $types = [AccountTypeEnum::ASSET->value, AccountTypeEnum::DEFAULT->value, AccountTypeEnum::MORTGAGE->value, AccountTypeEnum::DEBT->value,AccountTypeEnum::LOAN->value];
+ $grouped = $this->getAccountsGrouped($types);
+
+ return $this->multiSelect($name, $grouped, $value, $options);
+ }
+
/**
* Same list but all liabilities as well.
*
@@ -154,7 +168,7 @@ class AccountForm
*/
public function longAccountList(string $name, $value = null, ?array $options = null): string
{
- $types = [AccountType::ASSET, AccountType::DEFAULT, AccountType::MORTGAGE, AccountType::DEBT, AccountType::CREDITCARD, AccountType::LOAN];
+ $types = [AccountType::ASSET, AccountType::DEFAULT, AccountType::MORTGAGE, AccountType::DEBT, AccountType::LOAN];
$grouped = $this->getAccountsGrouped($types);
return $this->select($name, $grouped, $value, $options);
diff --git a/app/Support/Form/FormSupport.php b/app/Support/Form/FormSupport.php
index f91931cd60..09c8de4910 100644
--- a/app/Support/Form/FormSupport.php
+++ b/app/Support/Form/FormSupport.php
@@ -56,6 +56,25 @@ trait FormSupport
return $html;
}
+ public function multiSelect(string $name, ?array $list = null, $selected = null, ?array $options = null): string
+ {
+ $list ??= [];
+ $label = $this->label($name, $options);
+ $options = $this->expandOptionArray($name, $label, $options);
+ $classes = $this->getHolderClasses($name);
+ $selected = $this->fillFieldValue($name, $selected);
+ unset($options['autocomplete'], $options['placeholder']);
+
+ try {
+ $html = view('form.multi-select', compact('classes', 'name', 'label', 'selected', 'options', 'list'))->render();
+ } catch (\Throwable $e) {
+ app('log')->debug(sprintf('Could not render multi-select(): %s', $e->getMessage()));
+ $html = 'Could not render multi-select.';
+ }
+
+ return $html;
+ }
+
protected function label(string $name, ?array $options = null): string
{
$options ??= [];
diff --git a/config/twigbridge.php b/config/twigbridge.php
index da8d491d82..60d1e1023d 100644
--- a/config/twigbridge.php
+++ b/config/twigbridge.php
@@ -197,6 +197,7 @@ return [
'assetAccountCheckList',
'assetAccountList',
'longAccountList',
+ 'assetLiabilityMultiAccountList',
],
],
'CurrencyForm' => [
diff --git a/resources/lang/en_US/firefly.php b/resources/lang/en_US/firefly.php
index aa395cd3da..1f6c37af8e 100644
--- a/resources/lang/en_US/firefly.php
+++ b/resources/lang/en_US/firefly.php
@@ -2197,6 +2197,7 @@ return [
'amount' => 'Amount',
'overview' => 'Overview',
'saveOnAccount' => 'Save on account',
+ 'saveOnAccounts' => 'Save on account(s)',
'unknown' => 'Unknown',
'monthly' => 'Monthly',
'profile' => 'Profile',
diff --git a/resources/lang/en_US/form.php b/resources/lang/en_US/form.php
index 5e6ab8d583..a83bbd764e 100644
--- a/resources/lang/en_US/form.php
+++ b/resources/lang/en_US/form.php
@@ -69,6 +69,7 @@ return [
// Ignore this comment
'targetamount' => 'Target amount',
+ 'target_amount' => 'Target amount',
'account_role' => 'Account role',
'opening_balance_date' => 'Opening balance date',
'cc_type' => 'Credit card payment plan',
@@ -106,7 +107,9 @@ return [
'deletePermanently' => 'Delete permanently',
'cancel' => 'Cancel',
'targetdate' => 'Target date',
+ 'target_date' => 'Target date',
'startdate' => 'Start date',
+ 'start_date' => 'Start date',
'tag' => 'Tag',
'under' => 'Under',
'symbol' => 'Symbol',
@@ -116,7 +119,6 @@ return [
'creditCardNumber' => 'Credit card number',
'has_headers' => 'Headers',
'date_format' => 'Date format',
- 'specifix' => 'Bank- or file specific fixes',
'attachments[]' => 'Attachments',
'title' => 'Title',
'notes' => 'Notes',
@@ -125,8 +127,7 @@ return [
'size' => 'Size',
'trigger' => 'Trigger',
'stop_processing' => 'Stop processing',
- 'start_date' => 'Start of range',
- 'end_date' => 'End of range',
+ 'end_date' => 'End date',
'enddate' => 'End date',
'move_rules_before_delete' => 'Rule group',
'start' => 'Start of range',
diff --git a/resources/lang/en_US/validation.php b/resources/lang/en_US/validation.php
index 9f6dc2fe54..587db8cb29 100644
--- a/resources/lang/en_US/validation.php
+++ b/resources/lang/en_US/validation.php
@@ -26,6 +26,8 @@ declare(strict_types=1);
return [
'invalid_account_type' => 'A piggy bank can only be linked to asset accounts and liabilities',
+ 'invalid_account_currency' => 'This account does not use the currency you have selected',
+ 'current_amount_too_much' => 'The combined amount in "current_amount" cannot exceed the "target_amount".',
'filter_must_be_in' => 'Filter ":filter" must be one of: :values',
'filter_not_string' => 'Filter ":filter" is expected to be a string of text',
'bad_api_filter' => 'This API endpoint does not support ":filter" as a filter.',
diff --git a/resources/views/form/multi-select.twig b/resources/views/form/multi-select.twig
new file mode 100644
index 0000000000..b27359e41e
--- /dev/null
+++ b/resources/views/form/multi-select.twig
@@ -0,0 +1,10 @@
+
+
+
+
+ {{ Html.select(name~"[]", list, selected).id(options.id).class('form-control').attribute('multiple').attribute('autocomplete','off').attribute('spellcheck','false').attribute('placeholder', options.placeholder) }}
+ {% include 'form.help' %}
+ {% include 'form.feedback' %}
+
+
+
diff --git a/resources/views/piggy-banks/create.twig b/resources/views/piggy-banks/create.twig
index f25dd211a8..84662207a4 100644
--- a/resources/views/piggy-banks/create.twig
+++ b/resources/views/piggy-banks/create.twig
@@ -8,7 +8,6 @@
- {{ __('firefly.bills_to_pay') }}
+ {{ __('firefly.bills_to_pay') }}
TODO No subscriptions are waiting to be paid
From 7c8445707e79e040d48523117ddac018e30a24c3 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Thu, 26 Dec 2024 14:12:05 +0100
Subject: [PATCH 116/167] Add moar debug.
---
app/Http/Controllers/Chart/AccountController.php | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/app/Http/Controllers/Chart/AccountController.php b/app/Http/Controllers/Chart/AccountController.php
index d4f95e0334..f2a3c6ea23 100644
--- a/app/Http/Controllers/Chart/AccountController.php
+++ b/app/Http/Controllers/Chart/AccountController.php
@@ -417,7 +417,7 @@ class AccountController extends Controller
*/
public function period(Account $account, Carbon $start, Carbon $end): JsonResponse
{
- Log::debug('Now in period()');
+ Log::debug(sprintf('Now in period("%s", "%s")', $start->format('Y-m-d'), $end->format('Y-m-d')));
$chartData = [];
$cache = new CacheProperties();
$cache->addProperty('chart.account.period');
From a3ff73903aceb9d4e9a96fe5d3f8f408faadbb83 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Fri, 27 Dec 2024 05:44:03 +0100
Subject: [PATCH 117/167] Fix bad error message.
---
app/Jobs/DownloadExchangeRates.php | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/app/Jobs/DownloadExchangeRates.php b/app/Jobs/DownloadExchangeRates.php
index 17bf251f1d..5ba8d7f998 100644
--- a/app/Jobs/DownloadExchangeRates.php
+++ b/app/Jobs/DownloadExchangeRates.php
@@ -102,7 +102,7 @@ class DownloadExchangeRates implements ShouldQueue
try {
$res = $client->get($url);
} catch (ConnectException|RequestException $e) {
- app('log')->warning(sprintf('Trying to grab "%s" resulted in error "%d".', $url, $e->getMessage()));
+ app('log')->warning(sprintf('Trying to grab "%s" resulted in error "%s".', $url, $e->getMessage()));
return;
}
From 2314ce800484908c4691f212b04b971806c5657a Mon Sep 17 00:00:00 2001
From: James Cole
Date: Fri, 27 Dec 2024 06:48:58 +0100
Subject: [PATCH 118/167] Refactor and renam commands.
---
.../ConvertsDatesToUTC.php} | 23 +++++++-
.../Commands/Correction/CorrectDatabase.php | 10 +++-
.../CorrectsGroupInformation.php} | 8 +--
.../CorrectsTimezoneInformation.php} | 21 ++++++-
.../CreatesGroupMemberships.php} | 8 +--
.../RestoresOAuthKeys.php} | 10 ++--
...ptyObjects.php => ReportsEmptyObjects.php} | 4 +-
...portIntegrity.php => ReportsIntegrity.php} | 10 ++--
.../{ReportSum.php => ReportsSums.php} | 5 +-
...ier.php => AddsTransactionIdentifiers.php} | 4 +-
...base.php => RemovesDatabaseDecryption.php} | 7 +--
...Balance.php => RepairsAccountBalances.php} | 7 +--
...ences.php => RepairsPostgresSequences.php} | 7 +--
...ions.php => UpgradeTransferCurrencies.php} | 6 +-
...cies.php => UpgradesAccountCurrencies.php} | 4 +-
...ntMeta.php => UpgradesAccountMetaData.php} | 7 +--
...ttachments.php => UpgradesAttachments.php} | 4 +-
...teToRules.php => UpgradesBillsToRules.php} | 7 +--
...ods.php => UpgradesBudgetLimitPeriods.php} | 7 +--
...tCurrency.php => UpgradesBudgetLimits.php} | 7 +--
....php => UpgradesCreditCardLiabilities.php} | 7 +--
...es.php => UpgradesCurrencyPreferences.php} | 6 +-
...gradeDatabase.php => UpgradesDatabase.php} | 56 ++++++++-----------
...urnals.php => UpgradesJournalMetaData.php} | 9 +--
...rnalNotes.php => UpgradesJournalNotes.php} | 7 +--
...iabilities.php => UpgradesLiabilities.php} | 7 +--
...Eight.php => UpgradesLiabilitiesEight.php} | 30 +---------
...yBanks.php => UpgradesMultiPiggyBanks.php} | 6 +-
...eta.php => UpgradesRecurrenceMetaData.php} | 4 +-
...nceType.php => UpgradesRecurrenceType.php} | 4 +-
...uleActions.php => UpgradesRuleActions.php} | 4 +-
...Locations.php => UpgradesTagLocations.php} | 4 +-
...grateToGroups.php => UpgradesToGroups.php} | 11 +---
...=> UpgradesVariousCurrencyInformation.php} | 8 +--
.../Authentication/RemoteUserProvider.php | 2 +-
resources/lang/en_US/firefly.php | 1 +
resources/views/currencies/index.twig | 5 +-
37 files changed, 153 insertions(+), 184 deletions(-)
rename app/Console/Commands/{Integrity/ConvertDatesToUTC.php => Correction/ConvertsDatesToUTC.php} (79%)
rename app/Console/Commands/{Integrity/UpdateGroupInformation.php => Correction/CorrectsGroupInformation.php} (95%)
rename app/Console/Commands/{Integrity/AddTimezonesToDates.php => Correction/CorrectsTimezoneInformation.php} (82%)
rename app/Console/Commands/{Integrity/CreateGroupMemberships.php => Correction/CreatesGroupMemberships.php} (94%)
rename app/Console/Commands/{Integrity/RestoreOAuthKeys.php => Correction/RestoresOAuthKeys.php} (93%)
rename app/Console/Commands/Integrity/{ReportEmptyObjects.php => ReportsEmptyObjects.php} (98%)
rename app/Console/Commands/Integrity/{ReportIntegrity.php => ReportsIntegrity.php} (85%)
rename app/Console/Commands/Integrity/{ReportSum.php => ReportsSums.php} (96%)
rename app/Console/Commands/Upgrade/{TransactionIdentifier.php => AddsTransactionIdentifiers.php} (98%)
rename app/Console/Commands/Upgrade/{DecryptDatabase.php => RemovesDatabaseDecryption.php} (97%)
rename app/Console/Commands/Upgrade/{CorrectAccountBalance.php => RepairsAccountBalances.php} (91%)
rename app/Console/Commands/Upgrade/{FixPostgresSequences.php => RepairsPostgresSequences.php} (96%)
rename app/Console/Commands/Upgrade/{TransferCurrenciesCorrections.php => UpgradeTransferCurrencies.php} (99%)
rename app/Console/Commands/Upgrade/{AccountCurrencies.php => UpgradesAccountCurrencies.php} (98%)
rename app/Console/Commands/Upgrade/{RenameAccountMeta.php => UpgradesAccountMetaData.php} (93%)
rename app/Console/Commands/Upgrade/{MigrateAttachments.php => UpgradesAttachments.php} (95%)
rename app/Console/Commands/Upgrade/{MigrateToRules.php => UpgradesBillsToRules.php} (98%)
rename app/Console/Commands/Upgrade/{AppendBudgetLimitPeriods.php => UpgradesBudgetLimitPeriods.php} (96%)
rename app/Console/Commands/Upgrade/{BudgetLimitCurrency.php => UpgradesBudgetLimits.php} (94%)
rename app/Console/Commands/Upgrade/{CCLiabilities.php => UpgradesCreditCardLiabilities.php} (96%)
rename app/Console/Commands/Upgrade/{UpgradeCurrencyPreferences.php => UpgradesCurrencyPreferences.php} (95%)
rename app/Console/Commands/Upgrade/{UpgradeDatabase.php => UpgradesDatabase.php} (59%)
rename app/Console/Commands/Upgrade/{BackToJournals.php => UpgradesJournalMetaData.php} (96%)
rename app/Console/Commands/Upgrade/{MigrateJournalNotes.php => UpgradesJournalNotes.php} (93%)
rename app/Console/Commands/Upgrade/{UpgradeLiabilities.php => UpgradesLiabilities.php} (96%)
rename app/Console/Commands/Upgrade/{UpgradeLiabilitiesEight.php => UpgradesLiabilitiesEight.php} (85%)
rename app/Console/Commands/Upgrade/{UpgradeMultiPiggyBanks.php => UpgradesMultiPiggyBanks.php} (93%)
rename app/Console/Commands/Upgrade/{MigrateRecurrenceMeta.php => UpgradesRecurrenceMetaData.php} (95%)
rename app/Console/Commands/Upgrade/{MigrateRecurrenceType.php => UpgradesRecurrenceType.php} (91%)
rename app/Console/Commands/Upgrade/{MigrateRuleActions.php => UpgradesRuleActions.php} (97%)
rename app/Console/Commands/Upgrade/{MigrateTagLocations.php => UpgradesTagLocations.php} (94%)
rename app/Console/Commands/Upgrade/{MigrateToGroups.php => UpgradesToGroups.php} (98%)
rename app/Console/Commands/Upgrade/{OtherCurrenciesCorrections.php => UpgradesVariousCurrencyInformation.php} (97%)
diff --git a/app/Console/Commands/Integrity/ConvertDatesToUTC.php b/app/Console/Commands/Correction/ConvertsDatesToUTC.php
similarity index 79%
rename from app/Console/Commands/Integrity/ConvertDatesToUTC.php
rename to app/Console/Commands/Correction/ConvertsDatesToUTC.php
index 454ee8a033..d2a59c8666 100644
--- a/app/Console/Commands/Integrity/ConvertDatesToUTC.php
+++ b/app/Console/Commands/Correction/ConvertsDatesToUTC.php
@@ -1,4 +1,23 @@
friendlyWarning('Please do not use this command.');
+ return 0;
/**
* @var string $model
* @var array $fields
diff --git a/app/Console/Commands/Correction/CorrectDatabase.php b/app/Console/Commands/Correction/CorrectDatabase.php
index d3eadc0ee7..a0bc6607a3 100644
--- a/app/Console/Commands/Correction/CorrectDatabase.php
+++ b/app/Console/Commands/Correction/CorrectDatabase.php
@@ -34,7 +34,7 @@ class CorrectDatabase extends Command
{
use ShowsFriendlyMessages;
- protected $description = 'Will correct the integrity of your database, if necessary.';
+ protected $description = 'Will validate and correct the integrity of your database, if necessary.';
protected $signature = 'firefly-iii:correct-database';
/**
@@ -49,6 +49,14 @@ class CorrectDatabase extends Command
return 1;
}
$commands = [
+
+ // also just in case, some integrity commands:
+ // 'upgrade:restore-oauth-keys',
+ // 'upgrade:add-timezones-to-dates',
+ // 'upgrade:create-group-memberships',
+ // 'upgrade:upgrade-group-information',
+ // 'upgrade:610-currency-preferences',
+ // 'upgrade:620-piggy-banks',
'firefly-iii:fix-piggies',
'firefly-iii:create-link-types',
'firefly-iii:create-access-tokens',
diff --git a/app/Console/Commands/Integrity/UpdateGroupInformation.php b/app/Console/Commands/Correction/CorrectsGroupInformation.php
similarity index 95%
rename from app/Console/Commands/Integrity/UpdateGroupInformation.php
rename to app/Console/Commands/Correction/CorrectsGroupInformation.php
index 3be6c7ee0d..acdb3b4338 100644
--- a/app/Console/Commands/Integrity/UpdateGroupInformation.php
+++ b/app/Console/Commands/Correction/CorrectsGroupInformation.php
@@ -1,8 +1,8 @@
.
+ * along with this program. If not, see https://www.gnu.org/licenses/.
*/
declare(strict_types=1);
-namespace FireflyIII\Console\Commands\Integrity;
+namespace FireflyIII\Console\Commands\Correction;
use FireflyIII\Console\Commands\ShowsFriendlyMessages;
use FireflyIII\Models\Account;
diff --git a/app/Console/Commands/Integrity/AddTimezonesToDates.php b/app/Console/Commands/Correction/CorrectsTimezoneInformation.php
similarity index 82%
rename from app/Console/Commands/Integrity/AddTimezonesToDates.php
rename to app/Console/Commands/Correction/CorrectsTimezoneInformation.php
index cc8be30011..d17451e89a 100644
--- a/app/Console/Commands/Integrity/AddTimezonesToDates.php
+++ b/app/Console/Commands/Correction/CorrectsTimezoneInformation.php
@@ -1,4 +1,23 @@
.
+ * along with this program. If not, see https://www.gnu.org/licenses/.
*/
declare(strict_types=1);
-namespace FireflyIII\Console\Commands\Integrity;
+namespace FireflyIII\Console\Commands\Correction;
use FireflyIII\Console\Commands\ShowsFriendlyMessages;
use FireflyIII\Enums\UserRoleEnum;
diff --git a/app/Console/Commands/Integrity/RestoreOAuthKeys.php b/app/Console/Commands/Correction/RestoresOAuthKeys.php
similarity index 93%
rename from app/Console/Commands/Integrity/RestoreOAuthKeys.php
rename to app/Console/Commands/Correction/RestoresOAuthKeys.php
index b84a7eec14..d216702818 100644
--- a/app/Console/Commands/Integrity/RestoreOAuthKeys.php
+++ b/app/Console/Commands/Correction/RestoresOAuthKeys.php
@@ -1,8 +1,8 @@
.
+ * along with this program. If not, see https://www.gnu.org/licenses/.
*/
declare(strict_types=1);
-namespace FireflyIII\Console\Commands\Integrity;
+namespace FireflyIII\Console\Commands\Correction;
use FireflyIII\Console\Commands\ShowsFriendlyMessages;
use FireflyIII\Support\System\OAuthKeys;
diff --git a/app/Console/Commands/Integrity/ReportEmptyObjects.php b/app/Console/Commands/Integrity/ReportsEmptyObjects.php
similarity index 98%
rename from app/Console/Commands/Integrity/ReportEmptyObjects.php
rename to app/Console/Commands/Integrity/ReportsEmptyObjects.php
index 811398d673..882df65b5d 100644
--- a/app/Console/Commands/Integrity/ReportEmptyObjects.php
+++ b/app/Console/Commands/Integrity/ReportsEmptyObjects.php
@@ -34,13 +34,13 @@ use Illuminate\Console\Command;
/**
* Class ReportEmptyObjects
*/
-class ReportEmptyObjects extends Command
+class ReportsEmptyObjects extends Command
{
use ShowsFriendlyMessages;
protected $description = 'Reports on empty database objects.';
- protected $signature = 'firefly-iii:report-empty-objects';
+ protected $signature = 'integrity:empty-objects';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Integrity/ReportIntegrity.php b/app/Console/Commands/Integrity/ReportsIntegrity.php
similarity index 85%
rename from app/Console/Commands/Integrity/ReportIntegrity.php
rename to app/Console/Commands/Integrity/ReportsIntegrity.php
index 3dc698a2d3..59405ecef6 100644
--- a/app/Console/Commands/Integrity/ReportIntegrity.php
+++ b/app/Console/Commands/Integrity/ReportsIntegrity.php
@@ -30,7 +30,7 @@ use Illuminate\Console\Command;
/**
* Class ReportIntegrity
*/
-class ReportIntegrity extends Command
+class ReportsIntegrity extends Command
{
use ShowsFriendlyMessages;
@@ -48,11 +48,9 @@ class ReportIntegrity extends Command
return 1;
}
$commands = [
- 'firefly-iii:add-timezones-to-dates',
- 'firefly-iii:create-group-memberships',
- 'firefly-iii:report-empty-objects',
- 'firefly-iii:report-sum',
- 'firefly-iii:upgrade-group-information',
+ //'firefly-iii:add-timezones-to-dates',
+ 'integrity:empty-objects',
+ 'integrity:total-sums',
];
foreach ($commands as $command) {
$this->friendlyLine(sprintf('Now executing %s', $command));
diff --git a/app/Console/Commands/Integrity/ReportSum.php b/app/Console/Commands/Integrity/ReportsSums.php
similarity index 96%
rename from app/Console/Commands/Integrity/ReportSum.php
rename to app/Console/Commands/Integrity/ReportsSums.php
index d348468aba..82c763093d 100644
--- a/app/Console/Commands/Integrity/ReportSum.php
+++ b/app/Console/Commands/Integrity/ReportsSums.php
@@ -32,12 +32,13 @@ use Illuminate\Console\Command;
/**
* Class ReportSkeleton
*/
-class ReportSum extends Command
+class ReportsSums extends Command
{
use ShowsFriendlyMessages;
protected $description = 'Report on the total sum of transactions. Must be 0.';
- protected $signature = 'firefly-iii:report-sum';
+ protected $signature = 'integrity:total-sums';
+
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/TransactionIdentifier.php b/app/Console/Commands/Upgrade/AddsTransactionIdentifiers.php
similarity index 98%
rename from app/Console/Commands/Upgrade/TransactionIdentifier.php
rename to app/Console/Commands/Upgrade/AddsTransactionIdentifiers.php
index da2848ef4f..0099b11e5d 100644
--- a/app/Console/Commands/Upgrade/TransactionIdentifier.php
+++ b/app/Console/Commands/Upgrade/AddsTransactionIdentifiers.php
@@ -35,13 +35,13 @@ use Illuminate\Database\QueryException;
/**
* Class TransactionIdentifier
*/
-class TransactionIdentifier extends Command
+class AddsTransactionIdentifiers extends Command
{
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '480_transaction_identifier';
protected $description = 'Fixes transaction identifiers.';
- protected $signature = 'firefly-iii:transaction-identifiers {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:480-transaction-identifiers {--F|force : Force the execution of this command.}';
private JournalCLIRepositoryInterface $cliRepository;
private int $count;
diff --git a/app/Console/Commands/Upgrade/DecryptDatabase.php b/app/Console/Commands/Upgrade/RemovesDatabaseDecryption.php
similarity index 97%
rename from app/Console/Commands/Upgrade/DecryptDatabase.php
rename to app/Console/Commands/Upgrade/RemovesDatabaseDecryption.php
index a7ec4f2efa..a8eab8c9a7 100644
--- a/app/Console/Commands/Upgrade/DecryptDatabase.php
+++ b/app/Console/Commands/Upgrade/RemovesDatabaseDecryption.php
@@ -30,15 +30,12 @@ use FireflyIII\Models\Preference;
use Illuminate\Console\Command;
use Illuminate\Contracts\Encryption\DecryptException;
-/**
- * Class DecryptDatabase
- */
-class DecryptDatabase extends Command
+class RemovesDatabaseDecryption extends Command
{
use ShowsFriendlyMessages;
protected $description = 'Decrypts the database.';
- protected $signature = 'firefly-iii:decrypt-all';
+ protected $signature = 'upgrade:480-decrypt-all';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/CorrectAccountBalance.php b/app/Console/Commands/Upgrade/RepairsAccountBalances.php
similarity index 91%
rename from app/Console/Commands/Upgrade/CorrectAccountBalance.php
rename to app/Console/Commands/Upgrade/RepairsAccountBalances.php
index a28ea60737..670b20995c 100644
--- a/app/Console/Commands/Upgrade/CorrectAccountBalance.php
+++ b/app/Console/Commands/Upgrade/RepairsAccountBalances.php
@@ -28,16 +28,13 @@ use FireflyIII\Console\Commands\ShowsFriendlyMessages;
use FireflyIII\Support\Models\AccountBalanceCalculator;
use Illuminate\Console\Command;
-/**
- * Class CorrectionSkeleton
- */
-class CorrectAccountBalance extends Command
+class RepairsAccountBalances extends Command
{
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '610_correct_balances';
protected $description = 'Recalculate all account balance amounts';
- protected $signature = 'firefly-iii:correct-account-balance {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:610-account-balances {--F|force : Force the execution of this command.}';
public function handle(): int
{
diff --git a/app/Console/Commands/Upgrade/FixPostgresSequences.php b/app/Console/Commands/Upgrade/RepairsPostgresSequences.php
similarity index 96%
rename from app/Console/Commands/Upgrade/FixPostgresSequences.php
rename to app/Console/Commands/Upgrade/RepairsPostgresSequences.php
index 01f667f490..7d64be8637 100644
--- a/app/Console/Commands/Upgrade/FixPostgresSequences.php
+++ b/app/Console/Commands/Upgrade/RepairsPostgresSequences.php
@@ -27,16 +27,13 @@ namespace FireflyIII\Console\Commands\Upgrade;
use FireflyIII\Console\Commands\ShowsFriendlyMessages;
use Illuminate\Console\Command;
-/**
- * Class FixPostgresSequences
- */
-class FixPostgresSequences extends Command
+class RepairsPostgresSequences extends Command
{
use ShowsFriendlyMessages;
protected $description = 'Fixes issues with PostgreSQL sequences.';
- protected $signature = 'firefly-iii:fix-pgsql-sequences';
+ protected $signature = 'upgrade:600-pgsql-sequences';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/TransferCurrenciesCorrections.php b/app/Console/Commands/Upgrade/UpgradeTransferCurrencies.php
similarity index 99%
rename from app/Console/Commands/Upgrade/TransferCurrenciesCorrections.php
rename to app/Console/Commands/Upgrade/UpgradeTransferCurrencies.php
index ea6e4cb8ca..4057a7f863 100644
--- a/app/Console/Commands/Upgrade/TransferCurrenciesCorrections.php
+++ b/app/Console/Commands/Upgrade/UpgradeTransferCurrencies.php
@@ -35,15 +35,15 @@ use FireflyIII\Repositories\Journal\JournalCLIRepositoryInterface;
use Illuminate\Console\Command;
/**
- * Class TransferCurrenciesCorrections
+ * Class UpgradeTransferCurrencies
*/
-class TransferCurrenciesCorrections extends Command
+class UpgradeTransferCurrencies extends Command
{
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '480_transfer_currencies';
protected $description = 'Updates transfer currency information.';
- protected $signature = 'firefly-iii:transfer-currencies {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:480-transfer-currencies {--F|force : Force the execution of this command.}';
private array $accountCurrencies;
private AccountRepositoryInterface $accountRepos;
private JournalCLIRepositoryInterface $cliRepos;
diff --git a/app/Console/Commands/Upgrade/AccountCurrencies.php b/app/Console/Commands/Upgrade/UpgradesAccountCurrencies.php
similarity index 98%
rename from app/Console/Commands/Upgrade/AccountCurrencies.php
rename to app/Console/Commands/Upgrade/UpgradesAccountCurrencies.php
index bc4a0780c0..b50fa0c150 100644
--- a/app/Console/Commands/Upgrade/AccountCurrencies.php
+++ b/app/Console/Commands/Upgrade/UpgradesAccountCurrencies.php
@@ -39,14 +39,14 @@ use Illuminate\Console\Command;
/**
* Class AccountCurrencies
*/
-class AccountCurrencies extends Command
+class UpgradesAccountCurrencies extends Command
{
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '480_account_currencies';
protected $description = 'Give all accounts proper currency info.';
- protected $signature = 'firefly-iii:account-currencies {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:480-account-currencies {--F|force : Force the execution of this command.}';
private AccountRepositoryInterface $accountRepos;
private int $count;
private UserRepositoryInterface $userRepos;
diff --git a/app/Console/Commands/Upgrade/RenameAccountMeta.php b/app/Console/Commands/Upgrade/UpgradesAccountMetaData.php
similarity index 93%
rename from app/Console/Commands/Upgrade/RenameAccountMeta.php
rename to app/Console/Commands/Upgrade/UpgradesAccountMetaData.php
index aba059a38c..8ccbfd63de 100644
--- a/app/Console/Commands/Upgrade/RenameAccountMeta.php
+++ b/app/Console/Commands/Upgrade/UpgradesAccountMetaData.php
@@ -29,10 +29,7 @@ use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Models\AccountMeta;
use Illuminate\Console\Command;
-/**
- * Class RenameAccountMeta
- */
-class RenameAccountMeta extends Command
+class UpgradesAccountMetaData extends Command
{
use ShowsFriendlyMessages;
@@ -40,7 +37,7 @@ class RenameAccountMeta extends Command
protected $description = 'Rename account meta-data to new format.';
- protected $signature = 'firefly-iii:rename-account-meta {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:480-account-meta {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/MigrateAttachments.php b/app/Console/Commands/Upgrade/UpgradesAttachments.php
similarity index 95%
rename from app/Console/Commands/Upgrade/MigrateAttachments.php
rename to app/Console/Commands/Upgrade/UpgradesAttachments.php
index cb517059fc..aa2e310733 100644
--- a/app/Console/Commands/Upgrade/MigrateAttachments.php
+++ b/app/Console/Commands/Upgrade/UpgradesAttachments.php
@@ -33,7 +33,7 @@ use Illuminate\Console\Command;
/**
* Class MigrateAttachments
*/
-class MigrateAttachments extends Command
+class UpgradesAttachments extends Command
{
use ShowsFriendlyMessages;
@@ -41,7 +41,7 @@ class MigrateAttachments extends Command
protected $description = 'Migrates attachment meta-data.';
- protected $signature = 'firefly-iii:migrate-attachments {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:480-attachments {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/MigrateToRules.php b/app/Console/Commands/Upgrade/UpgradesBillsToRules.php
similarity index 98%
rename from app/Console/Commands/Upgrade/MigrateToRules.php
rename to app/Console/Commands/Upgrade/UpgradesBillsToRules.php
index d2fed1a94d..de70c8e761 100644
--- a/app/Console/Commands/Upgrade/MigrateToRules.php
+++ b/app/Console/Commands/Upgrade/UpgradesBillsToRules.php
@@ -36,10 +36,7 @@ use FireflyIII\Repositories\User\UserRepositoryInterface;
use FireflyIII\User;
use Illuminate\Console\Command;
-/**
- * Class MigrateToRules
- */
-class MigrateToRules extends Command
+class UpgradesBillsToRules extends Command
{
use ShowsFriendlyMessages;
@@ -47,7 +44,7 @@ class MigrateToRules extends Command
protected $description = 'Migrate bills to rules.';
- protected $signature = 'firefly-iii:bills-to-rules {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:480-bills-to-rules {--F|force : Force the execution of this command.}';
private BillRepositoryInterface $billRepository;
private int $count;
private RuleGroupRepositoryInterface $ruleGroupRepository;
diff --git a/app/Console/Commands/Upgrade/AppendBudgetLimitPeriods.php b/app/Console/Commands/Upgrade/UpgradesBudgetLimitPeriods.php
similarity index 96%
rename from app/Console/Commands/Upgrade/AppendBudgetLimitPeriods.php
rename to app/Console/Commands/Upgrade/UpgradesBudgetLimitPeriods.php
index 83a0d11548..a43f05682d 100644
--- a/app/Console/Commands/Upgrade/AppendBudgetLimitPeriods.php
+++ b/app/Console/Commands/Upgrade/UpgradesBudgetLimitPeriods.php
@@ -28,10 +28,7 @@ use FireflyIII\Console\Commands\ShowsFriendlyMessages;
use FireflyIII\Models\BudgetLimit;
use Illuminate\Console\Command;
-/**
- * Class AppendBudgetLimitPeriods
- */
-class AppendBudgetLimitPeriods extends Command
+class UpgradesBudgetLimitPeriods extends Command
{
use ShowsFriendlyMessages;
@@ -39,7 +36,7 @@ class AppendBudgetLimitPeriods extends Command
protected $description = 'Append budget limits with their (estimated) timeframe.';
- protected $signature = 'firefly-iii:budget-limit-periods {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:550-budget-limit-periods {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/BudgetLimitCurrency.php b/app/Console/Commands/Upgrade/UpgradesBudgetLimits.php
similarity index 94%
rename from app/Console/Commands/Upgrade/BudgetLimitCurrency.php
rename to app/Console/Commands/Upgrade/UpgradesBudgetLimits.php
index a00cf81e0d..98b4020d78 100644
--- a/app/Console/Commands/Upgrade/BudgetLimitCurrency.php
+++ b/app/Console/Commands/Upgrade/UpgradesBudgetLimits.php
@@ -31,10 +31,7 @@ use FireflyIII\Models\BudgetLimit;
use FireflyIII\User;
use Illuminate\Console\Command;
-/**
- * Class BudgetLimitCurrency
- */
-class BudgetLimitCurrency extends Command
+class UpgradesBudgetLimits extends Command
{
use ShowsFriendlyMessages;
@@ -42,7 +39,7 @@ class BudgetLimitCurrency extends Command
protected $description = 'Give budget limits a currency';
- protected $signature = 'firefly-iii:bl-currency {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:480-budget-limit-currencies {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/CCLiabilities.php b/app/Console/Commands/Upgrade/UpgradesCreditCardLiabilities.php
similarity index 96%
rename from app/Console/Commands/Upgrade/CCLiabilities.php
rename to app/Console/Commands/Upgrade/UpgradesCreditCardLiabilities.php
index f2211fb59a..33c8acfa90 100644
--- a/app/Console/Commands/Upgrade/CCLiabilities.php
+++ b/app/Console/Commands/Upgrade/UpgradesCreditCardLiabilities.php
@@ -31,16 +31,13 @@ use FireflyIII\Models\AccountType;
use Illuminate\Console\Command;
use Illuminate\Support\Collection;
-/**
- * Class CCLiabilities
- */
-class CCLiabilities extends Command
+class UpgradesCreditCardLiabilities extends Command
{
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '480_cc_liabilities';
protected $description = 'Convert old credit card liabilities.';
- protected $signature = 'firefly-iii:cc-liabilities {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:480-cc-liabilities {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/UpgradeCurrencyPreferences.php b/app/Console/Commands/Upgrade/UpgradesCurrencyPreferences.php
similarity index 95%
rename from app/Console/Commands/Upgrade/UpgradeCurrencyPreferences.php
rename to app/Console/Commands/Upgrade/UpgradesCurrencyPreferences.php
index 1e7cd051dc..927b9e1845 100644
--- a/app/Console/Commands/Upgrade/UpgradeCurrencyPreferences.php
+++ b/app/Console/Commands/Upgrade/UpgradesCurrencyPreferences.php
@@ -33,9 +33,9 @@ use Illuminate\Console\Command;
use Illuminate\Support\Collection;
/**
- * Class UpgradeCurrencyPreferences
+ * Class UpgradesCurrencyPreferences
*/
-class UpgradeCurrencyPreferences extends Command
+class UpgradesCurrencyPreferences extends Command
{
use ShowsFriendlyMessages;
@@ -43,7 +43,7 @@ class UpgradeCurrencyPreferences extends Command
protected $description = 'Upgrade user currency preferences';
- protected $signature = 'firefly-iii:upgrade-currency-preferences {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:610-currency-preferences {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/UpgradeDatabase.php b/app/Console/Commands/Upgrade/UpgradesDatabase.php
similarity index 59%
rename from app/Console/Commands/Upgrade/UpgradeDatabase.php
rename to app/Console/Commands/Upgrade/UpgradesDatabase.php
index 3b27f72ebd..10fdde02ea 100644
--- a/app/Console/Commands/Upgrade/UpgradeDatabase.php
+++ b/app/Console/Commands/Upgrade/UpgradesDatabase.php
@@ -29,10 +29,7 @@ set_time_limit(0);
use FireflyIII\Console\Commands\ShowsFriendlyMessages;
use Illuminate\Console\Command;
-/**
- * Class UpgradeDatabase
- */
-class UpgradeDatabase extends Command
+class UpgradesDatabase extends Command
{
use ShowsFriendlyMessages;
@@ -46,33 +43,26 @@ class UpgradeDatabase extends Command
{
$this->callInitialCommands();
$commands = [
- 'firefly-iii:transaction-identifiers',
- 'firefly-iii:migrate-to-groups',
- 'firefly-iii:account-currencies',
- 'firefly-iii:transfer-currencies',
- 'firefly-iii:other-currencies',
- 'firefly-iii:migrate-notes',
- 'firefly-iii:migrate-attachments',
- 'firefly-iii:bills-to-rules',
- 'firefly-iii:bl-currency',
- 'firefly-iii:cc-liabilities',
- 'firefly-iii:back-to-journals',
- 'firefly-iii:rename-account-meta',
- 'firefly-iii:migrate-recurrence-meta',
- 'firefly-iii:migrate-tag-locations',
- 'firefly-iii:migrate-recurrence-type',
- 'firefly-iii:upgrade-liabilities',
- 'firefly-iii:liabilities-600',
- 'firefly-iii:budget-limit-periods',
- 'firefly-iii:migrate-rule-actions',
- 'firefly-iii:restore-oauth-keys',
- 'firefly-iii:correct-account-balance',
- // also just in case, some integrity commands:
- 'firefly-iii:add-timezones-to-dates',
- 'firefly-iii:create-group-memberships',
- 'firefly-iii:upgrade-group-information',
- 'firefly-iii:upgrade-currency-preferences',
- 'firefly-iii:upgrade-multi-piggies',
+ 'upgrade:480-transaction-identifiers',
+ 'upgrade:480-migrate-to-groups',
+ 'upgrade:480-account-currencies',
+ 'upgrade:480-transfer-currencies',
+ 'upgrade:480-currency-information',
+ 'upgrade:480-notes',
+ 'upgrade:480-attachments',
+ 'upgrade:480-bills-to-rules',
+ 'upgrade:480-budget-limit-currencies',
+ 'upgrade:480-cc-liabilities',
+ 'upgrade:480-journal-meta-data',
+ 'upgrade:480-account-meta',
+ 'upgrade:481-recurrence-meta',
+ 'upgrade:500-tag-locations',
+ 'upgrade:550-recurrence-type',
+ 'upgrade:560-liabilities',
+ 'upgrade:600-liabilities',
+ 'upgrade:550-budget-limit-periods',
+ 'upgrade:600-rule-actions',
+ 'upgrade:610-account-balance',
'firefly-iii:correct-database',
];
$args = [];
@@ -94,7 +84,7 @@ class UpgradeDatabase extends Command
private function callInitialCommands(): void
{
$this->call('migrate', ['--seed' => true, '--force' => true, '--no-interaction' => true]);
- $this->call('firefly-iii:fix-pgsql-sequences');
- $this->call('firefly-iii:decrypt-all');
+ $this->call('upgrade:600-pgsql-sequences');
+ $this->call('upgrade:480-decrypt-all');
}
}
diff --git a/app/Console/Commands/Upgrade/BackToJournals.php b/app/Console/Commands/Upgrade/UpgradesJournalMetaData.php
similarity index 96%
rename from app/Console/Commands/Upgrade/BackToJournals.php
rename to app/Console/Commands/Upgrade/UpgradesJournalMetaData.php
index 31f72f2c74..325de12feb 100644
--- a/app/Console/Commands/Upgrade/BackToJournals.php
+++ b/app/Console/Commands/Upgrade/UpgradesJournalMetaData.php
@@ -32,10 +32,7 @@ use FireflyIII\Models\TransactionJournal;
use Illuminate\Console\Command;
use Illuminate\Support\Collection;
-/**
- * Class BackToJournals
- */
-class BackToJournals extends Command
+class UpgradesJournalMetaData extends Command
{
use ShowsFriendlyMessages;
@@ -43,7 +40,7 @@ class BackToJournals extends Command
protected $description = 'Move meta data back to journals, not individual transactions.';
- protected $signature = 'firefly-iii:back-to-journals {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:480-journal-meta-data {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
@@ -71,7 +68,7 @@ class BackToJournals extends Command
private function isMigrated(): bool
{
- $configVar = app('fireflyconfig')->get(MigrateToGroups::CONFIG_NAME, false);
+ $configVar = app('fireflyconfig')->get(self::CONFIG_NAME, false);
return (bool) $configVar->data;
}
diff --git a/app/Console/Commands/Upgrade/MigrateJournalNotes.php b/app/Console/Commands/Upgrade/UpgradesJournalNotes.php
similarity index 93%
rename from app/Console/Commands/Upgrade/MigrateJournalNotes.php
rename to app/Console/Commands/Upgrade/UpgradesJournalNotes.php
index 2434ba4d10..e638b4144b 100644
--- a/app/Console/Commands/Upgrade/MigrateJournalNotes.php
+++ b/app/Console/Commands/Upgrade/UpgradesJournalNotes.php
@@ -29,10 +29,7 @@ use FireflyIII\Models\Note;
use FireflyIII\Models\TransactionJournalMeta;
use Illuminate\Console\Command;
-/**
- * Class MigrateJournalNotes
- */
-class MigrateJournalNotes extends Command
+class UpgradesJournalNotes extends Command
{
use ShowsFriendlyMessages;
@@ -40,7 +37,7 @@ class MigrateJournalNotes extends Command
protected $description = 'Migrate notes for transaction journals.';
- protected $signature = 'firefly-iii:migrate-notes {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:480-notes {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/UpgradeLiabilities.php b/app/Console/Commands/Upgrade/UpgradesLiabilities.php
similarity index 96%
rename from app/Console/Commands/Upgrade/UpgradeLiabilities.php
rename to app/Console/Commands/Upgrade/UpgradesLiabilities.php
index 66902b171c..c75ccc6a99 100644
--- a/app/Console/Commands/Upgrade/UpgradeLiabilities.php
+++ b/app/Console/Commands/Upgrade/UpgradesLiabilities.php
@@ -34,16 +34,13 @@ use FireflyIII\Services\Internal\Support\CreditRecalculateService;
use FireflyIII\User;
use Illuminate\Console\Command;
-/**
- * Class UpgradeLiabilities
- */
-class UpgradeLiabilities extends Command
+class UpgradesLiabilities extends Command
{
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '560_upgrade_liabilities';
protected $description = 'Upgrade liabilities to new 5.6.0 structure.';
- protected $signature = 'firefly-iii:upgrade-liabilities {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:560-liabilities {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/UpgradeLiabilitiesEight.php b/app/Console/Commands/Upgrade/UpgradesLiabilitiesEight.php
similarity index 85%
rename from app/Console/Commands/Upgrade/UpgradeLiabilitiesEight.php
rename to app/Console/Commands/Upgrade/UpgradesLiabilitiesEight.php
index 1422e77363..a28fb86324 100644
--- a/app/Console/Commands/Upgrade/UpgradeLiabilitiesEight.php
+++ b/app/Console/Commands/Upgrade/UpgradesLiabilitiesEight.php
@@ -35,16 +35,13 @@ use FireflyIII\Services\Internal\Support\CreditRecalculateService;
use FireflyIII\User;
use Illuminate\Console\Command;
-/**
- * Class UpgradeLiabilitiesEight
- */
-class UpgradeLiabilitiesEight extends Command
+class UpgradesLiabilitiesEight extends Command
{
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '600_upgrade_liabilities';
protected $description = 'Upgrade liabilities to new 6.0.0 structure.';
- protected $signature = 'firefly-iii:liabilities-600 {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:600-liabilities {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
@@ -201,32 +198,9 @@ class UpgradeLiabilitiesEight extends Command
/** @var TransactionJournal $journal */
foreach ($journals as $journal) {
- // $delete = false;
- // /** @var Transaction $source */
- // $source = $journal->transactions()->where('amount', '<', 0)->first();
- // /** @var Transaction $dest */
- // $dest = $journal->transactions()->where('amount', '>', 0)->first();
-
- /**
- * // if source is this liability and destination is expense, remove transaction.
- * // if source is revenue and destination is liability, remove transaction.
- * if ($source->account_id === $account->id && $dest->account->accountType->type === AccountType::EXPENSE) {
- * $delete = true;
- * }
- * if ($dest->account_id === $account->id && $source->account->accountType->type === AccountType::REVENUE) {
- * $delete = true;
- * }
- *
- * // overruled. No transaction will be deleted, ever.
- * // code is kept in place, so I can revisit my reasoning.
- * $delete = false;
- */
-
- // if ($delete) {
$service = app(TransactionGroupDestroyService::class);
$service->destroy($journal->transactionGroup);
++$count;
- // }
}
return $count;
diff --git a/app/Console/Commands/Upgrade/UpgradeMultiPiggyBanks.php b/app/Console/Commands/Upgrade/UpgradesMultiPiggyBanks.php
similarity index 93%
rename from app/Console/Commands/Upgrade/UpgradeMultiPiggyBanks.php
rename to app/Console/Commands/Upgrade/UpgradesMultiPiggyBanks.php
index 6914bc0919..9284ca913a 100644
--- a/app/Console/Commands/Upgrade/UpgradeMultiPiggyBanks.php
+++ b/app/Console/Commands/Upgrade/UpgradesMultiPiggyBanks.php
@@ -30,15 +30,15 @@ use FireflyIII\Repositories\PiggyBank\PiggyBankRepositoryInterface;
use Illuminate\Console\Command;
use Illuminate\Support\Facades\Log;
-class UpgradeMultiPiggyBanks extends Command
+class UpgradesMultiPiggyBanks extends Command
{
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '620_make_multi_piggies';
- protected $description = 'Upgrade piggybanks so they can use multiple accounts.';
+ protected $description = 'Upgrade piggy banks so they can use multiple accounts.';
- protected $signature = 'firefly-iii:upgrade-multi-piggies {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:620-piggy-banks {--F|force : Force the execution of this command.}';
private AccountRepositoryInterface $accountRepository;
private PiggyBankRepositoryInterface $repository;
diff --git a/app/Console/Commands/Upgrade/MigrateRecurrenceMeta.php b/app/Console/Commands/Upgrade/UpgradesRecurrenceMetaData.php
similarity index 95%
rename from app/Console/Commands/Upgrade/MigrateRecurrenceMeta.php
rename to app/Console/Commands/Upgrade/UpgradesRecurrenceMetaData.php
index 5b79a96f3c..e2e04cf3cd 100644
--- a/app/Console/Commands/Upgrade/MigrateRecurrenceMeta.php
+++ b/app/Console/Commands/Upgrade/UpgradesRecurrenceMetaData.php
@@ -33,7 +33,7 @@ use Illuminate\Console\Command;
/**
* Class MigrateRecurrenceMeta
*/
-class MigrateRecurrenceMeta extends Command
+class UpgradesRecurrenceMetaData extends Command
{
use ShowsFriendlyMessages;
@@ -41,7 +41,7 @@ class MigrateRecurrenceMeta extends Command
protected $description = 'Migrate recurrence meta data';
- protected $signature = 'firefly-iii:migrate-recurrence-meta {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:481-recurrence-meta {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/MigrateRecurrenceType.php b/app/Console/Commands/Upgrade/UpgradesRecurrenceType.php
similarity index 91%
rename from app/Console/Commands/Upgrade/MigrateRecurrenceType.php
rename to app/Console/Commands/Upgrade/UpgradesRecurrenceType.php
index d8cf398141..802e303f94 100644
--- a/app/Console/Commands/Upgrade/MigrateRecurrenceType.php
+++ b/app/Console/Commands/Upgrade/UpgradesRecurrenceType.php
@@ -30,7 +30,7 @@ use Illuminate\Console\Command;
/**
* Class MigrateRecurrenceType
*/
-class MigrateRecurrenceType extends Command
+class UpgradesRecurrenceType extends Command
{
use ShowsFriendlyMessages;
@@ -38,7 +38,7 @@ class MigrateRecurrenceType extends Command
protected $description = 'Migrate transaction type of recurring transaction.';
- protected $signature = 'firefly-iii:migrate-recurrence-type {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:550-recurrence-type {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/MigrateRuleActions.php b/app/Console/Commands/Upgrade/UpgradesRuleActions.php
similarity index 97%
rename from app/Console/Commands/Upgrade/MigrateRuleActions.php
rename to app/Console/Commands/Upgrade/UpgradesRuleActions.php
index f0c825b40f..c6341238ae 100644
--- a/app/Console/Commands/Upgrade/MigrateRuleActions.php
+++ b/app/Console/Commands/Upgrade/UpgradesRuleActions.php
@@ -27,7 +27,7 @@ use FireflyIII\Console\Commands\ShowsFriendlyMessages;
use FireflyIII\Models\RuleAction;
use Illuminate\Console\Command;
-class MigrateRuleActions extends Command
+class UpgradesRuleActions extends Command
{
use ShowsFriendlyMessages;
@@ -35,7 +35,7 @@ class MigrateRuleActions extends Command
protected $description = 'Migrate rule actions away from expression engine';
- protected $signature = 'firefly-iii:migrate-rule-actions {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:600-rule-actions {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/MigrateTagLocations.php b/app/Console/Commands/Upgrade/UpgradesTagLocations.php
similarity index 94%
rename from app/Console/Commands/Upgrade/MigrateTagLocations.php
rename to app/Console/Commands/Upgrade/UpgradesTagLocations.php
index 7284622067..d0a297c20c 100644
--- a/app/Console/Commands/Upgrade/MigrateTagLocations.php
+++ b/app/Console/Commands/Upgrade/UpgradesTagLocations.php
@@ -32,7 +32,7 @@ use Illuminate\Console\Command;
/**
* Class MigrateTagLocations
*/
-class MigrateTagLocations extends Command
+class UpgradesTagLocations extends Command
{
use ShowsFriendlyMessages;
@@ -40,7 +40,7 @@ class MigrateTagLocations extends Command
protected $description = 'Migrate tag locations.';
- protected $signature = 'firefly-iii:migrate-tag-locations {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:500-tag-locations {--F|force : Force the execution of this command.}';
/**
* Execute the console command.
diff --git a/app/Console/Commands/Upgrade/MigrateToGroups.php b/app/Console/Commands/Upgrade/UpgradesToGroups.php
similarity index 98%
rename from app/Console/Commands/Upgrade/MigrateToGroups.php
rename to app/Console/Commands/Upgrade/UpgradesToGroups.php
index c9b475217a..c0c7cf3e10 100644
--- a/app/Console/Commands/Upgrade/MigrateToGroups.php
+++ b/app/Console/Commands/Upgrade/UpgradesToGroups.php
@@ -36,20 +36,13 @@ use FireflyIII\Services\Internal\Destroy\JournalDestroyService;
use Illuminate\Console\Command;
use Illuminate\Support\Collection;
-/**
- * This command will take split transactions and migrate them to "transaction groups".
- *
- * It will only run once, but can be forced to run again.
- *
- * Class MigrateToGroups
- */
-class MigrateToGroups extends Command
+class UpgradesToGroups extends Command
{
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '480_migrated_to_groups';
protected $description = 'Migrates a pre-4.7.8 transaction structure to the 4.7.8+ transaction structure.';
- protected $signature = 'firefly-iii:migrate-to-groups {--F|force : Force the migration, even if it fired before.}';
+ protected $signature = 'upgrade:480-migrate-to-groups {--F|force : Force the migration, even if it fired before.}';
private JournalCLIRepositoryInterface $cliRepository;
private int $count;
private TransactionGroupFactory $groupFactory;
diff --git a/app/Console/Commands/Upgrade/OtherCurrenciesCorrections.php b/app/Console/Commands/Upgrade/UpgradesVariousCurrencyInformation.php
similarity index 97%
rename from app/Console/Commands/Upgrade/OtherCurrenciesCorrections.php
rename to app/Console/Commands/Upgrade/UpgradesVariousCurrencyInformation.php
index 0f4a601054..4e7398915f 100644
--- a/app/Console/Commands/Upgrade/OtherCurrenciesCorrections.php
+++ b/app/Console/Commands/Upgrade/UpgradesVariousCurrencyInformation.php
@@ -36,16 +36,14 @@ use FireflyIII\Repositories\Journal\JournalCLIRepositoryInterface;
use FireflyIII\Repositories\Journal\JournalRepositoryInterface;
use Illuminate\Console\Command;
-/**
- * Class OtherCurrenciesCorrections
- */
-class OtherCurrenciesCorrections extends Command
+
+class UpgradesVariousCurrencyInformation extends Command
{
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '480_other_currencies';
protected $description = 'Update all journal currency information.';
- protected $signature = 'firefly-iii:other-currencies {--F|force : Force the execution of this command.}';
+ protected $signature = 'upgrade:480-currency-information {--F|force : Force the execution of this command.}';
private array $accountCurrencies;
private AccountRepositoryInterface $accountRepos;
private JournalCLIRepositoryInterface $cliRepos;
diff --git a/app/Support/Authentication/RemoteUserProvider.php b/app/Support/Authentication/RemoteUserProvider.php
index a218dd5bfe..548b6bab15 100644
--- a/app/Support/Authentication/RemoteUserProvider.php
+++ b/app/Support/Authentication/RemoteUserProvider.php
@@ -24,7 +24,7 @@ declare(strict_types=1);
namespace FireflyIII\Support\Authentication;
-use FireflyIII\Console\Commands\Integrity\CreateGroupMemberships;
+use FireflyIII\Console\Commands\Correction\CreateGroupMemberships;
use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Models\Role;
use FireflyIII\User;
diff --git a/resources/lang/en_US/firefly.php b/resources/lang/en_US/firefly.php
index 313229c2d8..403811e6eb 100644
--- a/resources/lang/en_US/firefly.php
+++ b/resources/lang/en_US/firefly.php
@@ -1766,6 +1766,7 @@ return [
'updated_currency' => 'Currency :name updated',
'ask_site_owner' => 'Please ask :owner to add, remove or edit currencies.',
'currencies_intro' => 'Firefly III supports various currencies which you can set and enable here.',
+ 'currencies_switch_default' => 'If you have a large database, switching from one default currency to another may take a moment.',
'make_default_currency' => 'Make default',
'default_currency' => 'default',
'currency_is_disabled' => 'Disabled',
diff --git a/resources/views/currencies/index.twig b/resources/views/currencies/index.twig
index 93b30071d9..9da52a312b 100644
--- a/resources/views/currencies/index.twig
+++ b/resources/views/currencies/index.twig
@@ -13,11 +13,10 @@
{{ 'create_currency'|_ }}
-
+
{{ 'currencies_intro'|_ }}
-
-
{{ 'currencies_default_disabled'|_ }}
+ {{ 'currencies_switch_default'|_ }}
{% if currencies|length > 0 %}
@@ -125,7 +128,13 @@
data-id="{{ budget.id }}">{{ trans('firefly.available_between', {start: budget.start_date.isoFormat(monthAndDayFormat), end: budget.end_date.isoFormat(monthAndDayFormat) }) }}
:
{{ formatAmountBySymbol(budget.amount, budget.transaction_currency.symbol, budget.transaction_currency.decimal_places, true) }}
+ data-value="{{ budget.amount }}">
+ {{ formatAmountBySymbol(budget.amount, budget.transaction_currency.symbol, budget.transaction_currency.decimal_places, true) }}
+ {% if(convertToNative and 0 != budget.native_amount) %}
+ ({{ formatAmountBySymbol(budget.native_amount, defaultCurrency.symbol, defaultCurrency.decimal_places, true) }})
+ {% endif %}
+
+
diff --git a/resources/views/budgets/show.twig b/resources/views/budgets/show.twig
index ca1dbd4995..d0ec49a61f 100644
--- a/resources/views/budgets/show.twig
+++ b/resources/views/budgets/show.twig
@@ -158,12 +158,19 @@
{{ 'amount'|_ }} |
{{ formatAmountBySymbol(limit.amount, limit.transactionCurrency.symbol, limit.transactionCurrency.decimal_places) }}
+ {% if convertToNative and 0 != limit.native_amount %}
+ ({{ formatAmountBySymbol(limit.native_amount, defaultCurrency.symbol, defaultCurrency.decimal_places) }})
+ {% endif %}
|
{{ 'spent'|_ }} |
- {{ formatAmountBySymbol(limit.spent, limit.transactionCurrency.symbol, limit.transactionCurrency.decimal_places) }}
+ {% if convertToNative %}
+ {{ formatAmountBySymbol(limit.spent, defaultCurrency.symbol, defaultCurrency.decimal_places) }}
+ {% else %}
+ {{ formatAmountBySymbol(limit.spent, limit.transactionCurrency.symbol, limit.transactionCurrency.decimal_places) }}
+ {% endif %}
|
{% if limit.spent > 0 %}
From 68b446db1841f82e135dc11de13aae160c8e20b6 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Fri, 27 Dec 2024 19:46:40 +0100
Subject: [PATCH 129/167] Final changes.
---
.../Controllers/Chart/CategoryController.php | 80 +++++-----
app/Http/Controllers/DebugController.php | 4 +
.../Category/OperationsRepository.php | 151 +++++++++++-------
.../Category/WholePeriodChartGenerator.php | 5 +-
4 files changed, 142 insertions(+), 98 deletions(-)
diff --git a/app/Http/Controllers/Chart/CategoryController.php b/app/Http/Controllers/Chart/CategoryController.php
index 3a2e51a999..91bd8b24e3 100644
--- a/app/Http/Controllers/Chart/CategoryController.php
+++ b/app/Http/Controllers/Chart/CategoryController.php
@@ -70,24 +70,27 @@ class CategoryController extends Controller
public function all(Category $category): JsonResponse
{
// cache results:
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty('chart.category.all');
$cache->addProperty($category->id);
+ $cache->addProperty($this->convertToNative);
if ($cache->has()) {
- return response()->json($cache->get());
+ // return response()->json($cache->get());
}
/** @var CategoryRepositoryInterface $repository */
- $repository = app(CategoryRepositoryInterface::class);
- $start = $repository->firstUseDate($category) ?? $this->getDate();
- $range = app('navigation')->getViewRange(false);
- $start = app('navigation')->startOfPeriod($start, $range);
- $end = $this->getDate();
+ $repository = app(CategoryRepositoryInterface::class);
+ $start = $repository->firstUseDate($category) ?? $this->getDate();
+ $range = app('navigation')->getViewRange(false);
+ $start = app('navigation')->startOfPeriod($start, $range);
+ $end = $this->getDate();
/** @var WholePeriodChartGenerator $chartGenerator */
- $chartGenerator = app(WholePeriodChartGenerator::class);
- $chartData = $chartGenerator->generate($category, $start, $end);
- $data = $this->generator->multiSet($chartData);
+ $chartGenerator = app(WholePeriodChartGenerator::class);
+ $chartGenerator->convertToNative = $this->convertToNative;
+
+ $chartData = $chartGenerator->generate($category, $start, $end);
+ $data = $this->generator->multiSet($chartData);
$cache->store($data);
return response()->json($data);
@@ -104,10 +107,10 @@ class CategoryController extends Controller
*/
public function frontPage(): JsonResponse
{
- $start = session('start', today(config('app.timezone'))->startOfMonth());
- $end = session('end', today(config('app.timezone'))->endOfMonth());
+ $start = session('start', today(config('app.timezone'))->startOfMonth());
+ $end = session('end', today(config('app.timezone'))->endOfMonth());
// chart properties for cache:
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty($start);
$cache->addProperty($end);
$cache->addProperty($this->convertToNative);
@@ -136,10 +139,11 @@ class CategoryController extends Controller
$cache->addProperty('chart.category.period');
$cache->addProperty($accounts->pluck('id')->toArray());
$cache->addProperty($category);
+ $cache->addProperty($this->convertToNative);
if ($cache->has()) {
- return response()->json($cache->get());
+ // return response()->json($cache->get());
}
- $data = $this->reportPeriodChart($accounts, $start, $end, $category);
+ $data = $this->reportPeriodChart($accounts, $start, $end, $category);
$cache->store($data);
@@ -160,8 +164,8 @@ class CategoryController extends Controller
$noCatRepository = app(NoCategoryRepositoryInterface::class);
// this gives us all currencies
- $expenses = $noCatRepository->listExpenses($start, $end, $accounts);
- $income = $noCatRepository->listIncome($start, $end, $accounts);
+ $expenses = $noCatRepository->listExpenses($start, $end, $accounts);
+ $income = $noCatRepository->listIncome($start, $end, $accounts);
}
if (null !== $category) {
@@ -169,9 +173,9 @@ class CategoryController extends Controller
$opsRepository = app(OperationsRepositoryInterface::class);
$categoryId = $category->id;
// this gives us all currencies
- $collection = new Collection([$category]);
- $expenses = $opsRepository->listExpenses($start, $end, $accounts, $collection);
- $income = $opsRepository->listIncome($start, $end, $accounts, $collection);
+ $collection = new Collection([$category]);
+ $expenses = $opsRepository->listExpenses($start, $end, $accounts, $collection);
+ $income = $opsRepository->listIncome($start, $end, $accounts, $collection);
}
$currencies = array_unique(array_merge(array_keys($income), array_keys($expenses)));
$periods = app('navigation')->listOfPeriods($start, $end);
@@ -185,19 +189,19 @@ class CategoryController extends Controller
$inKey = sprintf('%d-in', $currencyId);
$chartData[$outKey]
= [
- 'label' => sprintf('%s (%s)', (string) trans('firefly.spent'), $currencyInfo['currency_name']),
- 'entries' => [],
- 'type' => 'bar',
- 'backgroundColor' => 'rgba(219, 68, 55, 0.5)', // red
- ];
+ 'label' => sprintf('%s (%s)', (string) trans('firefly.spent'), $currencyInfo['currency_name']),
+ 'entries' => [],
+ 'type' => 'bar',
+ 'backgroundColor' => 'rgba(219, 68, 55, 0.5)', // red
+ ];
$chartData[$inKey]
- = [
- 'label' => sprintf('%s (%s)', (string) trans('firefly.earned'), $currencyInfo['currency_name']),
- 'entries' => [],
- 'type' => 'bar',
- 'backgroundColor' => 'rgba(0, 141, 76, 0.5)', // green
- ];
+ = [
+ 'label' => sprintf('%s (%s)', (string) trans('firefly.earned'), $currencyInfo['currency_name']),
+ 'entries' => [],
+ 'type' => 'bar',
+ 'backgroundColor' => 'rgba(0, 141, 76, 0.5)', // green
+ ];
// loop empty periods:
foreach (array_keys($periods) as $period) {
$label = $periods[$period];
@@ -205,7 +209,7 @@ class CategoryController extends Controller
$chartData[$inKey]['entries'][$label] = '0';
}
// loop income and expenses for this category.:
- $outSet = $expenses[$currencyId]['categories'][$categoryId] ?? ['transaction_journals' => []];
+ $outSet = $expenses[$currencyId]['categories'][$categoryId] ?? ['transaction_journals' => []];
foreach ($outSet['transaction_journals'] as $journal) {
$amount = app('steam')->positive($journal['amount']);
$date = $journal['date']->isoFormat($format);
@@ -214,7 +218,7 @@ class CategoryController extends Controller
$chartData[$outKey]['entries'][$date] = bcadd($amount, $chartData[$outKey]['entries'][$date]);
}
- $inSet = $income[$currencyId]['categories'][$categoryId] ?? ['transaction_journals' => []];
+ $inSet = $income[$currencyId]['categories'][$categoryId] ?? ['transaction_journals' => []];
foreach ($inSet['transaction_journals'] as $journal) {
$amount = app('steam')->positive($journal['amount']);
$date = $journal['date']->isoFormat($format);
@@ -240,7 +244,7 @@ class CategoryController extends Controller
if ($cache->has()) {
return response()->json($cache->get());
}
- $data = $this->reportPeriodChart($accounts, $start, $end, null);
+ $data = $this->reportPeriodChart($accounts, $start, $end, null);
$cache->store($data);
@@ -255,14 +259,14 @@ class CategoryController extends Controller
*/
public function specificPeriod(Category $category, Carbon $date): JsonResponse
{
- $range = app('navigation')->getViewRange(false);
- $start = app('navigation')->startOfPeriod($date, $range);
- $end = session()->get('end');
+ $range = app('navigation')->getViewRange(false);
+ $start = app('navigation')->startOfPeriod($date, $range);
+ $end = session()->get('end');
if ($end < $start) {
[$end, $start] = [$start, $end];
}
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty($start);
$cache->addProperty($end);
$cache->addProperty($category->id);
diff --git a/app/Http/Controllers/DebugController.php b/app/Http/Controllers/DebugController.php
index e08bbe706f..510a4ca910 100644
--- a/app/Http/Controllers/DebugController.php
+++ b/app/Http/Controllers/DebugController.php
@@ -76,6 +76,10 @@ class DebugController extends Controller
|| str_starts_with($route->uri(), '_debugbar')
|| str_starts_with($route->uri(), '_ignition')
|| str_starts_with($route->uri(), 'oauth')
+ || str_starts_with($route->uri(), 'chart')
+ || str_starts_with($route->uri(), 'v1/jscript')
+ || str_starts_with($route->uri(), 'v2/jscript')
+ || str_starts_with($route->uri(), 'json')
|| str_starts_with($route->uri(), 'sanctum')
) {
continue;
diff --git a/app/Repositories/Category/OperationsRepository.php b/app/Repositories/Category/OperationsRepository.php
index 5f62bf2433..6741f3ffa8 100644
--- a/app/Repositories/Category/OperationsRepository.php
+++ b/app/Repositories/Category/OperationsRepository.php
@@ -63,13 +63,13 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setCategories($this->getCategories());
}
$collector->withCategoryInformation()->withAccountInformation()->withBudgetInformation();
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $categoryId = (int) $journal['category_id'];
- $categoryName = (string) $journal['category_name'];
+ $currencyId = (int) $journal['currency_id'];
+ $categoryId = (int) $journal['category_id'];
+ $categoryName = (string) $journal['category_name'];
// catch "no category" entries.
if (0 === $categoryId) {
@@ -77,7 +77,7 @@ class OperationsRepository implements OperationsRepositoryInterface
}
// info about the currency:
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'categories' => [],
'currency_id' => (string) $currencyId,
'currency_name' => $journal['currency_name'],
@@ -112,7 +112,7 @@ class OperationsRepository implements OperationsRepositoryInterface
return $array;
}
- public function setUser(null|Authenticatable|User $user): void
+ public function setUser(null | Authenticatable | User $user): void
{
if ($user instanceof User) {
$this->user = $user;
@@ -147,13 +147,13 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setCategories($this->getCategories());
}
$collector->withCategoryInformation()->withAccountInformation();
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $categoryId = (int) $journal['category_id'];
- $categoryName = (string) $journal['category_name'];
+ $currencyId = (int) $journal['currency_id'];
+ $categoryId = (int) $journal['category_id'];
+ $categoryName = (string) $journal['category_name'];
// catch "no category" entries.
if (0 === $categoryId) {
@@ -161,7 +161,7 @@ class OperationsRepository implements OperationsRepositoryInterface
}
// info about the currency:
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'categories' => [],
'currency_id' => (string) $currencyId,
'currency_name' => $journal['currency_name'],
@@ -200,8 +200,7 @@ class OperationsRepository implements OperationsRepositoryInterface
/** @var GroupCollectorInterface $collector */
$collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionType::TRANSFER])
- ->setDestinationAccounts($accounts)->excludeSourceAccounts($accounts)
- ;
+ ->setDestinationAccounts($accounts)->excludeSourceAccounts($accounts);
if (null !== $categories && $categories->count() > 0) {
$collector->setCategories($categories);
}
@@ -209,13 +208,13 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setCategories($this->getCategories());
}
$collector->withCategoryInformation()->withAccountInformation()->withBudgetInformation();
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $categoryId = (int) $journal['category_id'];
- $categoryName = (string) $journal['category_name'];
+ $currencyId = (int) $journal['currency_id'];
+ $categoryId = (int) $journal['category_id'];
+ $categoryName = (string) $journal['category_name'];
// catch "no category" entries.
if (0 === $categoryId) {
@@ -223,7 +222,7 @@ class OperationsRepository implements OperationsRepositoryInterface
}
// info about the currency:
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'categories' => [],
'currency_id' => (string) $currencyId,
'currency_name' => $journal['currency_name'],
@@ -263,8 +262,7 @@ class OperationsRepository implements OperationsRepositoryInterface
/** @var GroupCollectorInterface $collector */
$collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionType::TRANSFER])
- ->setSourceAccounts($accounts)->excludeDestinationAccounts($accounts)
- ;
+ ->setSourceAccounts($accounts)->excludeDestinationAccounts($accounts);
if (null !== $categories && $categories->count() > 0) {
$collector->setCategories($categories);
}
@@ -272,13 +270,13 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setCategories($this->getCategories());
}
$collector->withCategoryInformation()->withAccountInformation()->withBudgetInformation();
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $categoryId = (int) $journal['category_id'];
- $categoryName = (string) $journal['category_name'];
+ $currencyId = (int) $journal['currency_id'];
+ $categoryId = (int) $journal['category_id'];
+ $categoryName = (string) $journal['category_name'];
// catch "no category" entries.
if (0 === $categoryId) {
@@ -286,7 +284,7 @@ class OperationsRepository implements OperationsRepositoryInterface
}
// info about the currency:
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'categories' => [],
'currency_id' => (string) $currencyId,
'currency_name' => $journal['currency_name'],
@@ -327,7 +325,7 @@ class OperationsRepository implements OperationsRepositoryInterface
public function sumExpenses(Carbon $start, Carbon $end, ?Collection $accounts = null, ?Collection $categories = null): array
{
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionTypeEnum::WITHDRAWAL->value]);
// default currency information for native stuff.
@@ -341,29 +339,35 @@ class OperationsRepository implements OperationsRepositoryInterface
}
$collector->setCategories($categories);
$collector->withCategoryInformation();
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
Log::debug(sprintf('Collected %d journals', count($journals)));
foreach ($journals as $journal) {
// Almost the same as in \FireflyIII\Repositories\Budget\OperationsRepository::sumExpenses
- $amount = '0';
- $currencyId = (int) $journal['currency_id'];
- $currencyName = $journal['currency_name'];
- $currencySymbol = $journal['currency_symbol'];
- $currencyCode = $journal['currency_code'];
- $currencyDecimalPlaces = $journal['currency_decimal_places'];
+ $amount = '0';
+ $currencyId = (int) $journal['currency_id'];
+ $currencyName = $journal['currency_name'];
+ $currencySymbol = $journal['currency_symbol'];
+ $currencyCode = $journal['currency_code'];
+ $currencyDecimalPlaces = $journal['currency_decimal_places'];
if ($convertToNative) {
- $useNative = $default->id !== (int) $journal['currency_id'];
- $amount = Amount::getAmountFromJournal($journal);
- if ($useNative) {
+ $amount = Amount::getAmountFromJournal($journal);
+ if ($default->id !== (int) $journal['currency_id'] && $default->id !== (int) $journal['foreign_currency_id']) {
$currencyId = $default->id;
$currencyName = $default->name;
$currencySymbol = $default->symbol;
$currencyCode = $default->code;
$currencyDecimalPlaces = $default->decimal_places;
}
+ if ($default->id !== (int) $journal['currency_id'] && $default->id === (int) $journal['foreign_currency_id']) {
+ $currencyId = $journal['foreign_currency_id'];
+ $currencyName = $journal['foreign_currency_name'];
+ $currencySymbol = $journal['foreign_currency_symbol'];
+ $currencyCode = $journal['foreign_currency_code'];
+ $currencyDecimalPlaces = $journal['foreign_currency_decimal_places'];
+ }
Log::debug(sprintf('[a] Add amount %s %s', $currencyCode, $amount));
}
if (!$convertToNative) {
@@ -372,8 +376,7 @@ class OperationsRepository implements OperationsRepositoryInterface
$amount = $journal['amount'];
}
-
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'sum' => '0',
'currency_id' => (string) $currencyId,
'currency_name' => $currencyName,
@@ -395,8 +398,7 @@ class OperationsRepository implements OperationsRepositoryInterface
/** @var GroupCollectorInterface $collector */
$collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)
- ->setTypes([TransactionType::DEPOSIT])
- ;
+ ->setTypes([TransactionTypeEnum::DEPOSIT->value]);
if (null !== $accounts && $accounts->count() > 0) {
$collector->setAccounts($accounts);
@@ -405,20 +407,52 @@ class OperationsRepository implements OperationsRepositoryInterface
$categories = $this->getCategories();
}
$collector->setCategories($categories);
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $convertToNative = app('preferences')->get('convert_to_native', false)->data;
+ $default = app('amount')->getDefaultCurrency();
+ $array = [];
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $array[$currencyId] ??= [
+ // Almost the same as in \FireflyIII\Repositories\Budget\OperationsRepository::sumExpenses
+ $amount = '0';
+ $currencyId = (int) $journal['currency_id'];
+ $currencyName = $journal['currency_name'];
+ $currencySymbol = $journal['currency_symbol'];
+ $currencyCode = $journal['currency_code'];
+ $currencyDecimalPlaces = $journal['currency_decimal_places'];
+ if ($convertToNative) {
+ $amount = Amount::getAmountFromJournal($journal);
+ if ($default->id !== (int) $journal['currency_id'] && $default->id !== (int) $journal['foreign_currency_id']) {
+ $currencyId = $default->id;
+ $currencyName = $default->name;
+ $currencySymbol = $default->symbol;
+ $currencyCode = $default->code;
+ $currencyDecimalPlaces = $default->decimal_places;
+ }
+ if ($default->id !== (int) $journal['currency_id'] && $default->id === (int) $journal['foreign_currency_id']) {
+ $currencyId = $journal['foreign_currency_id'];
+ $currencyName = $journal['foreign_currency_name'];
+ $currencySymbol = $journal['foreign_currency_symbol'];
+ $currencyCode = $journal['foreign_currency_code'];
+ $currencyDecimalPlaces = $journal['foreign_currency_decimal_places'];
+ }
+ Log::debug(sprintf('[a] Add amount %s %s', $currencyCode, $amount));
+ }
+ if (!$convertToNative) {
+ // ignore the amount in foreign currency.
+ Log::debug(sprintf('[b] Add amount %s %s', $currencyCode, $journal['amount']));
+ $amount = $journal['amount'];
+ }
+
+ $array[$currencyId] ??= [
'sum' => '0',
'currency_id' => (string) $currencyId,
- 'currency_name' => $journal['currency_name'],
- 'currency_symbol' => $journal['currency_symbol'],
- 'currency_code' => $journal['currency_code'],
- 'currency_decimal_places' => $journal['currency_decimal_places'],
+ 'currency_name' => $currencyName,
+ 'currency_symbol' => $currencySymbol,
+ 'currency_code' => $currencyCode,
+ 'currency_decimal_places' => $currencyDecimalPlaces,
];
- $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->positive($journal['amount']));
+ $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->positive($amount));
}
return $array;
@@ -432,8 +466,7 @@ class OperationsRepository implements OperationsRepositoryInterface
/** @var GroupCollectorInterface $collector */
$collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)
- ->setTypes([TransactionType::TRANSFER])
- ;
+ ->setTypes([TransactionType::TRANSFER]);
if (null !== $accounts && $accounts->count() > 0) {
$collector->setAccounts($accounts);
@@ -442,12 +475,12 @@ class OperationsRepository implements OperationsRepositoryInterface
$categories = $this->getCategories();
}
$collector->setCategories($categories);
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
foreach ($journals as $journal) {
$currencyId = (int) $journal['currency_id'];
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'sum' => '0',
'currency_id' => (string) $currencyId,
'currency_name' => $journal['currency_name'],
diff --git a/app/Support/Chart/Category/WholePeriodChartGenerator.php b/app/Support/Chart/Category/WholePeriodChartGenerator.php
index 1a562aa370..2b2e39b182 100644
--- a/app/Support/Chart/Category/WholePeriodChartGenerator.php
+++ b/app/Support/Chart/Category/WholePeriodChartGenerator.php
@@ -25,6 +25,7 @@ declare(strict_types=1);
namespace FireflyIII\Support\Chart\Category;
use Carbon\Carbon;
+use FireflyIII\Enums\AccountTypeEnum;
use FireflyIII\Models\AccountType;
use FireflyIII\Models\Category;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
@@ -36,6 +37,8 @@ use Illuminate\Support\Collection;
*/
class WholePeriodChartGenerator
{
+ public bool $convertToNative;
+
public function generate(Category $category, Carbon $start, Carbon $end): array
{
$collection = new Collection([$category]);
@@ -46,7 +49,7 @@ class WholePeriodChartGenerator
/** @var AccountRepositoryInterface $accountRepository */
$accountRepository = app(AccountRepositoryInterface::class);
- $types = [AccountType::DEFAULT, AccountType::ASSET, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE];
+ $types = [AccountTypeEnum::DEFAULT->value, AccountTypeEnum::ASSET->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value];
$accounts = $accountRepository->getAccountsByType($types);
$step = $this->calculateStep($start, $end);
$chartData = [];
From f191086adb366cea64ebad7b372410e0edf6a4c2 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Fri, 27 Dec 2024 19:47:35 +0100
Subject: [PATCH 130/167] Enable cache again.
---
app/Helpers/Report/NetWorth.php | 2 +-
app/Http/Controllers/Chart/AccountController.php | 2 +-
app/Http/Controllers/Chart/BillController.php | 2 +-
app/Http/Controllers/Chart/BudgetController.php | 6 +++---
app/Http/Controllers/Chart/CategoryController.php | 6 +++---
app/Http/Controllers/Chart/ReportController.php | 2 +-
app/Support/Http/Controllers/AugumentData.php | 2 +-
app/Support/Http/Controllers/ChartGeneration.php | 2 +-
app/Support/Http/Controllers/PeriodOverview.php | 2 +-
app/Support/Steam.php | 2 +-
10 files changed, 14 insertions(+), 14 deletions(-)
diff --git a/app/Helpers/Report/NetWorth.php b/app/Helpers/Report/NetWorth.php
index 2b5c17c944..6fc0c3a0c1 100644
--- a/app/Helpers/Report/NetWorth.php
+++ b/app/Helpers/Report/NetWorth.php
@@ -74,7 +74,7 @@ class NetWorth implements NetWorthInterface
$cache->addProperty('net-worth-by-accounts');
$cache->addProperty($ids);
if ($cache->has()) {
- // return $cache->get();
+ return $cache->get();
}
Log::debug(sprintf('Now in byAccounts("%s", "%s")', $ids, $date->format('Y-m-d H:i:s')));
$default = Amount::getDefaultCurrency();
diff --git a/app/Http/Controllers/Chart/AccountController.php b/app/Http/Controllers/Chart/AccountController.php
index f2a3c6ea23..c3ffe5f1d2 100644
--- a/app/Http/Controllers/Chart/AccountController.php
+++ b/app/Http/Controllers/Chart/AccountController.php
@@ -426,7 +426,7 @@ class AccountController extends Controller
$cache->addProperty($this->convertToNative);
$cache->addProperty($account->id);
if ($cache->has()) {
- // return response()->json($cache->get());
+ return response()->json($cache->get());
}
// collect and filter balances for the entire period.
diff --git a/app/Http/Controllers/Chart/BillController.php b/app/Http/Controllers/Chart/BillController.php
index 529a1170c8..e4cf002336 100644
--- a/app/Http/Controllers/Chart/BillController.php
+++ b/app/Http/Controllers/Chart/BillController.php
@@ -111,7 +111,7 @@ class BillController extends Controller
$cache->addProperty($bill->id);
$cache->addProperty($this->convertToNative);
if ($cache->has()) {
- // return response()->json($cache->get());
+ return response()->json($cache->get());
}
$locale = app('steam')->getLocale();
diff --git a/app/Http/Controllers/Chart/BudgetController.php b/app/Http/Controllers/Chart/BudgetController.php
index b06bdf2bfb..f830264167 100644
--- a/app/Http/Controllers/Chart/BudgetController.php
+++ b/app/Http/Controllers/Chart/BudgetController.php
@@ -221,7 +221,7 @@ class BudgetController extends Controller
$cache->addProperty($end);
if ($cache->has()) {
- // return response()->json($cache->get());
+ return response()->json($cache->get());
}
$collector->setRange($start, $end);
$collector->setBudget($budget);
@@ -385,7 +385,7 @@ class BudgetController extends Controller
$cache->addProperty($end);
if ($cache->has()) {
- // return response()->json($cache->get());
+ return response()->json($cache->get());
}
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::WITHDRAWAL])->setBudget($budget)->withAccountInformation();
@@ -457,7 +457,7 @@ class BudgetController extends Controller
$cache->addProperty($this->convertToNative);
$cache->addProperty('chart.budget.frontpage');
if ($cache->has()) {
- // return response()->json($cache->get());
+ return response()->json($cache->get());
}
Log::debug('Regenerate frontpage chart from scratch.');
$chartGenerator = app(FrontpageChartGenerator::class);
diff --git a/app/Http/Controllers/Chart/CategoryController.php b/app/Http/Controllers/Chart/CategoryController.php
index 91bd8b24e3..c48b8cf3ff 100644
--- a/app/Http/Controllers/Chart/CategoryController.php
+++ b/app/Http/Controllers/Chart/CategoryController.php
@@ -75,7 +75,7 @@ class CategoryController extends Controller
$cache->addProperty($category->id);
$cache->addProperty($this->convertToNative);
if ($cache->has()) {
- // return response()->json($cache->get());
+ return response()->json($cache->get());
}
/** @var CategoryRepositoryInterface $repository */
@@ -116,7 +116,7 @@ class CategoryController extends Controller
$cache->addProperty($this->convertToNative);
$cache->addProperty('chart.category.frontpage');
if ($cache->has()) {
- // return response()->json($cache->get());
+ return response()->json($cache->get());
}
$frontpageGenerator = new FrontpageChartGenerator($start, $end);
@@ -141,7 +141,7 @@ class CategoryController extends Controller
$cache->addProperty($category);
$cache->addProperty($this->convertToNative);
if ($cache->has()) {
- // return response()->json($cache->get());
+ return response()->json($cache->get());
}
$data = $this->reportPeriodChart($accounts, $start, $end, $category);
diff --git a/app/Http/Controllers/Chart/ReportController.php b/app/Http/Controllers/Chart/ReportController.php
index 7c5db3052e..d538ebbd97 100644
--- a/app/Http/Controllers/Chart/ReportController.php
+++ b/app/Http/Controllers/Chart/ReportController.php
@@ -145,7 +145,7 @@ class ReportController extends Controller
$cache->addProperty($accounts);
$cache->addProperty($end);
if ($cache->has()) {
- // return response()->json($cache->get());
+ return response()->json($cache->get());
}
Log::debug('Going to do operations for accounts ', $accounts->pluck('id')->toArray());
diff --git a/app/Support/Http/Controllers/AugumentData.php b/app/Support/Http/Controllers/AugumentData.php
index 574cad84c5..e3c39ea4b2 100644
--- a/app/Support/Http/Controllers/AugumentData.php
+++ b/app/Support/Http/Controllers/AugumentData.php
@@ -183,7 +183,7 @@ trait AugumentData
$cache->addProperty('get-limits');
if ($cache->has()) {
- // return $cache->get();
+ return $cache->get();
}
$set = $blRepository->getBudgetLimits($budget, $start, $end);
diff --git a/app/Support/Http/Controllers/ChartGeneration.php b/app/Support/Http/Controllers/ChartGeneration.php
index e66a202364..3fea9eada1 100644
--- a/app/Support/Http/Controllers/ChartGeneration.php
+++ b/app/Support/Http/Controllers/ChartGeneration.php
@@ -54,7 +54,7 @@ trait ChartGeneration
$cache->addProperty($accounts);
$cache->addProperty($convertToNative);
if ($cache->has()) {
- // return $cache->get();
+ return $cache->get();
}
app('log')->debug('Regenerate chart.account.account-balance-chart from scratch.');
$locale = app('steam')->getLocale();
diff --git a/app/Support/Http/Controllers/PeriodOverview.php b/app/Support/Http/Controllers/PeriodOverview.php
index e1df4293c3..925438b375 100644
--- a/app/Support/Http/Controllers/PeriodOverview.php
+++ b/app/Support/Http/Controllers/PeriodOverview.php
@@ -333,7 +333,7 @@ trait PeriodOverview
$cache->addProperty('no-budget-period-entries');
if ($cache->has()) {
- // return $cache->get();
+ return $cache->get();
}
/** @var array $dates */
diff --git a/app/Support/Steam.php b/app/Support/Steam.php
index 7d5ca78599..0201aefba0 100644
--- a/app/Support/Steam.php
+++ b/app/Support/Steam.php
@@ -84,7 +84,7 @@ class Steam
$cache->addProperty($start);
$cache->addProperty($end);
if ($cache->has()) {
- // return $cache->get();
+ return $cache->get();
}
$balances = [];
From 2dddaa36d517c49186e954897641755dc20960ba Mon Sep 17 00:00:00 2001
From: James Cole
Date: Fri, 27 Dec 2024 19:51:20 +0100
Subject: [PATCH 131/167] Actions will default to php 8.4
---
.github/workflows/release.yml | 2 +-
.github/workflows/sonarcloud.yml | 2 +-
2 files changed, 2 insertions(+), 2 deletions(-)
diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml
index 9a95c7c7aa..077117ed49 100644
--- a/.github/workflows/release.yml
+++ b/.github/workflows/release.yml
@@ -10,7 +10,7 @@ on:
phpversion:
description: 'PHP version'
required: true
- default: '8.3'
+ default: '8.4'
schedule:
- cron: '0 3 * * MON'
diff --git a/.github/workflows/sonarcloud.yml b/.github/workflows/sonarcloud.yml
index 41ef4cfeb9..2f7ca3e532 100644
--- a/.github/workflows/sonarcloud.yml
+++ b/.github/workflows/sonarcloud.yml
@@ -19,7 +19,7 @@ jobs:
- name: Setup PHP with Xdebug
uses: shivammathur/setup-php@v2
with:
- php-version: '8.3'
+ php-version: '8.4'
coverage: xdebug
extensions: >-
bcmath
From 23c4352c1800eaa134f5cc6e48e3e8322ecd153f Mon Sep 17 00:00:00 2001
From: github-actions <41898282+github-actions[bot]@users.noreply.github.com>
Date: Fri, 27 Dec 2024 22:03:16 +0100
Subject: [PATCH 132/167] Auto commit for release 'develop' on 2024-12-27
---
.ci/php-cs-fixer/composer.lock | 24 +-
app/Helpers/Report/NetWorth.php | 2 +-
.../Controllers/Budget/IndexController.php | 21 +-
.../Controllers/Chart/AccountController.php | 2 +-
app/Http/Controllers/Chart/BillController.php | 2 +-
.../Controllers/Chart/BudgetController.php | 76 +++---
.../Controllers/Chart/CategoryController.php | 76 +++---
.../Controllers/Chart/ReportController.php | 2 +-
app/Http/Controllers/JavascriptController.php | 2 +-
.../Category/OperationsRepository.php | 108 ++++----
.../Category/WholePeriodChartGenerator.php | 1 -
app/Support/Http/Controllers/AugumentData.php | 6 +-
.../Http/Controllers/ChartGeneration.php | 2 +-
.../Http/Controllers/PeriodOverview.php | 242 +++++++++---------
app/Support/Steam.php | 2 +-
composer.lock | 40 +--
config/firefly.php | 2 +-
package-lock.json | 16 +-
18 files changed, 316 insertions(+), 310 deletions(-)
diff --git a/.ci/php-cs-fixer/composer.lock b/.ci/php-cs-fixer/composer.lock
index 4b2ae2657f..c358fdbe1c 100644
--- a/.ci/php-cs-fixer/composer.lock
+++ b/.ci/php-cs-fixer/composer.lock
@@ -1369,12 +1369,12 @@
},
"type": "library",
"extra": {
+ "thanks": {
+ "url": "https://github.com/symfony/contracts",
+ "name": "symfony/contracts"
+ },
"branch-alias": {
"dev-main": "3.5-dev"
- },
- "thanks": {
- "name": "symfony/contracts",
- "url": "https://github.com/symfony/contracts"
}
},
"autoload": {
@@ -1517,12 +1517,12 @@
},
"type": "library",
"extra": {
+ "thanks": {
+ "url": "https://github.com/symfony/contracts",
+ "name": "symfony/contracts"
+ },
"branch-alias": {
"dev-main": "3.5-dev"
- },
- "thanks": {
- "name": "symfony/contracts",
- "url": "https://github.com/symfony/contracts"
}
},
"autoload": {
@@ -2329,12 +2329,12 @@
},
"type": "library",
"extra": {
+ "thanks": {
+ "url": "https://github.com/symfony/contracts",
+ "name": "symfony/contracts"
+ },
"branch-alias": {
"dev-main": "3.5-dev"
- },
- "thanks": {
- "name": "symfony/contracts",
- "url": "https://github.com/symfony/contracts"
}
},
"autoload": {
diff --git a/app/Helpers/Report/NetWorth.php b/app/Helpers/Report/NetWorth.php
index 6fc0c3a0c1..9b70e4b713 100644
--- a/app/Helpers/Report/NetWorth.php
+++ b/app/Helpers/Report/NetWorth.php
@@ -74,7 +74,7 @@ class NetWorth implements NetWorthInterface
$cache->addProperty('net-worth-by-accounts');
$cache->addProperty($ids);
if ($cache->has()) {
- return $cache->get();
+ return $cache->get();
}
Log::debug(sprintf('Now in byAccounts("%s", "%s")', $ids, $date->format('Y-m-d H:i:s')));
$default = Amount::getDefaultCurrency();
diff --git a/app/Http/Controllers/Budget/IndexController.php b/app/Http/Controllers/Budget/IndexController.php
index 78509f8b17..c49cee169c 100644
--- a/app/Http/Controllers/Budget/IndexController.php
+++ b/app/Http/Controllers/Budget/IndexController.php
@@ -162,7 +162,7 @@ class IndexController extends Controller
private function getAllAvailableBudgets(Carbon $start, Carbon $end): array
{
- $converter = new ExchangeRateConverter();
+ $converter = new ExchangeRateConverter();
// get all available budgets.
$ab = $this->abRepository->get($start, $end);
$availableBudgets = [];
@@ -170,24 +170,25 @@ class IndexController extends Controller
// for each, complement with spent amount:
/** @var AvailableBudget $entry */
foreach ($ab as $entry) {
- $array = $entry->toArray();
- $array['start_date'] = $entry->start_date;
- $array['end_date'] = $entry->end_date;
+ $array = $entry->toArray();
+ $array['start_date'] = $entry->start_date;
+ $array['end_date'] = $entry->end_date;
// spent in period:
- $spentArr = $this->opsRepository->sumExpenses($entry->start_date, $entry->end_date, null, null, $entry->transactionCurrency);
- $array['spent'] = $spentArr[$entry->transaction_currency_id]['sum'] ?? '0';
- $array['native_spent'] = $this->convertToNative && $entry->transaction_currency_id !== $this->defaultCurrency->id ? $converter->convert($entry->transactionCurrency, $this->defaultCurrency, $entry->start_date, $array['spent']) : null;
+ $spentArr = $this->opsRepository->sumExpenses($entry->start_date, $entry->end_date, null, null, $entry->transactionCurrency);
+ $array['spent'] = $spentArr[$entry->transaction_currency_id]['sum'] ?? '0';
+ $array['native_spent'] = $this->convertToNative && $entry->transaction_currency_id !== $this->defaultCurrency->id ? $converter->convert($entry->transactionCurrency, $this->defaultCurrency, $entry->start_date, $array['spent']) : null;
// budgeted in period:
- $budgeted = $this->blRepository->budgeted($entry->start_date, $entry->end_date, $entry->transactionCurrency);
- $array['budgeted'] = $budgeted;
+ $budgeted = $this->blRepository->budgeted($entry->start_date, $entry->end_date, $entry->transactionCurrency);
+ $array['budgeted'] = $budgeted;
$array['native_budgeted'] = $this->convertToNative && $entry->transaction_currency_id !== $this->defaultCurrency->id ? $converter->convert($entry->transactionCurrency, $this->defaultCurrency, $entry->start_date, $budgeted) : null;
// this time, because of complex sums, use the currency converter.
- $availableBudgets[] = $array;
+ $availableBudgets[] = $array;
unset($spentArr);
}
+
return $availableBudgets;
}
diff --git a/app/Http/Controllers/Chart/AccountController.php b/app/Http/Controllers/Chart/AccountController.php
index c3ffe5f1d2..09d5bb6ccd 100644
--- a/app/Http/Controllers/Chart/AccountController.php
+++ b/app/Http/Controllers/Chart/AccountController.php
@@ -426,7 +426,7 @@ class AccountController extends Controller
$cache->addProperty($this->convertToNative);
$cache->addProperty($account->id);
if ($cache->has()) {
- return response()->json($cache->get());
+ return response()->json($cache->get());
}
// collect and filter balances for the entire period.
diff --git a/app/Http/Controllers/Chart/BillController.php b/app/Http/Controllers/Chart/BillController.php
index e4cf002336..a5ab00b99b 100644
--- a/app/Http/Controllers/Chart/BillController.php
+++ b/app/Http/Controllers/Chart/BillController.php
@@ -111,7 +111,7 @@ class BillController extends Controller
$cache->addProperty($bill->id);
$cache->addProperty($this->convertToNative);
if ($cache->has()) {
- return response()->json($cache->get());
+ return response()->json($cache->get());
}
$locale = app('steam')->getLocale();
diff --git a/app/Http/Controllers/Chart/BudgetController.php b/app/Http/Controllers/Chart/BudgetController.php
index f830264167..3f92b2dabb 100644
--- a/app/Http/Controllers/Chart/BudgetController.php
+++ b/app/Http/Controllers/Chart/BudgetController.php
@@ -97,7 +97,7 @@ class BudgetController extends Controller
$cache->addProperty($budget->id);
if ($cache->has()) {
- return response()->json($cache->get());
+ return response()->json($cache->get());
}
$step = $this->calculateStep($start, $end); // depending on diff, do something with range of chart.
$collection = new Collection([$budget]);
@@ -164,15 +164,15 @@ class BudgetController extends Controller
$cache->addProperty($budget->id);
if ($cache->has()) {
- return response()->json($cache->get());
+ return response()->json($cache->get());
}
$locale = app('steam')->getLocale();
$entries = [];
$amount = $budgetLimit->amount;
$budgetCollection = new Collection([$budget]);
$currency = $budgetLimit->transactionCurrency;
- if($this->convertToNative) {
- $amount = $budgetLimit->native_amount;
+ if ($this->convertToNative) {
+ $amount = $budgetLimit->native_amount;
$currency = $this->defaultCurrency;
}
@@ -221,7 +221,7 @@ class BudgetController extends Controller
$cache->addProperty($end);
if ($cache->has()) {
- return response()->json($cache->get());
+ return response()->json($cache->get());
}
$collector->setRange($start, $end);
$collector->setBudget($budget);
@@ -232,22 +232,22 @@ class BudgetController extends Controller
// group by asset account ID:
foreach ($journals as $journal) {
$key = sprintf('%d-%d', $journal['source_account_id'], $journal['currency_id']);
- $amount = $journal['amount'];
+ $amount = $journal['amount'];
// if convert to native, use the native things, unless it's the foreign amount which is in the native currency.
- if($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] !== $this->defaultCurrency->id) {
- $key = sprintf('%d-%d', $journal['source_account_id'], $this->defaultCurrency->id);
+ if ($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] !== $this->defaultCurrency->id) {
+ $key = sprintf('%d-%d', $journal['source_account_id'], $this->defaultCurrency->id);
$symbol = $this->defaultCurrency->symbol;
- $code = $this->defaultCurrency->code;
- $name = $this->defaultCurrency->name;
+ $code = $this->defaultCurrency->code;
+ $name = $this->defaultCurrency->name;
$amount = $journal['native_amount'];
}
- if($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] === $this->defaultCurrency->id) {
- $key = sprintf('%d-%d', $journal['source_account_id'], $this->defaultCurrency->id);
+ if ($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] === $this->defaultCurrency->id) {
+ $key = sprintf('%d-%d', $journal['source_account_id'], $this->defaultCurrency->id);
$symbol = $this->defaultCurrency->symbol;
- $code = $this->defaultCurrency->code;
- $name = $this->defaultCurrency->name;
+ $code = $this->defaultCurrency->code;
+ $name = $this->defaultCurrency->name;
$amount = $journal['foreign_amount'];
}
@@ -312,26 +312,26 @@ class BudgetController extends Controller
$chartData = [];
foreach ($journals as $journal) {
$key = sprintf('%d-%d', $journal['category_id'], $journal['currency_id']);
- $symbol = $journal['currency_symbol'];
- $code = $journal['currency_code'];
- $name = $journal['currency_name'];
- $amount = $journal['amount'];
+ $symbol = $journal['currency_symbol'];
+ $code = $journal['currency_code'];
+ $name = $journal['currency_name'];
+ $amount = $journal['amount'];
// if convert to native, use the native things, unless it's the foreign amount which is in the native currency.
- if($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] !== $this->defaultCurrency->id
+ if ($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] !== $this->defaultCurrency->id
) {
- $key = sprintf('%d-%d', $journal['category_id'], $this->defaultCurrency->id);
+ $key = sprintf('%d-%d', $journal['category_id'], $this->defaultCurrency->id);
$symbol = $this->defaultCurrency->symbol;
- $code = $this->defaultCurrency->code;
- $name = $this->defaultCurrency->name;
+ $code = $this->defaultCurrency->code;
+ $name = $this->defaultCurrency->name;
$amount = $journal['native_amount'];
}
- if($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] === $this->defaultCurrency->id
+ if ($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] === $this->defaultCurrency->id
) {
- $key = sprintf('%d-%d', $journal['category_id'], $this->defaultCurrency->id);
+ $key = sprintf('%d-%d', $journal['category_id'], $this->defaultCurrency->id);
$symbol = $this->defaultCurrency->symbol;
- $code = $this->defaultCurrency->code;
- $name = $this->defaultCurrency->name;
+ $code = $this->defaultCurrency->code;
+ $name = $this->defaultCurrency->name;
$amount = $journal['foreign_amount'];
}
@@ -385,7 +385,7 @@ class BudgetController extends Controller
$cache->addProperty($end);
if ($cache->has()) {
- return response()->json($cache->get());
+ return response()->json($cache->get());
}
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::WITHDRAWAL])->setBudget($budget)->withAccountInformation();
@@ -396,22 +396,22 @@ class BudgetController extends Controller
/** @var array $journal */
foreach ($journals as $journal) {
$key = sprintf('%d-%d', $journal['destination_account_id'], $journal['currency_id']);
- $amount = $journal['amount'];
+ $amount = $journal['amount'];
// if convert to native, use the native things, unless it's the foreign amount which is in the native currency.
- if($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] !== $this->defaultCurrency->id) {
- $key = sprintf('%d-%d', $journal['destination_account_id'], $this->defaultCurrency->id);
+ if ($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] !== $this->defaultCurrency->id) {
+ $key = sprintf('%d-%d', $journal['destination_account_id'], $this->defaultCurrency->id);
$symbol = $this->defaultCurrency->symbol;
- $code = $this->defaultCurrency->code;
- $name = $this->defaultCurrency->name;
+ $code = $this->defaultCurrency->code;
+ $name = $this->defaultCurrency->name;
$amount = $journal['native_amount'];
}
- if($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] === $this->defaultCurrency->id) {
- $key = sprintf('%d-%d', $journal['destination_account_id'], $this->defaultCurrency->id);
+ if ($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] === $this->defaultCurrency->id) {
+ $key = sprintf('%d-%d', $journal['destination_account_id'], $this->defaultCurrency->id);
$symbol = $this->defaultCurrency->symbol;
- $code = $this->defaultCurrency->code;
- $name = $this->defaultCurrency->name;
+ $code = $this->defaultCurrency->code;
+ $name = $this->defaultCurrency->name;
$amount = $journal['foreign_amount'];
}
@@ -419,7 +419,7 @@ class BudgetController extends Controller
'amount' => '0',
'currency_symbol' => $symbol,
'currency_code' => $code,
- 'currency_name' => $name
+ 'currency_name' => $name,
];
$result[$key]['amount'] = bcadd($amount, $result[$key]['amount']);
}
@@ -457,7 +457,7 @@ class BudgetController extends Controller
$cache->addProperty($this->convertToNative);
$cache->addProperty('chart.budget.frontpage');
if ($cache->has()) {
- return response()->json($cache->get());
+ return response()->json($cache->get());
}
Log::debug('Regenerate frontpage chart from scratch.');
$chartGenerator = app(FrontpageChartGenerator::class);
diff --git a/app/Http/Controllers/Chart/CategoryController.php b/app/Http/Controllers/Chart/CategoryController.php
index c48b8cf3ff..9c9fc19ead 100644
--- a/app/Http/Controllers/Chart/CategoryController.php
+++ b/app/Http/Controllers/Chart/CategoryController.php
@@ -70,27 +70,27 @@ class CategoryController extends Controller
public function all(Category $category): JsonResponse
{
// cache results:
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty('chart.category.all');
$cache->addProperty($category->id);
$cache->addProperty($this->convertToNative);
if ($cache->has()) {
- return response()->json($cache->get());
+ return response()->json($cache->get());
}
/** @var CategoryRepositoryInterface $repository */
- $repository = app(CategoryRepositoryInterface::class);
- $start = $repository->firstUseDate($category) ?? $this->getDate();
- $range = app('navigation')->getViewRange(false);
- $start = app('navigation')->startOfPeriod($start, $range);
- $end = $this->getDate();
+ $repository = app(CategoryRepositoryInterface::class);
+ $start = $repository->firstUseDate($category) ?? $this->getDate();
+ $range = app('navigation')->getViewRange(false);
+ $start = app('navigation')->startOfPeriod($start, $range);
+ $end = $this->getDate();
/** @var WholePeriodChartGenerator $chartGenerator */
$chartGenerator = app(WholePeriodChartGenerator::class);
$chartGenerator->convertToNative = $this->convertToNative;
- $chartData = $chartGenerator->generate($category, $start, $end);
- $data = $this->generator->multiSet($chartData);
+ $chartData = $chartGenerator->generate($category, $start, $end);
+ $data = $this->generator->multiSet($chartData);
$cache->store($data);
return response()->json($data);
@@ -107,16 +107,16 @@ class CategoryController extends Controller
*/
public function frontPage(): JsonResponse
{
- $start = session('start', today(config('app.timezone'))->startOfMonth());
- $end = session('end', today(config('app.timezone'))->endOfMonth());
+ $start = session('start', today(config('app.timezone'))->startOfMonth());
+ $end = session('end', today(config('app.timezone'))->endOfMonth());
// chart properties for cache:
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty($start);
$cache->addProperty($end);
$cache->addProperty($this->convertToNative);
$cache->addProperty('chart.category.frontpage');
if ($cache->has()) {
- return response()->json($cache->get());
+ return response()->json($cache->get());
}
$frontpageGenerator = new FrontpageChartGenerator($start, $end);
@@ -141,9 +141,9 @@ class CategoryController extends Controller
$cache->addProperty($category);
$cache->addProperty($this->convertToNative);
if ($cache->has()) {
- return response()->json($cache->get());
+ return response()->json($cache->get());
}
- $data = $this->reportPeriodChart($accounts, $start, $end, $category);
+ $data = $this->reportPeriodChart($accounts, $start, $end, $category);
$cache->store($data);
@@ -164,8 +164,8 @@ class CategoryController extends Controller
$noCatRepository = app(NoCategoryRepositoryInterface::class);
// this gives us all currencies
- $expenses = $noCatRepository->listExpenses($start, $end, $accounts);
- $income = $noCatRepository->listIncome($start, $end, $accounts);
+ $expenses = $noCatRepository->listExpenses($start, $end, $accounts);
+ $income = $noCatRepository->listIncome($start, $end, $accounts);
}
if (null !== $category) {
@@ -173,9 +173,9 @@ class CategoryController extends Controller
$opsRepository = app(OperationsRepositoryInterface::class);
$categoryId = $category->id;
// this gives us all currencies
- $collection = new Collection([$category]);
- $expenses = $opsRepository->listExpenses($start, $end, $accounts, $collection);
- $income = $opsRepository->listIncome($start, $end, $accounts, $collection);
+ $collection = new Collection([$category]);
+ $expenses = $opsRepository->listExpenses($start, $end, $accounts, $collection);
+ $income = $opsRepository->listIncome($start, $end, $accounts, $collection);
}
$currencies = array_unique(array_merge(array_keys($income), array_keys($expenses)));
$periods = app('navigation')->listOfPeriods($start, $end);
@@ -189,19 +189,19 @@ class CategoryController extends Controller
$inKey = sprintf('%d-in', $currencyId);
$chartData[$outKey]
= [
- 'label' => sprintf('%s (%s)', (string) trans('firefly.spent'), $currencyInfo['currency_name']),
- 'entries' => [],
- 'type' => 'bar',
- 'backgroundColor' => 'rgba(219, 68, 55, 0.5)', // red
- ];
+ 'label' => sprintf('%s (%s)', (string) trans('firefly.spent'), $currencyInfo['currency_name']),
+ 'entries' => [],
+ 'type' => 'bar',
+ 'backgroundColor' => 'rgba(219, 68, 55, 0.5)', // red
+ ];
$chartData[$inKey]
- = [
- 'label' => sprintf('%s (%s)', (string) trans('firefly.earned'), $currencyInfo['currency_name']),
- 'entries' => [],
- 'type' => 'bar',
- 'backgroundColor' => 'rgba(0, 141, 76, 0.5)', // green
- ];
+ = [
+ 'label' => sprintf('%s (%s)', (string) trans('firefly.earned'), $currencyInfo['currency_name']),
+ 'entries' => [],
+ 'type' => 'bar',
+ 'backgroundColor' => 'rgba(0, 141, 76, 0.5)', // green
+ ];
// loop empty periods:
foreach (array_keys($periods) as $period) {
$label = $periods[$period];
@@ -209,7 +209,7 @@ class CategoryController extends Controller
$chartData[$inKey]['entries'][$label] = '0';
}
// loop income and expenses for this category.:
- $outSet = $expenses[$currencyId]['categories'][$categoryId] ?? ['transaction_journals' => []];
+ $outSet = $expenses[$currencyId]['categories'][$categoryId] ?? ['transaction_journals' => []];
foreach ($outSet['transaction_journals'] as $journal) {
$amount = app('steam')->positive($journal['amount']);
$date = $journal['date']->isoFormat($format);
@@ -218,7 +218,7 @@ class CategoryController extends Controller
$chartData[$outKey]['entries'][$date] = bcadd($amount, $chartData[$outKey]['entries'][$date]);
}
- $inSet = $income[$currencyId]['categories'][$categoryId] ?? ['transaction_journals' => []];
+ $inSet = $income[$currencyId]['categories'][$categoryId] ?? ['transaction_journals' => []];
foreach ($inSet['transaction_journals'] as $journal) {
$amount = app('steam')->positive($journal['amount']);
$date = $journal['date']->isoFormat($format);
@@ -244,7 +244,7 @@ class CategoryController extends Controller
if ($cache->has()) {
return response()->json($cache->get());
}
- $data = $this->reportPeriodChart($accounts, $start, $end, null);
+ $data = $this->reportPeriodChart($accounts, $start, $end, null);
$cache->store($data);
@@ -259,14 +259,14 @@ class CategoryController extends Controller
*/
public function specificPeriod(Category $category, Carbon $date): JsonResponse
{
- $range = app('navigation')->getViewRange(false);
- $start = app('navigation')->startOfPeriod($date, $range);
- $end = session()->get('end');
+ $range = app('navigation')->getViewRange(false);
+ $start = app('navigation')->startOfPeriod($date, $range);
+ $end = session()->get('end');
if ($end < $start) {
[$end, $start] = [$start, $end];
}
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty($start);
$cache->addProperty($end);
$cache->addProperty($category->id);
diff --git a/app/Http/Controllers/Chart/ReportController.php b/app/Http/Controllers/Chart/ReportController.php
index d538ebbd97..cecdde2826 100644
--- a/app/Http/Controllers/Chart/ReportController.php
+++ b/app/Http/Controllers/Chart/ReportController.php
@@ -145,7 +145,7 @@ class ReportController extends Controller
$cache->addProperty($accounts);
$cache->addProperty($end);
if ($cache->has()) {
- return response()->json($cache->get());
+ return response()->json($cache->get());
}
Log::debug('Going to do operations for accounts ', $accounts->pluck('id')->toArray());
diff --git a/app/Http/Controllers/JavascriptController.php b/app/Http/Controllers/JavascriptController.php
index d0afef6dfa..7a0b271d14 100644
--- a/app/Http/Controllers/JavascriptController.php
+++ b/app/Http/Controllers/JavascriptController.php
@@ -95,7 +95,7 @@ class JavascriptController extends Controller
public function variables(Request $request, AccountRepositoryInterface $repository): Response
{
$account = $repository->find((int) $request->get('account'));
- $currency = $this->defaultCurrency;
+ $currency = $this->defaultCurrency;
if (null !== $account) {
$currency = $repository->getAccountCurrency($account) ?? $this->defaultCurrency;
}
diff --git a/app/Repositories/Category/OperationsRepository.php b/app/Repositories/Category/OperationsRepository.php
index 6741f3ffa8..bca0e084e0 100644
--- a/app/Repositories/Category/OperationsRepository.php
+++ b/app/Repositories/Category/OperationsRepository.php
@@ -63,13 +63,13 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setCategories($this->getCategories());
}
$collector->withCategoryInformation()->withAccountInformation()->withBudgetInformation();
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $categoryId = (int) $journal['category_id'];
- $categoryName = (string) $journal['category_name'];
+ $currencyId = (int) $journal['currency_id'];
+ $categoryId = (int) $journal['category_id'];
+ $categoryName = (string) $journal['category_name'];
// catch "no category" entries.
if (0 === $categoryId) {
@@ -77,7 +77,7 @@ class OperationsRepository implements OperationsRepositoryInterface
}
// info about the currency:
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'categories' => [],
'currency_id' => (string) $currencyId,
'currency_name' => $journal['currency_name'],
@@ -112,7 +112,7 @@ class OperationsRepository implements OperationsRepositoryInterface
return $array;
}
- public function setUser(null | Authenticatable | User $user): void
+ public function setUser(null|Authenticatable|User $user): void
{
if ($user instanceof User) {
$this->user = $user;
@@ -147,13 +147,13 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setCategories($this->getCategories());
}
$collector->withCategoryInformation()->withAccountInformation();
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $categoryId = (int) $journal['category_id'];
- $categoryName = (string) $journal['category_name'];
+ $currencyId = (int) $journal['currency_id'];
+ $categoryId = (int) $journal['category_id'];
+ $categoryName = (string) $journal['category_name'];
// catch "no category" entries.
if (0 === $categoryId) {
@@ -161,7 +161,7 @@ class OperationsRepository implements OperationsRepositoryInterface
}
// info about the currency:
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'categories' => [],
'currency_id' => (string) $currencyId,
'currency_name' => $journal['currency_name'],
@@ -200,7 +200,8 @@ class OperationsRepository implements OperationsRepositoryInterface
/** @var GroupCollectorInterface $collector */
$collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionType::TRANSFER])
- ->setDestinationAccounts($accounts)->excludeSourceAccounts($accounts);
+ ->setDestinationAccounts($accounts)->excludeSourceAccounts($accounts)
+ ;
if (null !== $categories && $categories->count() > 0) {
$collector->setCategories($categories);
}
@@ -208,13 +209,13 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setCategories($this->getCategories());
}
$collector->withCategoryInformation()->withAccountInformation()->withBudgetInformation();
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $categoryId = (int) $journal['category_id'];
- $categoryName = (string) $journal['category_name'];
+ $currencyId = (int) $journal['currency_id'];
+ $categoryId = (int) $journal['category_id'];
+ $categoryName = (string) $journal['category_name'];
// catch "no category" entries.
if (0 === $categoryId) {
@@ -222,7 +223,7 @@ class OperationsRepository implements OperationsRepositoryInterface
}
// info about the currency:
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'categories' => [],
'currency_id' => (string) $currencyId,
'currency_name' => $journal['currency_name'],
@@ -262,7 +263,8 @@ class OperationsRepository implements OperationsRepositoryInterface
/** @var GroupCollectorInterface $collector */
$collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionType::TRANSFER])
- ->setSourceAccounts($accounts)->excludeDestinationAccounts($accounts);
+ ->setSourceAccounts($accounts)->excludeDestinationAccounts($accounts)
+ ;
if (null !== $categories && $categories->count() > 0) {
$collector->setCategories($categories);
}
@@ -270,13 +272,13 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setCategories($this->getCategories());
}
$collector->withCategoryInformation()->withAccountInformation()->withBudgetInformation();
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $categoryId = (int) $journal['category_id'];
- $categoryName = (string) $journal['category_name'];
+ $currencyId = (int) $journal['currency_id'];
+ $categoryId = (int) $journal['category_id'];
+ $categoryName = (string) $journal['category_name'];
// catch "no category" entries.
if (0 === $categoryId) {
@@ -284,7 +286,7 @@ class OperationsRepository implements OperationsRepositoryInterface
}
// info about the currency:
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'categories' => [],
'currency_id' => (string) $currencyId,
'currency_name' => $journal['currency_name'],
@@ -325,7 +327,7 @@ class OperationsRepository implements OperationsRepositoryInterface
public function sumExpenses(Carbon $start, Carbon $end, ?Collection $accounts = null, ?Collection $categories = null): array
{
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionTypeEnum::WITHDRAWAL->value]);
// default currency information for native stuff.
@@ -339,19 +341,19 @@ class OperationsRepository implements OperationsRepositoryInterface
}
$collector->setCategories($categories);
$collector->withCategoryInformation();
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
Log::debug(sprintf('Collected %d journals', count($journals)));
foreach ($journals as $journal) {
// Almost the same as in \FireflyIII\Repositories\Budget\OperationsRepository::sumExpenses
- $amount = '0';
- $currencyId = (int) $journal['currency_id'];
- $currencyName = $journal['currency_name'];
- $currencySymbol = $journal['currency_symbol'];
- $currencyCode = $journal['currency_code'];
- $currencyDecimalPlaces = $journal['currency_decimal_places'];
+ $amount = '0';
+ $currencyId = (int) $journal['currency_id'];
+ $currencyName = $journal['currency_name'];
+ $currencySymbol = $journal['currency_symbol'];
+ $currencyCode = $journal['currency_code'];
+ $currencyDecimalPlaces = $journal['currency_decimal_places'];
if ($convertToNative) {
$amount = Amount::getAmountFromJournal($journal);
if ($default->id !== (int) $journal['currency_id'] && $default->id !== (int) $journal['foreign_currency_id']) {
@@ -376,7 +378,7 @@ class OperationsRepository implements OperationsRepositoryInterface
$amount = $journal['amount'];
}
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'sum' => '0',
'currency_id' => (string) $currencyId,
'currency_name' => $currencyName,
@@ -396,9 +398,10 @@ class OperationsRepository implements OperationsRepositoryInterface
public function sumIncome(Carbon $start, Carbon $end, ?Collection $accounts = null, ?Collection $categories = null): array
{
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)
- ->setTypes([TransactionTypeEnum::DEPOSIT->value]);
+ ->setTypes([TransactionTypeEnum::DEPOSIT->value])
+ ;
if (null !== $accounts && $accounts->count() > 0) {
$collector->setAccounts($accounts);
@@ -407,19 +410,19 @@ class OperationsRepository implements OperationsRepositoryInterface
$categories = $this->getCategories();
}
$collector->setCategories($categories);
- $journals = $collector->getExtractedJournals();
+ $journals = $collector->getExtractedJournals();
$convertToNative = app('preferences')->get('convert_to_native', false)->data;
$default = app('amount')->getDefaultCurrency();
- $array = [];
+ $array = [];
foreach ($journals as $journal) {
// Almost the same as in \FireflyIII\Repositories\Budget\OperationsRepository::sumExpenses
- $amount = '0';
- $currencyId = (int) $journal['currency_id'];
- $currencyName = $journal['currency_name'];
- $currencySymbol = $journal['currency_symbol'];
- $currencyCode = $journal['currency_code'];
- $currencyDecimalPlaces = $journal['currency_decimal_places'];
+ $amount = '0';
+ $currencyId = (int) $journal['currency_id'];
+ $currencyName = $journal['currency_name'];
+ $currencySymbol = $journal['currency_symbol'];
+ $currencyCode = $journal['currency_code'];
+ $currencyDecimalPlaces = $journal['currency_decimal_places'];
if ($convertToNative) {
$amount = Amount::getAmountFromJournal($journal);
if ($default->id !== (int) $journal['currency_id'] && $default->id !== (int) $journal['foreign_currency_id']) {
@@ -444,7 +447,7 @@ class OperationsRepository implements OperationsRepositoryInterface
$amount = $journal['amount'];
}
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'sum' => '0',
'currency_id' => (string) $currencyId,
'currency_name' => $currencyName,
@@ -466,7 +469,8 @@ class OperationsRepository implements OperationsRepositoryInterface
/** @var GroupCollectorInterface $collector */
$collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)
- ->setTypes([TransactionType::TRANSFER]);
+ ->setTypes([TransactionType::TRANSFER])
+ ;
if (null !== $accounts && $accounts->count() > 0) {
$collector->setAccounts($accounts);
@@ -475,12 +479,12 @@ class OperationsRepository implements OperationsRepositoryInterface
$categories = $this->getCategories();
}
$collector->setCategories($categories);
- $journals = $collector->getExtractedJournals();
- $array = [];
+ $journals = $collector->getExtractedJournals();
+ $array = [];
foreach ($journals as $journal) {
$currencyId = (int) $journal['currency_id'];
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'sum' => '0',
'currency_id' => (string) $currencyId,
'currency_name' => $journal['currency_name'],
diff --git a/app/Support/Chart/Category/WholePeriodChartGenerator.php b/app/Support/Chart/Category/WholePeriodChartGenerator.php
index 2b2e39b182..239015bf20 100644
--- a/app/Support/Chart/Category/WholePeriodChartGenerator.php
+++ b/app/Support/Chart/Category/WholePeriodChartGenerator.php
@@ -26,7 +26,6 @@ namespace FireflyIII\Support\Chart\Category;
use Carbon\Carbon;
use FireflyIII\Enums\AccountTypeEnum;
-use FireflyIII\Models\AccountType;
use FireflyIII\Models\Category;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
use FireflyIII\Repositories\Category\OperationsRepositoryInterface;
diff --git a/app/Support/Http/Controllers/AugumentData.php b/app/Support/Http/Controllers/AugumentData.php
index e3c39ea4b2..ca37bf480e 100644
--- a/app/Support/Http/Controllers/AugumentData.php
+++ b/app/Support/Http/Controllers/AugumentData.php
@@ -183,7 +183,7 @@ trait AugumentData
$cache->addProperty('get-limits');
if ($cache->has()) {
- return $cache->get();
+ return $cache->get();
}
$set = $blRepository->getBudgetLimits($budget, $start, $end);
@@ -191,12 +191,12 @@ trait AugumentData
$budgetCollection = new Collection([$budget]);
// merge sets based on a key, in case of convert to native
- $limits = new Collection();
+ $limits = new Collection();
/** @var BudgetLimit $entry */
foreach ($set as $entry) {
$currency = $entry->transactionCurrency;
- if($this->convertToNative) {
+ if ($this->convertToNative) {
// the sumExpenses method already handles this.
$currency = $this->defaultCurrency;
}
diff --git a/app/Support/Http/Controllers/ChartGeneration.php b/app/Support/Http/Controllers/ChartGeneration.php
index 3fea9eada1..572f0b6044 100644
--- a/app/Support/Http/Controllers/ChartGeneration.php
+++ b/app/Support/Http/Controllers/ChartGeneration.php
@@ -54,7 +54,7 @@ trait ChartGeneration
$cache->addProperty($accounts);
$cache->addProperty($convertToNative);
if ($cache->has()) {
- return $cache->get();
+ return $cache->get();
}
app('log')->debug('Regenerate chart.account.account-balance-chart from scratch.');
$locale = app('steam')->getLocale();
diff --git a/app/Support/Http/Controllers/PeriodOverview.php b/app/Support/Http/Controllers/PeriodOverview.php
index 925438b375..b66ba5747c 100644
--- a/app/Support/Http/Controllers/PeriodOverview.php
+++ b/app/Support/Http/Controllers/PeriodOverview.php
@@ -75,11 +75,11 @@ trait PeriodOverview
*/
protected function getAccountPeriodOverview(Account $account, Carbon $start, Carbon $end): array
{
- $range = app('navigation')->getViewRange(true);
+ $range = app('navigation')->getViewRange(true);
[$start, $end] = $end < $start ? [$end, $start] : [$start, $end];
// properties for cache
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty($start);
$cache->addProperty($end);
$cache->addProperty('account-show-period-entries');
@@ -89,32 +89,32 @@ trait PeriodOverview
}
/** @var array $dates */
- $dates = app('navigation')->blockPeriods($start, $end, $range);
- $entries = [];
+ $dates = app('navigation')->blockPeriods($start, $end, $range);
+ $entries = [];
// collect all expenses in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setAccounts(new Collection([$account]));
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::DEPOSIT]);
- $earnedSet = $collector->getExtractedJournals();
+ $earnedSet = $collector->getExtractedJournals();
// collect all income in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setAccounts(new Collection([$account]));
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::WITHDRAWAL]);
- $spentSet = $collector->getExtractedJournals();
+ $spentSet = $collector->getExtractedJournals();
// collect all transfers in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setAccounts(new Collection([$account]));
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::TRANSFER]);
- $transferSet = $collector->getExtractedJournals();
+ $transferSet = $collector->getExtractedJournals();
// loop dates
foreach ($dates as $currentDate) {
@@ -125,15 +125,15 @@ trait PeriodOverview
$transferredIn = $this->filterTransferredIn($account, $this->filterJournalsByDate($transferSet, $currentDate['start'], $currentDate['end']));
$entries[]
= [
- 'title' => $title,
- 'route' => route('accounts.show', [$account->id, $currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]),
+ 'title' => $title,
+ 'route' => route('accounts.show', [$account->id, $currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]),
- 'total_transactions' => count($spent) + count($earned) + count($transferredAway) + count($transferredIn),
- 'spent' => $this->groupByCurrency($spent),
- 'earned' => $this->groupByCurrency($earned),
- 'transferred_away' => $this->groupByCurrency($transferredAway),
- 'transferred_in' => $this->groupByCurrency($transferredIn),
- ];
+ 'total_transactions' => count($spent) + count($earned) + count($transferredAway) + count($transferredIn),
+ 'spent' => $this->groupByCurrency($spent),
+ 'earned' => $this->groupByCurrency($earned),
+ 'transferred_away' => $this->groupByCurrency($transferredAway),
+ 'transferred_in' => $this->groupByCurrency($transferredIn),
+ ];
}
$cache->store($entries);
@@ -197,13 +197,13 @@ trait PeriodOverview
/** @var array $journal */
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $currencyCode = $journal['currency_code'];
- $currencyName = $journal['currency_name'];
- $currencySymbol = $journal['currency_symbol'];
- $currencyDecimalPlaces = $journal['currency_decimal_places'];
- $foreignCurrencyId = $journal['foreign_currency_id'];
- $amount = $journal['amount'];
+ $currencyId = (int) $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ $currencyName = $journal['currency_name'];
+ $currencySymbol = $journal['currency_symbol'];
+ $currencyDecimalPlaces = $journal['currency_decimal_places'];
+ $foreignCurrencyId = $journal['foreign_currency_id'];
+ $amount = $journal['amount'];
if ($this->convertToNative && $currencyId !== $this->defaultCurrency->id && $foreignCurrencyId !== $this->defaultCurrency->id) {
@@ -215,7 +215,7 @@ trait PeriodOverview
$currencyDecimalPlaces = $this->defaultCurrency->decimal_places;
}
if ($this->convertToNative && $currencyId !== $this->defaultCurrency->id && $foreignCurrencyId === $this->defaultCurrency->id) {
- $currencyId = (int) $foreignCurrencyId;
+ $currencyId = (int) $foreignCurrencyId;
$currencyCode = $journal['foreign_currency_code'];
$currencyName = $journal['foreign_currency_name'];
$currencySymbol = $journal['foreign_currency_symbol'];
@@ -247,11 +247,11 @@ trait PeriodOverview
*/
protected function getCategoryPeriodOverview(Category $category, Carbon $start, Carbon $end): array
{
- $range = app('navigation')->getViewRange(true);
+ $range = app('navigation')->getViewRange(true);
[$start, $end] = $end < $start ? [$end, $start] : [$start, $end];
// properties for entries with their amounts.
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty($start);
$cache->addProperty($end);
$cache->addProperty($range);
@@ -263,32 +263,32 @@ trait PeriodOverview
}
/** @var array $dates */
- $dates = app('navigation')->blockPeriods($start, $end, $range);
- $entries = [];
+ $dates = app('navigation')->blockPeriods($start, $end, $range);
+ $entries = [];
// collect all expenses in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setCategory($category);
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::DEPOSIT]);
- $earnedSet = $collector->getExtractedJournals();
+ $earnedSet = $collector->getExtractedJournals();
// collect all income in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setCategory($category);
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::WITHDRAWAL]);
- $spentSet = $collector->getExtractedJournals();
+ $spentSet = $collector->getExtractedJournals();
// collect all transfers in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setCategory($category);
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::TRANSFER]);
- $transferSet = $collector->getExtractedJournals();
+ $transferSet = $collector->getExtractedJournals();
foreach ($dates as $currentDate) {
$spent = $this->filterJournalsByDate($spentSet, $currentDate['start'], $currentDate['end']);
$earned = $this->filterJournalsByDate($earnedSet, $currentDate['start'], $currentDate['end']);
@@ -296,17 +296,17 @@ trait PeriodOverview
$title = app('navigation')->periodShow($currentDate['end'], $currentDate['period']);
$entries[]
= [
- 'transactions' => 0,
- 'title' => $title,
- 'route' => route(
- 'categories.show',
- [$category->id, $currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]
- ),
- 'total_transactions' => count($spent) + count($earned) + count($transferred),
- 'spent' => $this->groupByCurrency($spent),
- 'earned' => $this->groupByCurrency($earned),
- 'transferred' => $this->groupByCurrency($transferred),
- ];
+ 'transactions' => 0,
+ 'title' => $title,
+ 'route' => route(
+ 'categories.show',
+ [$category->id, $currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]
+ ),
+ 'total_transactions' => count($spent) + count($earned) + count($transferred),
+ 'spent' => $this->groupByCurrency($spent),
+ 'earned' => $this->groupByCurrency($earned),
+ 'transferred' => $this->groupByCurrency($transferred),
+ ];
}
$cache->store($entries);
@@ -322,43 +322,43 @@ trait PeriodOverview
*/
protected function getNoBudgetPeriodOverview(Carbon $start, Carbon $end): array
{
- $range = app('navigation')->getViewRange(true);
+ $range = app('navigation')->getViewRange(true);
[$start, $end] = $end < $start ? [$end, $start] : [$start, $end];
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty($start);
$cache->addProperty($end);
$cache->addProperty($this->convertToNative);
$cache->addProperty('no-budget-period-entries');
if ($cache->has()) {
- return $cache->get();
+ return $cache->get();
}
/** @var array $dates */
- $dates = app('navigation')->blockPeriods($start, $end, $range);
- $entries = [];
+ $dates = app('navigation')->blockPeriods($start, $end, $range);
+ $entries = [];
// get all expenses without a budget.
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setRange($start, $end)->withoutBudget()->withAccountInformation()->setTypes([TransactionType::WITHDRAWAL]);
- $journals = $collector->getExtractedJournals();
+ $journals = $collector->getExtractedJournals();
foreach ($dates as $currentDate) {
$set = $this->filterJournalsByDate($journals, $currentDate['start'], $currentDate['end']);
$title = app('navigation')->periodShow($currentDate['end'], $currentDate['period']);
$entries[]
= [
- 'title' => $title,
- 'route' => route('budgets.no-budget', [$currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]),
- 'total_transactions' => count($set),
- 'spent' => $this->groupByCurrency($set),
- 'earned' => [],
- 'transferred_away' => [],
- 'transferred_in' => [],
- ];
+ 'title' => $title,
+ 'route' => route('budgets.no-budget', [$currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]),
+ 'total_transactions' => count($set),
+ 'spent' => $this->groupByCurrency($set),
+ 'earned' => [],
+ 'transferred_away' => [],
+ 'transferred_in' => [],
+ ];
}
$cache->store($entries);
@@ -375,38 +375,38 @@ trait PeriodOverview
protected function getNoCategoryPeriodOverview(Carbon $theDate): array
{
app('log')->debug(sprintf('Now in getNoCategoryPeriodOverview(%s)', $theDate->format('Y-m-d')));
- $range = app('navigation')->getViewRange(true);
- $first = $this->journalRepos->firstNull();
- $start = null === $first ? new Carbon() : $first->date;
- $end = clone $theDate;
- $end = app('navigation')->endOfPeriod($end, $range);
+ $range = app('navigation')->getViewRange(true);
+ $first = $this->journalRepos->firstNull();
+ $start = null === $first ? new Carbon() : $first->date;
+ $end = clone $theDate;
+ $end = app('navigation')->endOfPeriod($end, $range);
app('log')->debug(sprintf('Start for getNoCategoryPeriodOverview() is %s', $start->format('Y-m-d')));
app('log')->debug(sprintf('End for getNoCategoryPeriodOverview() is %s', $end->format('Y-m-d')));
// properties for cache
- $dates = app('navigation')->blockPeriods($start, $end, $range);
- $entries = [];
+ $dates = app('navigation')->blockPeriods($start, $end, $range);
+ $entries = [];
// collect all expenses in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->withoutCategory();
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::DEPOSIT]);
- $earnedSet = $collector->getExtractedJournals();
+ $earnedSet = $collector->getExtractedJournals();
// collect all income in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->withoutCategory();
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::WITHDRAWAL]);
- $spentSet = $collector->getExtractedJournals();
+ $spentSet = $collector->getExtractedJournals();
// collect all transfers in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->withoutCategory();
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::TRANSFER]);
@@ -420,13 +420,13 @@ trait PeriodOverview
$title = app('navigation')->periodShow($currentDate['end'], $currentDate['period']);
$entries[]
= [
- 'title' => $title,
- 'route' => route('categories.no-category', [$currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]),
- 'total_transactions' => count($spent) + count($earned) + count($transferred),
- 'spent' => $this->groupByCurrency($spent),
- 'earned' => $this->groupByCurrency($earned),
- 'transferred' => $this->groupByCurrency($transferred),
- ];
+ 'title' => $title,
+ 'route' => route('categories.no-category', [$currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]),
+ 'total_transactions' => count($spent) + count($earned) + count($transferred),
+ 'spent' => $this->groupByCurrency($spent),
+ 'earned' => $this->groupByCurrency($earned),
+ 'transferred' => $this->groupByCurrency($transferred),
+ ];
}
app('log')->debug('End of loops');
@@ -440,11 +440,11 @@ trait PeriodOverview
*/
protected function getTagPeriodOverview(Tag $tag, Carbon $start, Carbon $end): array // period overview for tags.
{
- $range = app('navigation')->getViewRange(true);
+ $range = app('navigation')->getViewRange(true);
[$start, $end] = $end < $start ? [$end, $start] : [$start, $end];
// properties for cache
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty($start);
$cache->addProperty($end);
$cache->addProperty('tag-period-entries');
@@ -454,37 +454,37 @@ trait PeriodOverview
}
/** @var array $dates */
- $dates = app('navigation')->blockPeriods($start, $end, $range);
- $entries = [];
+ $dates = app('navigation')->blockPeriods($start, $end, $range);
+ $entries = [];
// collect all expenses in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTag($tag);
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::DEPOSIT]);
- $earnedSet = $collector->getExtractedJournals();
+ $earnedSet = $collector->getExtractedJournals();
// collect all income in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTag($tag);
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::WITHDRAWAL]);
- $spentSet = $collector->getExtractedJournals();
+ $spentSet = $collector->getExtractedJournals();
// collect all transfers in this period:
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTag($tag);
$collector->setRange($start, $end);
$collector->setTypes([TransactionType::TRANSFER]);
- $transferSet = $collector->getExtractedJournals();
+ $transferSet = $collector->getExtractedJournals();
// filer all of them:
- $earnedSet = $this->filterJournalsByTag($earnedSet, $tag);
- $spentSet = $this->filterJournalsByTag($spentSet, $tag);
- $transferSet = $this->filterJournalsByTag($transferSet, $tag);
+ $earnedSet = $this->filterJournalsByTag($earnedSet, $tag);
+ $spentSet = $this->filterJournalsByTag($spentSet, $tag);
+ $transferSet = $this->filterJournalsByTag($transferSet, $tag);
foreach ($dates as $currentDate) {
$spent = $this->filterJournalsByDate($spentSet, $currentDate['start'], $currentDate['end']);
@@ -493,17 +493,17 @@ trait PeriodOverview
$title = app('navigation')->periodShow($currentDate['end'], $currentDate['period']);
$entries[]
= [
- 'transactions' => 0,
- 'title' => $title,
- 'route' => route(
- 'tags.show',
- [$tag->id, $currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]
- ),
- 'total_transactions' => count($spent) + count($earned) + count($transferred),
- 'spent' => $this->groupByCurrency($spent),
- 'earned' => $this->groupByCurrency($earned),
- 'transferred' => $this->groupByCurrency($transferred),
- ];
+ 'transactions' => 0,
+ 'title' => $title,
+ 'route' => route(
+ 'tags.show',
+ [$tag->id, $currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]
+ ),
+ 'total_transactions' => count($spent) + count($earned) + count($transferred),
+ 'spent' => $this->groupByCurrency($spent),
+ 'earned' => $this->groupByCurrency($earned),
+ 'transferred' => $this->groupByCurrency($transferred),
+ ];
}
return $entries;
@@ -513,7 +513,7 @@ trait PeriodOverview
{
$return = [];
foreach ($set as $entry) {
- $found = false;
+ $found = false;
/** @var array $localTag */
foreach ($entry['tags'] as $localTag) {
@@ -535,12 +535,12 @@ trait PeriodOverview
*/
protected function getTransactionPeriodOverview(string $transactionType, Carbon $start, Carbon $end): array
{
- $range = app('navigation')->getViewRange(true);
- $types = config(sprintf('firefly.transactionTypesByType.%s', $transactionType));
+ $range = app('navigation')->getViewRange(true);
+ $types = config(sprintf('firefly.transactionTypesByType.%s', $transactionType));
[$start, $end] = $end < $start ? [$end, $start] : [$start, $end];
// properties for cache
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty($start);
$cache->addProperty($end);
$cache->addProperty('transactions-period-entries');
@@ -550,13 +550,13 @@ trait PeriodOverview
}
/** @var array $dates */
- $dates = app('navigation')->blockPeriods($start, $end, $range);
- $entries = [];
+ $dates = app('navigation')->blockPeriods($start, $end, $range);
+ $entries = [];
// collect all journals in this period (regardless of type)
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes($types)->setRange($start, $end);
- $genericSet = $collector->getExtractedJournals();
+ $genericSet = $collector->getExtractedJournals();
foreach ($dates as $currentDate) {
$spent = [];
@@ -575,14 +575,14 @@ trait PeriodOverview
$transferred = $this->filterJournalsByDate($genericSet, $currentDate['start'], $currentDate['end']);
}
$entries[]
- = [
- 'title' => $title,
- 'route' => route('transactions.index', [$transactionType, $currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]),
- 'total_transactions' => count($spent) + count($earned) + count($transferred),
- 'spent' => $this->groupByCurrency($spent),
- 'earned' => $this->groupByCurrency($earned),
- 'transferred' => $this->groupByCurrency($transferred),
- ];
+ = [
+ 'title' => $title,
+ 'route' => route('transactions.index', [$transactionType, $currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]),
+ 'total_transactions' => count($spent) + count($earned) + count($transferred),
+ 'spent' => $this->groupByCurrency($spent),
+ 'earned' => $this->groupByCurrency($earned),
+ 'transferred' => $this->groupByCurrency($transferred),
+ ];
}
return $entries;
diff --git a/app/Support/Steam.php b/app/Support/Steam.php
index 0201aefba0..1aa9f73bf7 100644
--- a/app/Support/Steam.php
+++ b/app/Support/Steam.php
@@ -84,7 +84,7 @@ class Steam
$cache->addProperty($start);
$cache->addProperty($end);
if ($cache->has()) {
- return $cache->get();
+ return $cache->get();
}
$balances = [];
diff --git a/composer.lock b/composer.lock
index b9273f3f84..75bfaf5864 100644
--- a/composer.lock
+++ b/composer.lock
@@ -7330,12 +7330,12 @@
},
"type": "library",
"extra": {
+ "thanks": {
+ "url": "https://github.com/symfony/contracts",
+ "name": "symfony/contracts"
+ },
"branch-alias": {
"dev-main": "3.5-dev"
- },
- "thanks": {
- "name": "symfony/contracts",
- "url": "https://github.com/symfony/contracts"
}
},
"autoload": {
@@ -7637,12 +7637,12 @@
},
"type": "library",
"extra": {
+ "thanks": {
+ "url": "https://github.com/symfony/contracts",
+ "name": "symfony/contracts"
+ },
"branch-alias": {
"dev-main": "3.5-dev"
- },
- "thanks": {
- "name": "symfony/contracts",
- "url": "https://github.com/symfony/contracts"
}
},
"autoload": {
@@ -7860,12 +7860,12 @@
},
"type": "library",
"extra": {
+ "thanks": {
+ "url": "https://github.com/symfony/contracts",
+ "name": "symfony/contracts"
+ },
"branch-alias": {
"dev-main": "3.5-dev"
- },
- "thanks": {
- "name": "symfony/contracts",
- "url": "https://github.com/symfony/contracts"
}
},
"autoload": {
@@ -9670,12 +9670,12 @@
},
"type": "library",
"extra": {
+ "thanks": {
+ "url": "https://github.com/symfony/contracts",
+ "name": "symfony/contracts"
+ },
"branch-alias": {
"dev-main": "3.5-dev"
- },
- "thanks": {
- "name": "symfony/contracts",
- "url": "https://github.com/symfony/contracts"
}
},
"autoload": {
@@ -9930,12 +9930,12 @@
},
"type": "library",
"extra": {
+ "thanks": {
+ "url": "https://github.com/symfony/contracts",
+ "name": "symfony/contracts"
+ },
"branch-alias": {
"dev-main": "3.5-dev"
- },
- "thanks": {
- "name": "symfony/contracts",
- "url": "https://github.com/symfony/contracts"
}
},
"autoload": {
diff --git a/config/firefly.php b/config/firefly.php
index 604621b9c4..5968f7c992 100644
--- a/config/firefly.php
+++ b/config/firefly.php
@@ -81,7 +81,7 @@ return [
'running_balance_column' => env('USE_RUNNING_BALANCE', false),
// see cer.php for exchange rates feature flag.
],
- 'version' => 'branch-v6.2',
+ 'version' => 'develop/2024-12-27',
'api_version' => '2.1.0', // field is no longer used.
'db_version' => 25,
diff --git a/package-lock.json b/package-lock.json
index 4077e58d38..bc0e566e97 100644
--- a/package-lock.json
+++ b/package-lock.json
@@ -5663,9 +5663,9 @@
"license": "MIT"
},
"node_modules/electron-to-chromium": {
- "version": "1.5.75",
- "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.75.tgz",
- "integrity": "sha512-Lf3++DumRE/QmweGjU+ZcKqQ+3bKkU/qjaKYhIJKEOhgIO9Xs6IiAQFkfFoj+RhgDk4LUeNsLo6plExHqSyu6Q==",
+ "version": "1.5.76",
+ "resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.76.tgz",
+ "integrity": "sha512-CjVQyG7n7Sr+eBXE86HIulnL5N8xZY1sgmOPGuq/F0Rr0FJq63lg0kEtOIDfZBk44FnDLf6FUJ+dsJcuiUDdDQ==",
"dev": true,
"license": "ISC"
},
@@ -6967,6 +6967,7 @@
"url": "https://www.i18next.com/how-to/faq#i18next-is-awesome.-how-can-i-support-the-project"
}
],
+ "license": "MIT",
"dependencies": {
"@babel/runtime": "^7.23.2"
},
@@ -11272,12 +11273,13 @@
}
},
"node_modules/vite": {
- "version": "6.0.5",
- "resolved": "https://registry.npmjs.org/vite/-/vite-6.0.5.tgz",
- "integrity": "sha512-akD5IAH/ID5imgue2DYhzsEwCi0/4VKY31uhMLEYJwPP4TiUp8pL5PIK+Wo7H8qT8JY9i+pVfPydcFPYD1EL7g==",
+ "version": "6.0.6",
+ "resolved": "https://registry.npmjs.org/vite/-/vite-6.0.6.tgz",
+ "integrity": "sha512-NSjmUuckPmDU18bHz7QZ+bTYhRR0iA72cs2QAxCqDpafJ0S6qetco0LB3WW2OxlMHS0JmAv+yZ/R3uPmMyGTjQ==",
"dev": true,
+ "license": "MIT",
"dependencies": {
- "esbuild": "0.24.0",
+ "esbuild": "^0.24.2",
"postcss": "^8.4.49",
"rollup": "^4.23.0"
},
From 103b9056e4761c46641951c6e0959616679ad42d Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 06:55:17 +0100
Subject: [PATCH 133/167] Expand changelog, remove unused packages.
---
changelog.md | 35 +++
composer.json | 3 -
composer.lock | 738 +-------------------------------------------------
3 files changed, 36 insertions(+), 740 deletions(-)
diff --git a/changelog.md b/changelog.md
index 0a743732d8..2c01fec774 100644
--- a/changelog.md
+++ b/changelog.md
@@ -3,6 +3,41 @@
All notable changes to this project will be documented in this file.
This project adheres to [Semantic Versioning](http://semver.org/).
+## 6.2.0 - 2025-01-xx
+
+### Added
+
+- Multi-currency support. If you set `ENABLE_EXCHANGE_RATES=true` and optionally `ENABLE_EXTERNAL_RATES=true` Firefly III will try to calculate all foreign currencies back to your native currency. This is a work in progress, not all fields and all places will support this yet. Please check out the [documentation](#).
+- Notifications support Nfty, Pushover, Slack and Discord.
+- Many new security related notifications.
+- #5523
+- #8531
+- #8307
+- #7945
+- #6760
+- #6557
+
+### Changed
+
+- Firefly III requires PHP 8.4.
+- #9501
+- Docker container no longer runs under root.
+- "Bills" are now called "subscriptions" to better reflect their purpose.
+
+### Removed
+
+- Removed support for PHP 8.3 and lower.
+- Removed Docker support for linux/arm/v7, linux/arm/v8 and linux/386. Sorry.
+
+### Fixed
+
+- #9532
+- #7288
+
+### API
+
+- API changes related to new features are [documented](#).
+
## 6.1.25 - 2024-12-19
### Fixed
diff --git a/composer.json b/composer.json
index bfad00bff7..cbabb0f7ef 100644
--- a/composer.json
+++ b/composer.json
@@ -84,12 +84,9 @@
"bacon/bacon-qr-code": "2.*",
"diglactic/laravel-breadcrumbs": "^9",
"gdbots/query-parser": "^3.0",
- "genealabs/laravel-model-caching": "^11.0",
"guzzlehttp/guzzle": "^7.8",
"jc5/google2fa-laravel": "^2.0",
"jc5/recovery": "^2",
- "laravel-json-api/laravel": "^5.0",
- "laravel-json-api/non-eloquent": "^4.0",
"laravel-notification-channels/pushover": "^4.0",
"laravel/framework": "^11",
"laravel/passport": "^12",
diff --git a/composer.lock b/composer.lock
index 75bfaf5864..d034bb85d7 100644
--- a/composer.lock
+++ b/composer.lock
@@ -4,7 +4,7 @@
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
"This file is @generated automatically"
],
- "content-hash": "232d05ea287cfd97dde3fb95805a9b5a",
+ "content-hash": "19d10c2c3cd2c2a8d4b12d9d01a34491",
"packages": [
{
"name": "bacon/bacon-qr-code",
@@ -1182,130 +1182,6 @@
},
"time": "2021-12-05T19:44:35+00:00"
},
- {
- "name": "genealabs/laravel-model-caching",
- "version": "11.0.1",
- "source": {
- "type": "git",
- "url": "https://github.com/mikebronner/laravel-model-caching.git",
- "reference": "2a38f0f1ed3554cf2da272d66c4d08a7885f196b"
- },
- "dist": {
- "type": "zip",
- "url": "https://api.github.com/repos/mikebronner/laravel-model-caching/zipball/2a38f0f1ed3554cf2da272d66c4d08a7885f196b",
- "reference": "2a38f0f1ed3554cf2da272d66c4d08a7885f196b",
- "shasum": ""
- },
- "require": {
- "genealabs/laravel-pivot-events": "^10.0|^11.0",
- "illuminate/cache": "^10.0|^11.0",
- "illuminate/config": "^10.0|^11.0",
- "illuminate/console": "^10.0|^11.0",
- "illuminate/container": "^10.0|^11.0",
- "illuminate/database": "^10.0|^11.0",
- "illuminate/http": "^10.0|^11.0",
- "illuminate/support": "^10.0|^11.0",
- "php": ">=8.1"
- },
- "require-dev": {
- "doctrine/dbal": "^3.3",
- "fakerphp/faker": "^1.11",
- "laravel/legacy-factories": "^1.3",
- "laravel/nova": "^4.0",
- "orchestra/testbench": "^8.0|^9.0",
- "orchestra/testbench-browser-kit": "^8.0",
- "php-coveralls/php-coveralls": "^2.2",
- "phpunit/phpunit": "^10.0",
- "slevomat/coding-standard": "^7.0|^8.14",
- "squizlabs/php_codesniffer": "^3.6",
- "symfony/thanks": "^1.2"
- },
- "type": "library",
- "extra": {
- "laravel": {
- "providers": [
- "GeneaLabs\\LaravelModelCaching\\Providers\\Service"
- ]
- }
- },
- "autoload": {
- "psr-4": {
- "GeneaLabs\\LaravelModelCaching\\": "src/"
- }
- },
- "notification-url": "https://packagist.org/downloads/",
- "license": [
- "MIT"
- ],
- "authors": [
- {
- "name": "Mike Bronner",
- "email": "hello@genealabs.com"
- }
- ],
- "description": "Automatic caching for Eloquent models.",
- "support": {
- "issues": "https://github.com/mikebronner/laravel-model-caching/issues",
- "source": "https://github.com/mikebronner/laravel-model-caching/tree/11.0.1"
- },
- "time": "2024-03-14T23:34:57+00:00"
- },
- {
- "name": "genealabs/laravel-pivot-events",
- "version": "11.0.0",
- "source": {
- "type": "git",
- "url": "https://github.com/mikebronner/laravel-pivot-events.git",
- "reference": "16e974d80160774641f4323f5ffb757b79f300d3"
- },
- "dist": {
- "type": "zip",
- "url": "https://api.github.com/repos/mikebronner/laravel-pivot-events/zipball/16e974d80160774641f4323f5ffb757b79f300d3",
- "reference": "16e974d80160774641f4323f5ffb757b79f300d3",
- "shasum": ""
- },
- "require": {
- "illuminate/database": "^8.0|^9.0|^10.0|^11.0",
- "illuminate/support": "^8.0|^9.0|^10.0|^11.0"
- },
- "require-dev": {
- "orchestra/testbench": "^9.0",
- "phpunit/phpunit": "^10.5",
- "symfony/thanks": "^1.0"
- },
- "type": "library",
- "autoload": {
- "psr-4": {
- "GeneaLabs\\LaravelPivotEvents\\": "src"
- }
- },
- "notification-url": "https://packagist.org/downloads/",
- "license": [
- "MIT"
- ],
- "authors": [
- {
- "name": "Mike Bronner",
- "email": "hello@genealabs.com",
- "homepage": "https://genealabs.com",
- "role": "Developer"
- }
- ],
- "description": "This package introduces new eloquent events for sync(), attach(), detach() or updateExistingPivot() methods on BelongsToMany relation.",
- "homepage": "https://github.com/mikebronner/laravel-pivot-events",
- "keywords": [
- "eloquent events",
- "eloquent extra events",
- "laravel BelongsToMany events",
- "laravel pivot events",
- "laravel sync events"
- ],
- "support": {
- "issues": "https://github.com/mikebronner/laravel-pivot-events/issues",
- "source": "https://github.com/mikebronner/laravel-pivot-events"
- },
- "time": "2024-03-14T23:24:54+00:00"
- },
{
"name": "graham-campbell/result-type",
"version": "v1.1.3",
@@ -1934,618 +1810,6 @@
},
"time": "2022-03-31T05:55:34+00:00"
},
- {
- "name": "laravel-json-api/core",
- "version": "v5.0.1",
- "source": {
- "type": "git",
- "url": "https://github.com/laravel-json-api/core.git",
- "reference": "e2f6696580166f7b6384318e28168252c2bd20f4"
- },
- "dist": {
- "type": "zip",
- "url": "https://api.github.com/repos/laravel-json-api/core/zipball/e2f6696580166f7b6384318e28168252c2bd20f4",
- "reference": "e2f6696580166f7b6384318e28168252c2bd20f4",
- "shasum": ""
- },
- "require": {
- "ext-json": "*",
- "illuminate/auth": "^11.0",
- "illuminate/contracts": "^11.0",
- "illuminate/http": "^11.0",
- "illuminate/support": "^11.0",
- "php": "^8.2"
- },
- "require-dev": {
- "phpunit/phpunit": "^10.5"
- },
- "type": "library",
- "extra": {
- "branch-alias": {
- "dev-develop": "5.x-dev"
- }
- },
- "autoload": {
- "psr-4": {
- "LaravelJsonApi\\Core\\": "src/Core",
- "LaravelJsonApi\\Contracts\\": "src/Contracts"
- }
- },
- "notification-url": "https://packagist.org/downloads/",
- "license": [
- "MIT"
- ],
- "authors": [
- {
- "name": "Cloud Creativity Ltd",
- "email": "info@cloudcreativity.co.uk"
- },
- {
- "name": "Christopher Gammie",
- "email": "contact@gammie.co.uk"
- }
- ],
- "description": "Contracts and support classes for Laravel JSON:API packages.",
- "homepage": "https://github.com/laravel-json-api/core",
- "keywords": [
- "JSON-API",
- "jsonapi",
- "jsonapi.org",
- "laravel"
- ],
- "support": {
- "issues": "https://github.com/laravel-json-api/core/issues",
- "source": "https://github.com/laravel-json-api/core/tree/v5.0.1"
- },
- "time": "2024-11-30T16:31:42+00:00"
- },
- {
- "name": "laravel-json-api/eloquent",
- "version": "v4.4.0",
- "source": {
- "type": "git",
- "url": "https://github.com/laravel-json-api/eloquent.git",
- "reference": "fd7ebf898fb6e78bcbb8cba1a3b0e0d2554df244"
- },
- "dist": {
- "type": "zip",
- "url": "https://api.github.com/repos/laravel-json-api/eloquent/zipball/fd7ebf898fb6e78bcbb8cba1a3b0e0d2554df244",
- "reference": "fd7ebf898fb6e78bcbb8cba1a3b0e0d2554df244",
- "shasum": ""
- },
- "require": {
- "ext-json": "*",
- "illuminate/database": "^11.0",
- "illuminate/support": "^11.0",
- "laravel-json-api/core": "^4.3.2|^5.0.1",
- "php": "^8.2"
- },
- "require-dev": {
- "orchestra/testbench": "^9.0",
- "phpunit/phpunit": "^10.5"
- },
- "type": "library",
- "extra": {
- "branch-alias": {
- "dev-develop": "4.x-dev"
- }
- },
- "autoload": {
- "psr-4": {
- "LaravelJsonApi\\Eloquent\\": "src/"
- }
- },
- "notification-url": "https://packagist.org/downloads/",
- "license": [
- "MIT"
- ],
- "authors": [
- {
- "name": "Cloud Creativity Ltd",
- "email": "info@cloudcreativity.co.uk"
- },
- {
- "name": "Christopher Gammie",
- "email": "contact@gammie.co.uk"
- }
- ],
- "description": "Serialize Eloquent models as JSON:API resources.",
- "homepage": "https://github.com/laravel-json-api/eloquent",
- "keywords": [
- "JSON-API",
- "jsonapi",
- "jsonapi.org",
- "laravel"
- ],
- "support": {
- "issues": "https://github.com/laravel-json-api/eloquent/issues",
- "source": "https://github.com/laravel-json-api/eloquent/tree/v4.4.0"
- },
- "time": "2024-11-30T17:36:37+00:00"
- },
- {
- "name": "laravel-json-api/encoder-neomerx",
- "version": "v4.1.0",
- "source": {
- "type": "git",
- "url": "https://github.com/laravel-json-api/encoder-neomerx.git",
- "reference": "077c745a0c3caca535d30cacbb36b8daee29b812"
- },
- "dist": {
- "type": "zip",
- "url": "https://api.github.com/repos/laravel-json-api/encoder-neomerx/zipball/077c745a0c3caca535d30cacbb36b8daee29b812",
- "reference": "077c745a0c3caca535d30cacbb36b8daee29b812",
- "shasum": ""
- },
- "require": {
- "ext-json": "*",
- "illuminate/contracts": "^11.0",
- "illuminate/support": "^11.0",
- "laravel-json-api/core": "^4.3.2|^5.0.1",
- "laravel-json-api/neomerx-json-api": "^5.0.3",
- "php": "^8.2"
- },
- "require-dev": {
- "phpunit/phpunit": "^10.5"
- },
- "type": "library",
- "extra": {
- "laravel": {
- "providers": [
- "LaravelJsonApi\\Encoder\\Neomerx\\ServiceProvider"
- ]
- },
- "branch-alias": {
- "dev-develop": "4.x-dev"
- }
- },
- "autoload": {
- "psr-4": {
- "LaravelJsonApi\\Encoder\\Neomerx\\": "src/"
- }
- },
- "notification-url": "https://packagist.org/downloads/",
- "license": [
- "MIT"
- ],
- "authors": [
- {
- "name": "Cloud Creativity Ltd",
- "email": "info@cloudcreativity.co.uk"
- },
- {
- "name": "Christopher Gammie",
- "email": "contact@gammie.co.uk"
- }
- ],
- "description": "Encode JSON:API resources using the neomerx/json-api package.",
- "homepage": "https://github.com/laravel-json-api/encoder-neomerx",
- "keywords": [
- "JSON-API",
- "jsonapi",
- "jsonapi.org",
- "laravel"
- ],
- "support": {
- "issues": "https://github.com/laravel-json-api/encoder-neomerx/issues",
- "source": "https://github.com/laravel-json-api/encoder-neomerx/tree/v4.1.0"
- },
- "time": "2024-11-30T17:28:56+00:00"
- },
- {
- "name": "laravel-json-api/exceptions",
- "version": "v3.1.0",
- "source": {
- "type": "git",
- "url": "https://github.com/laravel-json-api/exceptions.git",
- "reference": "1969ba640de3ec288e0a447532c9b43e0941d475"
- },
- "dist": {
- "type": "zip",
- "url": "https://api.github.com/repos/laravel-json-api/exceptions/zipball/1969ba640de3ec288e0a447532c9b43e0941d475",
- "reference": "1969ba640de3ec288e0a447532c9b43e0941d475",
- "shasum": ""
- },
- "require": {
- "ext-json": "*",
- "illuminate/contracts": "^11.0",
- "illuminate/pipeline": "^11.0",
- "laravel-json-api/core": "^4.3.2|^5.0.1",
- "laravel-json-api/validation": "^4.2",
- "php": "^8.2"
- },
- "require-dev": {
- "laravel-json-api/testing": "^3.0",
- "orchestra/testbench": "^9.0",
- "phpunit/phpunit": "^10.5"
- },
- "type": "library",
- "extra": {
- "branch-alias": {
- "dev-develop": "3.x-dev"
- }
- },
- "autoload": {
- "psr-4": {
- "LaravelJsonApi\\Exceptions\\": "src/"
- }
- },
- "notification-url": "https://packagist.org/downloads/",
- "license": [
- "MIT"
- ],
- "authors": [
- {
- "name": "Cloud Creativity Ltd",
- "email": "info@cloudcreativity.co.uk"
- },
- {
- "name": "Christopher Gammie",
- "email": "contact@gammie.co.uk"
- }
- ],
- "description": "JSON:API exception parsing for Laravel applications.",
- "homepage": "https://github.com/laravel-json-api/exceptions",
- "keywords": [
- "JSON-API",
- "jsonapi",
- "jsonapi.org",
- "laravel"
- ],
- "support": {
- "issues": "https://github.com/laravel-json-api/exceptions/issues",
- "source": "https://github.com/laravel-json-api/exceptions/tree/v3.1.0"
- },
- "time": "2024-11-30T17:20:13+00:00"
- },
- {
- "name": "laravel-json-api/laravel",
- "version": "v5.0.2",
- "source": {
- "type": "git",
- "url": "https://github.com/laravel-json-api/laravel.git",
- "reference": "53045c6a55b4923e3cfadc085fd5f0b7c8c79cfc"
- },
- "dist": {
- "type": "zip",
- "url": "https://api.github.com/repos/laravel-json-api/laravel/zipball/53045c6a55b4923e3cfadc085fd5f0b7c8c79cfc",
- "reference": "53045c6a55b4923e3cfadc085fd5f0b7c8c79cfc",
- "shasum": ""
- },
- "require": {
- "ext-json": "*",
- "laravel-json-api/core": "^5.0.1",
- "laravel-json-api/eloquent": "^4.4",
- "laravel-json-api/encoder-neomerx": "^4.1",
- "laravel-json-api/exceptions": "^3.1",
- "laravel-json-api/spec": "^3.1",
- "laravel-json-api/validation": "^4.2",
- "laravel/framework": "^11.0",
- "php": "^8.2"
- },
- "require-dev": {
- "laravel-json-api/testing": "^3.0.2",
- "orchestra/testbench": "^9.0",
- "phpunit/phpunit": "^10.5"
- },
- "type": "library",
- "extra": {
- "laravel": {
- "aliases": {
- "JsonApi": "LaravelJsonApi\\Core\\Facades\\JsonApi",
- "JsonApiRoute": "LaravelJsonApi\\Laravel\\Facades\\JsonApiRoute"
- },
- "providers": [
- "LaravelJsonApi\\Laravel\\ServiceProvider"
- ]
- },
- "branch-alias": {
- "dev-develop": "5.x-dev"
- }
- },
- "autoload": {
- "psr-4": {
- "LaravelJsonApi\\Laravel\\": "src/"
- }
- },
- "notification-url": "https://packagist.org/downloads/",
- "license": [
- "MIT"
- ],
- "authors": [
- {
- "name": "Cloud Creativity Ltd",
- "email": "info@cloudcreativity.co.uk"
- },
- {
- "name": "Christopher Gammie",
- "email": "contact@gammie.co.uk"
- }
- ],
- "description": "JSON:API for Laravel applications.",
- "homepage": "https://github.com/laravel-json-api/laravel",
- "keywords": [
- "JSON-API",
- "jsonapi",
- "jsonapi.org",
- "laravel"
- ],
- "support": {
- "issues": "https://github.com/laravel-json-api/laravel/issues",
- "source": "https://github.com/laravel-json-api/laravel/tree/v5.0.2"
- },
- "time": "2024-12-03T20:43:07+00:00"
- },
- {
- "name": "laravel-json-api/neomerx-json-api",
- "version": "v5.0.3",
- "source": {
- "type": "git",
- "url": "https://github.com/laravel-json-api/neomerx-json-api.git",
- "reference": "836342be5eb4bcf6c3734c7f8e82c9ceec3be550"
- },
- "dist": {
- "type": "zip",
- "url": "https://api.github.com/repos/laravel-json-api/neomerx-json-api/zipball/836342be5eb4bcf6c3734c7f8e82c9ceec3be550",
- "reference": "836342be5eb4bcf6c3734c7f8e82c9ceec3be550",
- "shasum": ""
- },
- "require": {
- "ext-json": "*",
- "php": "^7.4|^8.0"
- },
- "require-dev": {
- "friendsofphp/php-cs-fixer": "^3.17",
- "mockery/mockery": "^1.4.4",
- "phpmd/phpmd": "^2.11.1",
- "phpunit/phpunit": "^9.5.10",
- "scrutinizer/ocular": "^1.8",
- "squizlabs/php_codesniffer": "^3.6.2"
- },
- "type": "library",
- "extra": {
- "branch-alias": {
- "dev-develop": "5.x-dev"
- }
- },
- "autoload": {
- "files": [
- "src/I18n/format.php"
- ],
- "psr-4": {
- "Neomerx\\JsonApi\\": "src/"
- }
- },
- "notification-url": "https://packagist.org/downloads/",
- "license": [
- "Apache-2.0"
- ],
- "authors": [
- {
- "name": "neomerx",
- "email": "info@neomerx.com"
- },
- {
- "name": "Christopher Gammie",
- "email": "contact@gammie.co.uk"
- }
- ],
- "description": "Framework agnostic JSON API (jsonapi.org) implementation",
- "homepage": "https://github.com/neomerx/json-api",
- "keywords": [
- "JSON-API",
- "api",
- "json",
- "jsonapi",
- "jsonapi.org",
- "neomerx"
- ],
- "support": {
- "issues": "https://github.com/neomerx/json-api/issues",
- "source": "https://github.com/laravel-json-api/neomerx-json-api/tree/v5.0.3"
- },
- "time": "2024-11-29T17:49:31+00:00"
- },
- {
- "name": "laravel-json-api/non-eloquent",
- "version": "v4.1.0",
- "source": {
- "type": "git",
- "url": "https://github.com/laravel-json-api/non-eloquent.git",
- "reference": "3a28054ba3abd38323ec7c926419fc2a229766dd"
- },
- "dist": {
- "type": "zip",
- "url": "https://api.github.com/repos/laravel-json-api/non-eloquent/zipball/3a28054ba3abd38323ec7c926419fc2a229766dd",
- "reference": "3a28054ba3abd38323ec7c926419fc2a229766dd",
- "shasum": ""
- },
- "require": {
- "laravel-json-api/core": "^4.3.2|^5.0.1",
- "php": "^8.2"
- },
- "require-dev": {
- "orchestra/testbench": "^9.0",
- "phpunit/phpunit": "^10.5"
- },
- "type": "library",
- "extra": {
- "branch-alias": {
- "dev-develop": "4.x-dev"
- }
- },
- "autoload": {
- "psr-4": {
- "LaravelJsonApi\\NonEloquent\\": "src"
- }
- },
- "notification-url": "https://packagist.org/downloads/",
- "license": [
- "MIT"
- ],
- "authors": [
- {
- "name": "Cloud Creativity Ltd",
- "email": "info@cloudcreativity.co.uk"
- },
- {
- "name": "Christopher Gammie",
- "email": "contact@gammie.co.uk"
- }
- ],
- "description": "Construct JSON:API resources for non-Eloquent classes.",
- "homepage": "https://github.com/laravel-json-api/non-eloquent",
- "keywords": [
- "JSON-API",
- "jsonapi",
- "jsonapi.org",
- "laravel"
- ],
- "support": {
- "issues": "https://github.com/laravel-json-api/non-eloquent/issues",
- "source": "https://github.com/laravel-json-api/non-eloquent/tree/v4.1.0"
- },
- "time": "2024-11-30T17:51:30+00:00"
- },
- {
- "name": "laravel-json-api/spec",
- "version": "v3.1.0",
- "source": {
- "type": "git",
- "url": "https://github.com/laravel-json-api/spec.git",
- "reference": "75a7a77de4421d58b0f38e2c94fae728b9d3690e"
- },
- "dist": {
- "type": "zip",
- "url": "https://api.github.com/repos/laravel-json-api/spec/zipball/75a7a77de4421d58b0f38e2c94fae728b9d3690e",
- "reference": "75a7a77de4421d58b0f38e2c94fae728b9d3690e",
- "shasum": ""
- },
- "require": {
- "ext-json": "*",
- "illuminate/contracts": "^11.0",
- "illuminate/pipeline": "^11.0",
- "illuminate/support": "^11.0",
- "laravel-json-api/core": "^4.3.2|^5.0.1",
- "php": "^8.2"
- },
- "require-dev": {
- "orchestra/testbench": "^9.0",
- "phpunit/phpunit": "^10.5"
- },
- "type": "library",
- "extra": {
- "laravel": {
- "providers": [
- "LaravelJsonApi\\Spec\\ServiceProvider"
- ]
- },
- "branch-alias": {
- "dev-develop": "3.x-dev"
- }
- },
- "autoload": {
- "psr-4": {
- "LaravelJsonApi\\Spec\\": "src/"
- }
- },
- "notification-url": "https://packagist.org/downloads/",
- "license": [
- "MIT"
- ],
- "authors": [
- {
- "name": "Cloud Creativity Ltd",
- "email": "info@cloudcreativity.co.uk"
- },
- {
- "name": "Christopher Gammie",
- "email": "contact@gammie.co.uk"
- }
- ],
- "description": "Validate JSON documents for compliance with the JSON:API specification.",
- "homepage": "https://github.com/laravel-json-api/spec",
- "keywords": [
- "JSON-API",
- "jsonapi",
- "jsonapi.org",
- "laravel"
- ],
- "support": {
- "issues": "https://github.com/laravel-json-api/spec/issues",
- "source": "https://github.com/laravel-json-api/spec/tree/v3.1.0"
- },
- "time": "2024-11-30T16:59:19+00:00"
- },
- {
- "name": "laravel-json-api/validation",
- "version": "v4.2.0",
- "source": {
- "type": "git",
- "url": "https://github.com/laravel-json-api/validation.git",
- "reference": "635e942e44f01186ddea1c7a29d8e2d0de2c1540"
- },
- "dist": {
- "type": "zip",
- "url": "https://api.github.com/repos/laravel-json-api/validation/zipball/635e942e44f01186ddea1c7a29d8e2d0de2c1540",
- "reference": "635e942e44f01186ddea1c7a29d8e2d0de2c1540",
- "shasum": ""
- },
- "require": {
- "ext-json": "*",
- "illuminate/contracts": "^11.0",
- "illuminate/support": "^11.0",
- "laravel-json-api/core": "^4.3.2|^5.0.1",
- "php": "^8.2"
- },
- "require-dev": {
- "orchestra/testbench": "^9.0",
- "phpunit/phpunit": "^10.5"
- },
- "type": "library",
- "extra": {
- "laravel": {
- "providers": [
- "LaravelJsonApi\\Validation\\ServiceProvider"
- ]
- },
- "branch-alias": {
- "dev-develop": "4.x-dev"
- }
- },
- "autoload": {
- "psr-4": {
- "LaravelJsonApi\\Validation\\": "src/"
- }
- },
- "notification-url": "https://packagist.org/downloads/",
- "license": [
- "MIT"
- ],
- "authors": [
- {
- "name": "Cloud Creativity Ltd",
- "email": "info@cloudcreativity.co.uk"
- },
- {
- "name": "Christopher Gammie",
- "email": "contact@gammie.co.uk"
- }
- ],
- "description": "Laravel validation for JSON:API resources.",
- "homepage": "https://github.com/laravel-json-api/validation",
- "keywords": [
- "JSON-API",
- "jsonapi",
- "jsonapi.org",
- "laravel"
- ],
- "support": {
- "issues": "https://github.com/laravel-json-api/validation/issues",
- "source": "https://github.com/laravel-json-api/validation/tree/v4.2.0"
- },
- "time": "2024-11-30T17:11:17+00:00"
- },
{
"name": "laravel-notification-channels/pushover",
"version": "4.0.0",
From 2bd97d9a99cfc2d142d516d5cd842d78e8050c23 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 07:09:25 +0100
Subject: [PATCH 134/167] Remove references to laravel json api
---
.../Controllers/JsonApi/AccountController.php | 113 --------------
app/Exceptions/Handler.php | 6 -
app/JsonApi/Rules/IsValidFilter.php | 54 -------
app/JsonApi/Rules/IsValidPage.php | 53 -------
.../AccountBalanceRepository.php | 46 ------
.../AccountBalanceResource.php | 44 ------
.../AccountBalances/AccountBalanceSchema.php | 50 ------
.../Capabilities/AccountBalanceQuery.php | 59 --------
.../V2/Accounts/AccountCollectionQuery.php | 77 ----------
app/JsonApi/V2/Accounts/AccountRepository.php | 113 --------------
app/JsonApi/V2/Accounts/AccountRequest.php | 53 -------
app/JsonApi/V2/Accounts/AccountResource.php | 83 ----------
.../V2/Accounts/AccountResourceOld.php | 115 --------------
app/JsonApi/V2/Accounts/AccountSchema.php | 112 --------------
app/JsonApi/V2/Accounts/AccountSchemaOld.php | 69 ---------
.../V2/Accounts/AccountSingleQuery.php | 45 ------
.../V2/Accounts/Capabilities/AccountQuery.php | 142 ------------------
.../V2/Accounts/Capabilities/CrudAccount.php | 61 --------
.../Capabilities/CrudAccountRelations.php | 29 ----
app/JsonApi/V2/Server.php | 53 -------
app/JsonApi/V2/Users/UserResource.php | 41 -----
app/JsonApi/V2/Users/UserSchema.php | 55 -------
app/Support/Http/Api/ParsesQueryFilters.php | 75 ---------
app/Support/JsonApi/ExpandsQuery.php | 2 -
app/Support/JsonApi/SortsCollection.php | 1 -
app/Support/JsonApi/SortsQueryResults.php | 2 -
.../JsonApi/ValidateSortParameters.php | 1 -
changelog.md | 2 +-
28 files changed, 1 insertion(+), 1555 deletions(-)
delete mode 100644 app/Api/V2/Controllers/JsonApi/AccountController.php
delete mode 100644 app/JsonApi/Rules/IsValidFilter.php
delete mode 100644 app/JsonApi/Rules/IsValidPage.php
delete mode 100644 app/JsonApi/V2/AccountBalances/AccountBalanceRepository.php
delete mode 100644 app/JsonApi/V2/AccountBalances/AccountBalanceResource.php
delete mode 100644 app/JsonApi/V2/AccountBalances/AccountBalanceSchema.php
delete mode 100644 app/JsonApi/V2/AccountBalances/Capabilities/AccountBalanceQuery.php
delete mode 100644 app/JsonApi/V2/Accounts/AccountCollectionQuery.php
delete mode 100644 app/JsonApi/V2/Accounts/AccountRepository.php
delete mode 100644 app/JsonApi/V2/Accounts/AccountRequest.php
delete mode 100644 app/JsonApi/V2/Accounts/AccountResource.php
delete mode 100644 app/JsonApi/V2/Accounts/AccountResourceOld.php
delete mode 100644 app/JsonApi/V2/Accounts/AccountSchema.php
delete mode 100644 app/JsonApi/V2/Accounts/AccountSchemaOld.php
delete mode 100644 app/JsonApi/V2/Accounts/AccountSingleQuery.php
delete mode 100644 app/JsonApi/V2/Accounts/Capabilities/AccountQuery.php
delete mode 100644 app/JsonApi/V2/Accounts/Capabilities/CrudAccount.php
delete mode 100644 app/JsonApi/V2/Accounts/Capabilities/CrudAccountRelations.php
delete mode 100644 app/JsonApi/V2/Server.php
delete mode 100644 app/JsonApi/V2/Users/UserResource.php
delete mode 100644 app/JsonApi/V2/Users/UserSchema.php
delete mode 100644 app/Support/Http/Api/ParsesQueryFilters.php
diff --git a/app/Api/V2/Controllers/JsonApi/AccountController.php b/app/Api/V2/Controllers/JsonApi/AccountController.php
deleted file mode 100644
index e9f2c8bf62..0000000000
--- a/app/Api/V2/Controllers/JsonApi/AccountController.php
+++ /dev/null
@@ -1,113 +0,0 @@
-repository()
- ->queryAll()
- ->withRequest($request)
- ->get()
- ;
-
- // do something custom...
-
- return new DataResponse($models);
- }
-
- /**
- * Fetch zero to one JSON API resource by id.
- *
- * @return Responsable|Response
- */
- public function show(AccountSchema $schema, AccountSingleQuery $request, Account $account)
- {
- Log::debug(__METHOD__);
- $model = $schema->repository()
- ->queryOne($account)
- ->withRequest($request)
- ->first()
- ;
- Log::debug(sprintf('%s again!', __METHOD__));
-
- // do something custom...
-
- return new DataResponse($model);
- }
-
- // public function readAccountBalances(AnonymousQuery $query, AccountBalanceSchema $schema, Account $account): Responsable
- // {
- // $schema = JsonApi::server()->schemas()->schemaFor('account-balances');
- //
- // $models = $schema
- // ->repository()
- // ->queryAll()
- // ->withRequest($query)
- // ->withAccount($account)
- // ->get()
- // ;
- //
- // return DataResponse::make($models);
- // }
-}
diff --git a/app/Exceptions/Handler.php b/app/Exceptions/Handler.php
index 1c7c0b5f17..e8352aa791 100644
--- a/app/Exceptions/Handler.php
+++ b/app/Exceptions/Handler.php
@@ -36,8 +36,6 @@ use Illuminate\Session\TokenMismatchException;
use Illuminate\Support\Arr;
use Illuminate\Validation\ValidationException as LaravelValidationException;
use Laravel\Passport\Exceptions\OAuthServerException as LaravelOAuthException;
-use LaravelJsonApi\Core\Exceptions\JsonApiException;
-use LaravelJsonApi\Exceptions\ExceptionParser;
use League\OAuth2\Server\Exception\OAuthServerException;
use Symfony\Component\HttpFoundation\Exception\SuspiciousOperationException;
use Symfony\Component\HttpFoundation\Response;
@@ -65,7 +63,6 @@ class Handler extends ExceptionHandler
HttpException::class,
SuspiciousOperationException::class,
BadHttpHeaderException::class,
- JsonApiException::class,
];
/**
@@ -73,9 +70,6 @@ class Handler extends ExceptionHandler
*/
public function register(): void
{
- $this->renderable(
- ExceptionParser::make()->renderable()
- );
}
/**
diff --git a/app/JsonApi/Rules/IsValidFilter.php b/app/JsonApi/Rules/IsValidFilter.php
deleted file mode 100644
index 9c8b0a4319..0000000000
--- a/app/JsonApi/Rules/IsValidFilter.php
+++ /dev/null
@@ -1,54 +0,0 @@
-allowed = $keys;
- $this->allowed[] = 'user_group_id';
- }
-
- #[\Override]
- public function validate(string $attribute, mixed $value, \Closure $fail): void
- {
- if ('filter' !== $attribute) {
- $fail('validation.bad_api_filter')->translate();
- }
- if (!is_array($value)) {
- $value = explode(',', $value);
- }
- foreach ($value as $key => $val) {
- if (!in_array($key, $this->allowed, true)) {
- $fail('validation.bad_api_filter')->translate(['filter' => $key]);
- }
- }
- }
-}
diff --git a/app/JsonApi/Rules/IsValidPage.php b/app/JsonApi/Rules/IsValidPage.php
deleted file mode 100644
index b0c1182818..0000000000
--- a/app/JsonApi/Rules/IsValidPage.php
+++ /dev/null
@@ -1,53 +0,0 @@
-allowed = $keys;
- }
-
- #[\Override]
- public function validate(string $attribute, mixed $value, \Closure $fail): void
- {
- if ('page' !== $attribute) {
- $fail('validation.bad_api_filter')->translate();
- }
- if (!is_array($value)) {
- $value = explode(',', $value);
- }
- foreach ($value as $key => $val) {
- if (!in_array($key, $this->allowed, true)) {
- $fail('validation.bad_api_page')->translate();
- }
- }
- }
-}
diff --git a/app/JsonApi/V2/AccountBalances/AccountBalanceRepository.php b/app/JsonApi/V2/AccountBalances/AccountBalanceRepository.php
deleted file mode 100644
index 38aa5bb460..0000000000
--- a/app/JsonApi/V2/AccountBalances/AccountBalanceRepository.php
+++ /dev/null
@@ -1,46 +0,0 @@
-withServer($this->server)
- ->withSchema($this->schema)
- ;
- }
-}
diff --git a/app/JsonApi/V2/AccountBalances/AccountBalanceResource.php b/app/JsonApi/V2/AccountBalances/AccountBalanceResource.php
deleted file mode 100644
index d4a6841575..0000000000
--- a/app/JsonApi/V2/AccountBalances/AccountBalanceResource.php
+++ /dev/null
@@ -1,44 +0,0 @@
- $this->resource->amount,
- 'amount' => $this->resource->amount,
- ];
- }
-
- /**
- * Get the resource id.
- */
- public function id(): string
- {
- return $this->resource->id;
- }
-
- /**
- * Get the resource's relationships.
- *
- * @param null|Request $request
- */
- public function relationships($request): iterable
- {
- return [
- $this->relation('account')->withData($this->resource->getAccount()),
- ];
- }
-}
diff --git a/app/JsonApi/V2/AccountBalances/AccountBalanceSchema.php b/app/JsonApi/V2/AccountBalances/AccountBalanceSchema.php
deleted file mode 100644
index e0c2d13bb9..0000000000
--- a/app/JsonApi/V2/AccountBalances/AccountBalanceSchema.php
+++ /dev/null
@@ -1,50 +0,0 @@
-withServer($this->server)
- ->withSchema($this)
- ;
- }
-}
diff --git a/app/JsonApi/V2/AccountBalances/Capabilities/AccountBalanceQuery.php b/app/JsonApi/V2/AccountBalances/Capabilities/AccountBalanceQuery.php
deleted file mode 100644
index 6f4b6fd581..0000000000
--- a/app/JsonApi/V2/AccountBalances/Capabilities/AccountBalanceQuery.php
+++ /dev/null
@@ -1,59 +0,0 @@
-account = $account;
-
- return $this;
- }
-}
diff --git a/app/JsonApi/V2/Accounts/AccountCollectionQuery.php b/app/JsonApi/V2/Accounts/AccountCollectionQuery.php
deleted file mode 100644
index e4fac9c4e9..0000000000
--- a/app/JsonApi/V2/Accounts/AccountCollectionQuery.php
+++ /dev/null
@@ -1,77 +0,0 @@
- [
- 'nullable',
- 'array',
- JsonApiRule::fieldSets(),
- ],
- 'userGroupId' => [
- 'nullable',
- 'integer',
- new IsAllowedGroupAction(Account::class, request()->method()),
- ],
- 'startPeriod' => [
- 'nullable',
- 'date',
- new IsDateOrTime(),
- new IsValidDateRange(),
- ],
- 'endPeriod' => [
- 'nullable',
- 'date',
- new IsDateOrTime(),
- new IsValidDateRange(),
- ],
- 'filter' => [
- 'nullable',
- 'array',
- JsonApiRule::filter($validFilters),
- new IsValidAccountType(),
- ],
- 'include' => [
- 'nullable',
- 'string',
- JsonApiRule::includePaths(),
- ],
- 'page' => [
- 'nullable',
- 'array',
- JsonApiRule::page(),
- ],
- 'sort' => [
- 'nullable',
- 'string',
- JsonApiRule::sort(),
- ],
- 'withCount' => [
- 'nullable',
- 'string',
- JsonApiRule::countable(),
- ],
- ];
- }
-}
diff --git a/app/JsonApi/V2/Accounts/AccountRepository.php b/app/JsonApi/V2/Accounts/AccountRepository.php
deleted file mode 100644
index 039f52c355..0000000000
--- a/app/JsonApi/V2/Accounts/AccountRepository.php
+++ /dev/null
@@ -1,113 +0,0 @@
-enrichSingle($account);
- }
-
- public function queryAll(): Capabilities\AccountQuery
- {
- Log::debug(__METHOD__);
-
- return Capabilities\AccountQuery::make()
- ->withUserGroup($this->userGroup)
- ->withServer($this->server)
- ->withSchema($this->schema)
- ;
- }
-
- protected function crud(): Capabilities\CrudAccount
- {
- Log::debug(__METHOD__);
-
- return Capabilities\CrudAccount::make();
- }
-
- /**
- * TODO piggy banks
- * TODO transactions
- */
- protected function relations(): CrudRelations
- {
- Log::debug(__METHOD__);
-
- return Capabilities\CrudAccountRelations::make();
- }
-}
diff --git a/app/JsonApi/V2/Accounts/AccountRequest.php b/app/JsonApi/V2/Accounts/AccountRequest.php
deleted file mode 100644
index faf9cf9b78..0000000000
--- a/app/JsonApi/V2/Accounts/AccountRequest.php
+++ /dev/null
@@ -1,53 +0,0 @@
-convertString('type');
- // var_dump($types);exit;
-
- return [
- 'name' => ['required', 'max:1024', 'min:1'], // , new IsUniqueAccount()
- 'account_type' => ['required', 'max:1024', 'min:1', sprintf('in:%s', $types)],
- // 'iban' => ['iban', 'nullable', new UniqueIban(null, $type)],
- // 'bic' => 'bic|nullable',
- // 'account_number' => ['min:1', 'max:255', 'nullable', new UniqueAccountNumber(null, $type)],
- // 'opening_balance' => 'numeric|required_with:opening_balance_date|nullable',
- // 'opening_balance_date' => 'date|required_with:opening_balance|nullable',
- // 'virtual_balance' => 'numeric|nullable',
- // 'order' => 'numeric|nullable',
- // 'currency_id' => 'numeric|exists:transaction_currencies,id',
- // 'currency_code' => 'min:3|max:3|exists:transaction_currencies,code',
- // 'active' => [new IsBoolean()],
- // 'include_net_worth' => [new IsBoolean()],
- // 'account_role' => sprintf('nullable|in:%s|required_if:type,asset', $accountRoles),
- // 'credit_card_type' => sprintf('nullable|in:%s|required_if:account_role,ccAsset', $ccPaymentTypes),
- // 'monthly_payment_date' => 'nullable|date|required_if:account_role,ccAsset|required_if:credit_card_type,monthlyFull',
- // 'liability_type' => 'nullable|required_if:type,liability|required_if:type,liabilities|in:loan,debt,mortgage',
- // 'liability_amount' => ['required_with:liability_start_date', new IsValidPositiveAmount()],
- // 'liability_start_date' => 'required_with:liability_amount|date',
- // 'liability_direction' => 'nullable|required_if:type,liability|required_if:type,liabilities|in:credit,debit',
- // 'interest' => 'min:0|max:100|numeric',
- // 'interest_period' => sprintf('nullable|in:%s', implode(',', config('firefly.interest_periods'))),
- // 'notes' => 'min:0|max:32768',
- ];
- }
-}
diff --git a/app/JsonApi/V2/Accounts/AccountResource.php b/app/JsonApi/V2/Accounts/AccountResource.php
deleted file mode 100644
index c88e7405b7..0000000000
--- a/app/JsonApi/V2/Accounts/AccountResource.php
+++ /dev/null
@@ -1,83 +0,0 @@
- $this->resource->created_at,
- 'updated_at' => $this->resource->updated_at,
- 'name' => $this->resource->name,
- 'active' => $this->resource->active,
- 'order' => $this->resource->order,
- 'iban' => $this->resource->iban,
- 'account_type' => $this->resource->account_type_string,
- 'account_role' => $this->resource->account_role,
- 'account_number' => '' === $this->resource->account_number ? null : $this->resource->account_number,
-
- // currency (if the account has a currency setting, otherwise NULL).
- 'currency_id' => $this->resource->currency_id,
- 'currency_name' => $this->resource->currency_name,
- 'currency_code' => $this->resource->currency_code,
- 'currency_symbol' => $this->resource->currency_symbol,
- 'currency_decimal_places' => $this->resource->currency_decimal_places,
- 'is_multi_currency' => '1' === $this->resource->is_multi_currency,
-
- // balances
- 'balance' => $this->resource->balance,
- 'native_balance' => $this->resource->native_balance,
-
- // liability things
- 'liability_direction' => $this->resource->liability_direction,
- 'interest' => $this->resource->interest,
- 'interest_period' => $this->resource->interest_period,
- 'current_debt' => $this->resource->current_debt, // TODO may be removed in the future.
-
- // other things
- 'last_activity' => $this->resource->last_activity,
-
- // object group
- 'object_group_id' => $this->resource->object_group_id,
- 'object_group_title' => $this->resource->object_group_title,
- 'object_group_order' => $this->resource->object_group_order,
- ];
- }
-
- /**
- * Get the resource id.
- */
- public function id(): string
- {
- return (string) $this->resource->id;
- }
-
- /**
- * Get the resource's relationships.
- *
- * @param null|Request $request
- */
- public function relationships($request): iterable
- {
- return [
- $this->relation('user')->withData($this->resource->user),
- ];
- }
-}
diff --git a/app/JsonApi/V2/Accounts/AccountResourceOld.php b/app/JsonApi/V2/Accounts/AccountResourceOld.php
deleted file mode 100644
index 5e2298b873..0000000000
--- a/app/JsonApi/V2/Accounts/AccountResourceOld.php
+++ /dev/null
@@ -1,115 +0,0 @@
- $this->resource->created_at,
- 'updated_at' => $this->resource->updated_at,
- 'name' => $this->resource->name,
-
- // 'virtual_balance' => $this->resource->virtual_balance,
- // 'native_balance' => $this->resource->native_balance,
- // 'user' => $this->resource->user_array,
- // 'balances' => []
- //
-
- // balance (in currency, on date)
- // 'current_balance' => $this->resource->current_balance,
- // 'current_balance' => app('steam')->bcround(app('steam')->balance($account, $date), $decimalPlaces),
- // 'current_balance_date' => $date->toAtomString(),
-
- // 'notes' => $this->repository->getNoteText($account),
- // 'monthly_payment_date' => $monthlyPaymentDate,
- // 'credit_card_type' => $creditCardType,
- // 'account_number' => $this->repository->getMetaValue($account, 'account_number'),
- // 'bic' => $this->repository->getMetaValue($account, 'BIC'),
- // 'opening_balance' => $openingBalance,
- // 'opening_balance_date' => $openingBalanceDate,
- // 'liability_type' => $liabilityType,
- // 'liability_direction' => $liabilityDirection,
- // 'interest' => $interest,
- // 'interest_period' => $interestPeriod,
- // 'current_debt' => $this->repository->getMetaValue($account, 'current_debt'),
- // 'include_net_worth' => $includeNetWorth,
- // 'longitude' => $longitude,
- // 'latitude' => $latitude,
- // 'zoom_level' => $zoomLevel,
-
- // 'order' => $order,
-
- // 'native_currency_id' => (string) $this->default->id,
- // 'native_currency_code' => $this->default->code,
- // 'native_currency_symbol' => $this->default->symbol,
- // 'native_currency_decimal_places' => $this->default->decimal_places,
- //
- // // balance:
- // 'current_balance' => $balance,
- // 'native_current_balance' => $nativeBalance,
- // 'current_balance_date' => $this->getDate()->endOfDay()->toAtomString(),
- //
- // // balance difference
- // 'balance_difference' => $balanceDiff,
- // 'native_balance_difference' => $nativeBalanceDiff,
- // 'balance_difference_start' => $diffStart,
- // 'balance_difference_end' => $diffEnd,
- //
- //
- // // liability stuff
- // 'liability_type' => $liabilityType,
- //
- // // object group
- // 'object_group_id' => null !== $objectGroupId ? (string) $objectGroupId : null,
- // 'object_group_order' => $objectGroupOrder,
- // 'object_group_title' => $objectGroupTitle,
- // 'notes' => $this->repository->getNoteText($account),
- // 'monthly_payment_date' => $monthlyPaymentDate,
- // 'credit_card_type' => $creditCardType,
- // 'bic' => $this->repository->getMetaValue($account, 'BIC'),
- // 'virtual_balance' => number_format((float) $account->virtual_balance, $decimalPlaces, '.', ''),
- // 'opening_balance' => $openingBalance,
- // 'opening_balance_date' => $openingBalanceDate,
- // 'include_net_worth' => $includeNetWorth,
- // 'longitude' => $longitude,
- // 'latitude' => $latitude,
- // 'zoom_level' => $zoomLevel,
- ];
- }
-
- /**
- * Get the resource's relationships.
- *
- * @param null|Request $request
- */
- public function relationships($request): iterable
- {
- return [
- $this->relation('user')->withData($this->resource->user),
- $this->relation('currency')->withData($this->resource->transactionCurrency),
- // $this->relation('account_balances')->withData($this->resource->balances),
- ];
- }
-}
diff --git a/app/JsonApi/V2/Accounts/AccountSchema.php b/app/JsonApi/V2/Accounts/AccountSchema.php
deleted file mode 100644
index 707b722b1a..0000000000
--- a/app/JsonApi/V2/Accounts/AccountSchema.php
+++ /dev/null
@@ -1,112 +0,0 @@
-sortable(),
- Attribute::make('active')->sortable(),
- Attribute::make('order')->sortable(),
- Attribute::make('iban')->sortable(),
- Attribute::make('account_type'),
- Attribute::make('account_role'),
- Attribute::make('account_number')->sortable(),
-
- // currency
- Attribute::make('currency_id'),
- Attribute::make('currency_name'),
- Attribute::make('currency_code'),
- Attribute::make('currency_symbol'),
- Attribute::make('currency_decimal_places'),
- Attribute::make('is_multi_currency'),
-
- // balance
- Attribute::make('balance')->sortable(),
- Attribute::make('native_balance')->sortable(),
-
- // liability things
- Attribute::make('liability_direction'),
- Attribute::make('interest'),
- Attribute::make('interest_period'),
- // Attribute::make('current_debt')->sortable(),
-
- // TODO credit card fields.
-
- // dynamic data
- Attribute::make('last_activity')->sortable(),
- Attribute::make('balance_difference')->sortable(), // only used for sort.
-
- // group
- Attribute::make('object_group_id'),
- Attribute::make('object_group_title'),
- Attribute::make('object_group_order'),
-
- // relations.
- HasOne::make('user')->readOnly(),
- ];
- }
-
- /**
- * Get the resource filters.
- */
- public function filters(): array
- {
- Log::debug(__METHOD__);
- $array = [];
- $config = config('api.valid_api_filters')[Account::class];
- foreach ($config as $entry) {
- $array[] = Filter::make($entry);
- }
-
- return $array;
- }
-
- public function pagination(): EnumerablePagination
- {
- Log::debug(__METHOD__);
-
- return EnumerablePagination::make();
- }
-
- public function repository(): AccountRepository
- {
- Log::debug(__METHOD__);
- $this->setUserGroup($this->server->getUsergroup());
-
- return AccountRepository::make()
- ->withServer($this->server)
- ->withSchema($this)
- ->withUserGroup($this->userGroup)
- ;
- }
-}
diff --git a/app/JsonApi/V2/Accounts/AccountSchemaOld.php b/app/JsonApi/V2/Accounts/AccountSchemaOld.php
deleted file mode 100644
index 9494cb937b..0000000000
--- a/app/JsonApi/V2/Accounts/AccountSchemaOld.php
+++ /dev/null
@@ -1,69 +0,0 @@
-sortable()->readOnly(),
- DateTime::make('updated_at')->sortable()->readOnly(),
- Str::make('name')->sortable(),
- // Str::make('account_type'),
- // Str::make('virtual_balance'),
- // Str::make('iban'),
- // Boolean::make('active'),
- // Number::make('order'),
- HasOne::make('user')->readOnly(),
- // HasMany::make('account_balances'),
- ];
- }
-
- /**
- * Filters mentioned here can be used to filter the results.
- * TODO write down exactly how this works.
- */
- public function filters(): array
- {
- return [
- WhereIdIn::make($this),
- ];
- }
-
- /**
- * Get the resource paginator.
- */
- public function pagination(): ?Paginator
- {
- return PagePagination::make();
- }
-}
diff --git a/app/JsonApi/V2/Accounts/AccountSingleQuery.php b/app/JsonApi/V2/Accounts/AccountSingleQuery.php
deleted file mode 100644
index b6729dc444..0000000000
--- a/app/JsonApi/V2/Accounts/AccountSingleQuery.php
+++ /dev/null
@@ -1,45 +0,0 @@
- [
- 'nullable',
- 'array',
- JsonApiRule::fieldSets(),
- ],
- 'filter' => [
- 'nullable',
- 'array',
- JsonApiRule::filter()->forget('id'),
- ],
- 'include' => [
- 'nullable',
- 'string',
- JsonApiRule::includePaths(),
- ],
- 'page' => JsonApiRule::notSupported(),
- 'sort' => JsonApiRule::notSupported(),
- 'withCount' => [
- 'nullable',
- 'string',
- JsonApiRule::countable(),
- ],
- ];
- }
-}
diff --git a/app/JsonApi/V2/Accounts/Capabilities/AccountQuery.php b/app/JsonApi/V2/Accounts/Capabilities/AccountQuery.php
deleted file mode 100644
index efd2dae2de..0000000000
--- a/app/JsonApi/V2/Accounts/Capabilities/AccountQuery.php
+++ /dev/null
@@ -1,142 +0,0 @@
-queryParameters->sortFields();
-
- // collect pagination based on the page
- $pagination = $this->filtersPagination($this->queryParameters->page());
-
- // check if we need all accounts, regardless of pagination
- // This is necessary when the user wants to sort on specific params.
- $needsAll = $this->needsFullDataset(Account::class, $sort);
-
- // params that were not recognised, may be my own custom stuff.
- $otherParams = $this->getOtherParams($this->queryParameters->unrecognisedParameters());
-
- // start the query
- $query = $this->userGroup->accounts();
-
- // add sort and filter parameters to the query.
- $query = $this->addSortParams(Account::class, $query, $sort);
- $query = $this->addFilterParams(Account::class, $query, $this->queryParameters->filter());
-
- // collect the result.
- $collection = $query->get(['accounts.*']);
- // sort the data after the query, and return it right away.
- $collection = $this->sortCollection(Account::class, $collection, $sort);
-
- // if the entire collection needs to be enriched and sorted, do so now:
- $totalCount = $collection->count();
- Log::debug(sprintf('Total is %d', $totalCount));
- if ($needsAll) {
- Log::debug('Needs the entire collection');
- // enrich the entire collection
- $enrichment = new AccountEnrichment();
- $enrichment->setStart($otherParams['start'] ?? null);
- $enrichment->setEnd($otherParams['end'] ?? null);
- $collection = $enrichment->enrich($collection);
-
- // TODO sort the set based on post-query sort options:
- $collection = $this->postQuerySort(Account::class, $collection, $sort);
-
- // take the current page from the enriched set.
- $currentPage = $collection->skip(($pagination['number'] - 1) * $pagination['size'])->take($pagination['size']);
- }
- if (!$needsAll) {
- Log::debug('Needs only partial collection');
- // take from the collection the filtered page + page number:
- $currentPage = $collection->skip(($pagination['number'] - 1) * $pagination['size'])->take($pagination['size']);
-
- // enrich only the current page.
- $enrichment = new AccountEnrichment();
- $enrichment->setStart($otherParams['start'] ?? null);
- $enrichment->setEnd($otherParams['end'] ?? null);
- $currentPage = $enrichment->enrich($currentPage);
- }
- // get current page?
- Log::debug(sprintf('Skip %d, take %d', ($pagination['number'] - 1) * $pagination['size'], $pagination['size']));
- // $currentPage = $collection->skip(($pagination['number'] - 1) * $pagination['size'])->take($pagination['size']);
- Log::debug(sprintf('New collection size: %d', $currentPage->count()));
-
- // TODO add filters after the query, if there are filters that cannot be applied to the database
- // TODO same for sort things.
-
- return new LengthAwarePaginator($currentPage, $totalCount, $pagination['size'], $pagination['number']);
- }
-
- #[\Override]
- public function getOrPaginate(?array $page): iterable
- {
- exit('here weare');
- // TODO: Implement getOrPaginate() method.
- }
-
- #[\Override]
- public function paginate(array $page): Page
- {
- exit('here weare');
- // TODO: Implement paginate() method.
- }
-}
diff --git a/app/JsonApi/V2/Accounts/Capabilities/CrudAccount.php b/app/JsonApi/V2/Accounts/Capabilities/CrudAccount.php
deleted file mode 100644
index aec8e399dc..0000000000
--- a/app/JsonApi/V2/Accounts/Capabilities/CrudAccount.php
+++ /dev/null
@@ -1,61 +0,0 @@
-getOtherParams($this->request->query->all());
-
- Log::debug(__METHOD__);
- // enrich the collected data
- $enrichment = new AccountEnrichment();
-
- // set start and date, if present.
- $enrichment->setStart($otherParams['start'] ?? null);
- $enrichment->setEnd($otherParams['end'] ?? null);
-
- return $enrichment->enrichSingle($account);
- }
-}
diff --git a/app/JsonApi/V2/Accounts/Capabilities/CrudAccountRelations.php b/app/JsonApi/V2/Accounts/Capabilities/CrudAccountRelations.php
deleted file mode 100644
index 0386b9b62d..0000000000
--- a/app/JsonApi/V2/Accounts/Capabilities/CrudAccountRelations.php
+++ /dev/null
@@ -1,29 +0,0 @@
-detectUserGroup();
- $this->setUserGroup($res);
- }
-
- /**
- * Get the server's list of schemas.
- */
- protected function allSchemas(): array
- {
- // Log::debug(__METHOD__);
-
- return [
- AccountSchema::class,
- UserSchema::class,
- // AccountBalanceSchema::class,
- ];
- }
-}
diff --git a/app/JsonApi/V2/Users/UserResource.php b/app/JsonApi/V2/Users/UserResource.php
deleted file mode 100644
index 137325e65d..0000000000
--- a/app/JsonApi/V2/Users/UserResource.php
+++ /dev/null
@@ -1,41 +0,0 @@
- $this->resource->created_at,
- 'updated_at' => $this->resource->updated_at,
- 'email' => $this->resource->email,
- ];
- }
-
- /**
- * Get the resource's relationships.
- *
- * @param null|Request $request
- */
- public function relationships($request): iterable
- {
- return [
- // @TODO
- ];
- }
-}
diff --git a/app/JsonApi/V2/Users/UserSchema.php b/app/JsonApi/V2/Users/UserSchema.php
deleted file mode 100644
index 8a32b34676..0000000000
--- a/app/JsonApi/V2/Users/UserSchema.php
+++ /dev/null
@@ -1,55 +0,0 @@
-sortable()->readOnly(),
- DateTime::make('updated_at')->sortable()->readOnly(),
- Str::make('email'),
- HasMany::make('accounts'),
- ];
- }
-
- /**
- * Get the resource filters.
- */
- public function filters(): array
- {
- return [
- WhereIdIn::make($this),
- ];
- }
-
- /**
- * Get the resource paginator.
- */
- public function pagination(): ?Paginator
- {
- return PagePagination::make();
- }
-}
diff --git a/app/Support/Http/Api/ParsesQueryFilters.php b/app/Support/Http/Api/ParsesQueryFilters.php
deleted file mode 100644
index a3252eebee..0000000000
--- a/app/Support/Http/Api/ParsesQueryFilters.php
+++ /dev/null
@@ -1,75 +0,0 @@
-filter()?->value($field, []) ?? [];
-
- return is_string($array) ? [$array] : $array;
- }
-
- private function dateOrToday(QueryParameters $parameters, string $field): Carbon
- {
- $date = today();
-
- $value = $parameters->filter()?->value($field, date('Y-m-d'));
-
- if (is_array($value)) {
- Log::error(sprintf('Multiple values for date field "%s". Using first value.', $field));
- $value = $value[0];
- }
-
- try {
- $date = Carbon::createFromFormat('Y-m-d', $value, config('app.timezone'));
- } catch (InvalidFormatException $e) {
- Log::debug(sprintf('Invalid date format in request. Using today: %s', $e->getMessage()));
- }
-
- return $date;
- }
-
- private function integerFromQueryParams(QueryParameters $parameters, string $field, int $default): int
- {
- return (int) ($parameters->page()[$field] ?? $default);
- }
-
- private function stringFromFilterParams(QueryParameters $parameters, string $field, string $default): string
- {
- return (string) $parameters->filter()?->value($field, $default) ?? $default;
- }
-
- private function stringFromQueryParams(QueryParameters $parameters, string $field, string $default): string
- {
- return (string) ($parameters->page()[$field] ?? $default);
- }
-}
diff --git a/app/Support/JsonApi/ExpandsQuery.php b/app/Support/JsonApi/ExpandsQuery.php
index 5599efae5e..2062eb9e7d 100644
--- a/app/Support/JsonApi/ExpandsQuery.php
+++ b/app/Support/JsonApi/ExpandsQuery.php
@@ -28,8 +28,6 @@ use FireflyIII\Models\Account;
use FireflyIII\Support\Http\Api\AccountFilter;
use Illuminate\Contracts\Database\Eloquent\Builder;
use Illuminate\Support\Facades\Log;
-use LaravelJsonApi\Core\Query\FilterParameters;
-use LaravelJsonApi\Core\Query\SortFields;
trait ExpandsQuery
{
diff --git a/app/Support/JsonApi/SortsCollection.php b/app/Support/JsonApi/SortsCollection.php
index 1a58c1a621..30f0d0315b 100644
--- a/app/Support/JsonApi/SortsCollection.php
+++ b/app/Support/JsonApi/SortsCollection.php
@@ -26,7 +26,6 @@ namespace FireflyIII\Support\JsonApi;
use Illuminate\Support\Collection;
use Illuminate\Support\Facades\Log;
-use LaravelJsonApi\Core\Query\SortFields;
trait SortsCollection
{
diff --git a/app/Support/JsonApi/SortsQueryResults.php b/app/Support/JsonApi/SortsQueryResults.php
index 9c5539aa3b..17d8370405 100644
--- a/app/Support/JsonApi/SortsQueryResults.php
+++ b/app/Support/JsonApi/SortsQueryResults.php
@@ -27,8 +27,6 @@ namespace FireflyIII\Support\JsonApi;
use FireflyIII\Models\Account;
use Illuminate\Support\Collection;
use Illuminate\Support\Facades\Log;
-use LaravelJsonApi\Core\Query\SortField;
-use LaravelJsonApi\Core\Query\SortFields;
trait SortsQueryResults
{
diff --git a/app/Support/JsonApi/ValidateSortParameters.php b/app/Support/JsonApi/ValidateSortParameters.php
index c2fda7ecf2..79ae9c461e 100644
--- a/app/Support/JsonApi/ValidateSortParameters.php
+++ b/app/Support/JsonApi/ValidateSortParameters.php
@@ -25,7 +25,6 @@ declare(strict_types=1);
namespace FireflyIII\Support\JsonApi;
use Illuminate\Support\Facades\Log;
-use LaravelJsonApi\Core\Query\SortFields;
trait ValidateSortParameters
{
diff --git a/changelog.md b/changelog.md
index 2c01fec774..450bc5b765 100644
--- a/changelog.md
+++ b/changelog.md
@@ -7,7 +7,7 @@ This project adheres to [Semantic Versioning](http://semver.org/).
### Added
-- Multi-currency support. If you set `ENABLE_EXCHANGE_RATES=true` and optionally `ENABLE_EXTERNAL_RATES=true` Firefly III will try to calculate all foreign currencies back to your native currency. This is a work in progress, not all fields and all places will support this yet. Please check out the [documentation](#).
+- Multi-currency support. If you set `ENABLE_EXCHANGE_RATES=true` and optionally `ENABLE_EXTERNAL_RATES=true` Firefly III will try to calculate all foreign currencies back to your native currency. This is a work in progress, not all fields and all places will support this yet. Please check out the [documentation](https://docs.firefly-iii.org/explanation/financial-concepts/exchange-rates/).
- Notifications support Nfty, Pushover, Slack and Discord.
- Many new security related notifications.
- #5523
From 89ab360391d367720e8c269c6646a180eed9bb7b Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 07:10:33 +0100
Subject: [PATCH 135/167] Remove reference to cacheable models
---
app/Models/Account.php | 2 --
app/Models/Transaction.php | 2 --
2 files changed, 4 deletions(-)
diff --git a/app/Models/Account.php b/app/Models/Account.php
index 541949e718..dbe1dd9388 100644
--- a/app/Models/Account.php
+++ b/app/Models/Account.php
@@ -26,7 +26,6 @@ namespace FireflyIII\Models;
use FireflyIII\Support\Models\ReturnsIntegerIdTrait;
use FireflyIII\Support\Models\ReturnsIntegerUserIdTrait;
use FireflyIII\User;
-use GeneaLabs\LaravelModelCaching\Traits\Cachable;
use Illuminate\Database\Eloquent\Builder as EloquentBuilder;
use Illuminate\Database\Eloquent\Casts\Attribute;
use Illuminate\Database\Eloquent\Factories\HasFactory;
@@ -44,7 +43,6 @@ use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
*/
class Account extends Model
{
- use Cachable;
use HasFactory;
use ReturnsIntegerIdTrait;
use ReturnsIntegerUserIdTrait;
diff --git a/app/Models/Transaction.php b/app/Models/Transaction.php
index fe817abb60..793e0e7652 100644
--- a/app/Models/Transaction.php
+++ b/app/Models/Transaction.php
@@ -25,7 +25,6 @@ namespace FireflyIII\Models;
use Carbon\Carbon;
use FireflyIII\Support\Models\ReturnsIntegerIdTrait;
-use GeneaLabs\LaravelModelCaching\Traits\Cachable;
use Illuminate\Database\Eloquent\Builder;
use Illuminate\Database\Eloquent\Casts\Attribute;
use Illuminate\Database\Eloquent\Factories\HasFactory;
@@ -39,7 +38,6 @@ use Illuminate\Database\Eloquent\SoftDeletes;
*/
class Transaction extends Model
{
- use Cachable;
use HasFactory;
use ReturnsIntegerIdTrait;
use SoftDeletes;
From 0a089efcac591bcad0c52b732372faedf2d3e580 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 07:35:20 +0100
Subject: [PATCH 136/167] Clean up commands.
---
app/Api/V1/Controllers/Controller.php | 6 +-
.../Controllers/Summary/BasicController.php | 4 +-
.../Correction/CorrectsNativeAmounts.php | 4 ++
.../Upgrade/AddsTransactionIdentifiers.php | 3 -
.../Upgrade/RemovesDatabaseDecryption.php | 1 -
.../Upgrade/UpgradesAccountCurrencies.php | 3 -
.../Upgrade/UpgradesAccountMetaData.php | 3 -
.../Commands/Upgrade/UpgradesAttachments.php | 3 -
.../Commands/Upgrade/UpgradesBillsToRules.php | 3 -
.../Commands/Upgrade/UpgradesBudgetLimits.php | 3 -
.../Upgrade/UpgradesCreditCardLiabilities.php | 4 --
.../Commands/Upgrade/UpgradesDatabase.php | 1 -
.../Upgrade/UpgradesJournalMetaData.php | 2 +-
.../Commands/Upgrade/UpgradesJournalNotes.php | 3 -
.../Upgrade/UpgradesRecurrenceMetaData.php | 3 -
.../Upgrade/UpgradesRecurrenceType.php | 67 -------------------
.../Commands/Upgrade/UpgradesToGroups.php | 6 --
.../Upgrade/UpgradesTransferCurrencies.php | 6 --
app/Handlers/Observer/AccountObserver.php | 4 ++
app/Handlers/Observer/AutoBudgetObserver.php | 4 ++
.../Observer/AvailableBudgetObserver.php | 4 ++
app/Handlers/Observer/BillObserver.php | 4 ++
app/Handlers/Observer/BudgetLimitObserver.php | 3 +
.../Observer/PiggyBankEventObserver.php | 4 ++
app/Handlers/Observer/PiggyBankObserver.php | 1 +
app/Handlers/Observer/TransactionObserver.php | 4 ++
app/Helpers/Report/NetWorth.php | 2 +-
app/Http/Controllers/Controller.php | 3 +-
.../ExchangeRates/IndexController.php | 4 ++
app/Repositories/Bill/BillRepository.php | 4 +-
.../Budget/AvailableBudgetRepository.php | 5 +-
.../Budget/OperationsRepository.php | 4 +-
.../Category/NoCategoryRepository.php | 4 +-
.../Category/OperationsRepository.php | 8 +--
app/Support/Amount.php | 65 ++++++++++--------
.../Http/Controllers/ChartGeneration.php | 3 +-
app/Support/Steam.php | 4 +-
app/Support/Twig/General.php | 2 +-
resources/views/partials/menu-sidebar.twig | 2 +
resources/views/preferences/index.twig | 4 +-
40 files changed, 105 insertions(+), 162 deletions(-)
delete mode 100644 app/Console/Commands/Upgrade/UpgradesRecurrenceType.php
diff --git a/app/Api/V1/Controllers/Controller.php b/app/Api/V1/Controllers/Controller.php
index 50f0f6786a..862fa08867 100644
--- a/app/Api/V1/Controllers/Controller.php
+++ b/app/Api/V1/Controllers/Controller.php
@@ -28,6 +28,8 @@ use Carbon\Carbon;
use Carbon\Exceptions\InvalidDateException;
use Carbon\Exceptions\InvalidFormatException;
use FireflyIII\Models\Preference;
+use FireflyIII\Support\Facades\Amount;
+use FireflyIII\Support\Facades\Steam;
use FireflyIII\User;
use Illuminate\Foundation\Auth\Access\AuthorizesRequests;
use Illuminate\Foundation\Bus\DispatchesJobs;
@@ -68,8 +70,8 @@ abstract class Controller extends BaseController
function ($request, $next) {
$this->parameters = $this->getParameters();
if (auth()->check()) {
- $language = app('steam')->getLanguage();
- $this->convertToNative = app('preferences')->get('convert_to_native', false)->data;
+ $language = Steam::getLanguage();
+ $this->convertToNative = Amount::convertToNative();
app()->setLocale($language);
}
diff --git a/app/Api/V1/Controllers/Summary/BasicController.php b/app/Api/V1/Controllers/Summary/BasicController.php
index cce6a7dc4a..9dcb45b576 100644
--- a/app/Api/V1/Controllers/Summary/BasicController.php
+++ b/app/Api/V1/Controllers/Summary/BasicController.php
@@ -123,8 +123,8 @@ class BasicController extends Controller
private function getBalanceInformation(Carbon $start, Carbon $end): array
{
// some config settings
- $convertToNative = app('preferences')->get('convert_to_native', false)->data;
- $default = app('amount')->getDefaultCurrency();
+ $convertToNative = Amount::convertToNative();
+ $default = Amount::getDefaultCurrency();
// prep some arrays:
$incomes = [];
$expenses = [];
diff --git a/app/Console/Commands/Correction/CorrectsNativeAmounts.php b/app/Console/Commands/Correction/CorrectsNativeAmounts.php
index 04b896b7bf..bf5d7e98ec 100644
--- a/app/Console/Commands/Correction/CorrectsNativeAmounts.php
+++ b/app/Console/Commands/Correction/CorrectsNativeAmounts.php
@@ -59,6 +59,10 @@ class CorrectsNativeAmounts extends Command
*/
public function handle(): int
{
+ if(!config('cer.enabled')) {
+ $this->friendlyInfo('This command will not run because currency exchange rates are disabled.');
+ return 0;
+ }
Log::debug('Will update all native amounts. This may take some time.');
$this->friendlyWarning('Recalculating native amounts for all objects. This may take some time!');
diff --git a/app/Console/Commands/Upgrade/AddsTransactionIdentifiers.php b/app/Console/Commands/Upgrade/AddsTransactionIdentifiers.php
index f425abe9f9..281078dee2 100644
--- a/app/Console/Commands/Upgrade/AddsTransactionIdentifiers.php
+++ b/app/Console/Commands/Upgrade/AddsTransactionIdentifiers.php
@@ -76,9 +76,6 @@ class AddsTransactionIdentifiers extends Command
$this->updateJournalIdentifiers($journal);
}
- if (0 === $this->count) {
- $this->friendlyPositive('All split journal transaction identifiers are OK.');
- }
if (0 !== $this->count) {
$this->friendlyInfo(sprintf('Fixed %d split journal transaction identifier(s).', $this->count));
}
diff --git a/app/Console/Commands/Upgrade/RemovesDatabaseDecryption.php b/app/Console/Commands/Upgrade/RemovesDatabaseDecryption.php
index a8eab8c9a7..29f12ff34a 100644
--- a/app/Console/Commands/Upgrade/RemovesDatabaseDecryption.php
+++ b/app/Console/Commands/Upgrade/RemovesDatabaseDecryption.php
@@ -70,7 +70,6 @@ class RemovesDatabaseDecryption extends Command
private function decryptTable(string $table, array $fields): void
{
if ($this->isDecrypted($table)) {
- $this->friendlyInfo(sprintf('No decryption required for table "%s".', $table));
return;
}
diff --git a/app/Console/Commands/Upgrade/UpgradesAccountCurrencies.php b/app/Console/Commands/Upgrade/UpgradesAccountCurrencies.php
index d4f6495c46..89ef7e5b9b 100644
--- a/app/Console/Commands/Upgrade/UpgradesAccountCurrencies.php
+++ b/app/Console/Commands/Upgrade/UpgradesAccountCurrencies.php
@@ -62,9 +62,6 @@ class UpgradesAccountCurrencies extends Command
}
$this->updateAccountCurrencies();
- if (0 === $this->count) {
- $this->friendlyPositive('All account currencies are OK.');
- }
if (0 !== $this->count) {
$this->friendlyInfo(sprintf('Corrected %d account(s).', $this->count));
}
diff --git a/app/Console/Commands/Upgrade/UpgradesAccountMetaData.php b/app/Console/Commands/Upgrade/UpgradesAccountMetaData.php
index 8ccbfd63de..d181e41e22 100644
--- a/app/Console/Commands/Upgrade/UpgradesAccountMetaData.php
+++ b/app/Console/Commands/Upgrade/UpgradesAccountMetaData.php
@@ -73,9 +73,6 @@ class UpgradesAccountMetaData extends Command
$this->markAsExecuted();
- if (0 === $count) {
- $this->friendlyPositive('All account meta is OK.');
- }
if (0 !== $count) {
$this->friendlyInfo(sprintf('Renamed %d account meta entries (entry).', $count));
}
diff --git a/app/Console/Commands/Upgrade/UpgradesAttachments.php b/app/Console/Commands/Upgrade/UpgradesAttachments.php
index 93f4e628b7..c3e0d32eb9 100644
--- a/app/Console/Commands/Upgrade/UpgradesAttachments.php
+++ b/app/Console/Commands/Upgrade/UpgradesAttachments.php
@@ -79,9 +79,6 @@ class UpgradesAttachments extends Command
++$count;
}
}
- if (0 === $count) {
- $this->friendlyPositive('All attachments are OK.');
- }
if (0 !== $count) {
$this->friendlyInfo(sprintf('Updated %d attachment(s).', $count));
}
diff --git a/app/Console/Commands/Upgrade/UpgradesBillsToRules.php b/app/Console/Commands/Upgrade/UpgradesBillsToRules.php
index de70c8e761..1e2398c2be 100644
--- a/app/Console/Commands/Upgrade/UpgradesBillsToRules.php
+++ b/app/Console/Commands/Upgrade/UpgradesBillsToRules.php
@@ -73,9 +73,6 @@ class UpgradesBillsToRules extends Command
$this->migrateUser($user);
}
- if (0 === $this->count) {
- $this->friendlyPositive('All bills are OK.');
- }
if (0 !== $this->count) {
$this->friendlyInfo(sprintf('Verified and fixed %d bill(s).', $this->count));
}
diff --git a/app/Console/Commands/Upgrade/UpgradesBudgetLimits.php b/app/Console/Commands/Upgrade/UpgradesBudgetLimits.php
index 98b4020d78..c94fe0d7dd 100644
--- a/app/Console/Commands/Upgrade/UpgradesBudgetLimits.php
+++ b/app/Console/Commands/Upgrade/UpgradesBudgetLimits.php
@@ -77,9 +77,6 @@ class UpgradesBudgetLimits extends Command
}
}
}
- if (0 === $count) {
- $this->friendlyPositive('All budget limits are OK.');
- }
$this->markAsExecuted();
return 0;
diff --git a/app/Console/Commands/Upgrade/UpgradesCreditCardLiabilities.php b/app/Console/Commands/Upgrade/UpgradesCreditCardLiabilities.php
index 33c8acfa90..f8db7c06a9 100644
--- a/app/Console/Commands/Upgrade/UpgradesCreditCardLiabilities.php
+++ b/app/Console/Commands/Upgrade/UpgradesCreditCardLiabilities.php
@@ -55,7 +55,6 @@ class UpgradesCreditCardLiabilities extends Command
$ccType = AccountType::where('type', AccountType::CREDITCARD)->first();
$debtType = AccountType::where('type', AccountType::DEBT)->first();
if (null === $ccType || null === $debtType) {
- $this->friendlyPositive('No incorrectly stored credit card liabilities.');
$this->markAsExecuted();
return 0;
@@ -73,9 +72,6 @@ class UpgradesCreditCardLiabilities extends Command
'Credit card liability types are no longer supported and have been converted to generic debts. See: https://bit.ly/FF3-credit-cards'
);
}
- if (0 === $accounts->count()) {
- $this->friendlyPositive('No incorrectly stored credit card liabilities.');
- }
$this->markAsExecuted();
return 0;
diff --git a/app/Console/Commands/Upgrade/UpgradesDatabase.php b/app/Console/Commands/Upgrade/UpgradesDatabase.php
index fb24640cbc..b09c15f657 100644
--- a/app/Console/Commands/Upgrade/UpgradesDatabase.php
+++ b/app/Console/Commands/Upgrade/UpgradesDatabase.php
@@ -57,7 +57,6 @@ class UpgradesDatabase extends Command
'upgrade:480-account-meta',
'upgrade:481-recurrence-meta',
'upgrade:500-tag-locations',
- 'upgrade:550-recurrence-type',
'upgrade:560-liabilities',
'upgrade:600-liabilities',
'upgrade:550-budget-limit-periods',
diff --git a/app/Console/Commands/Upgrade/UpgradesJournalMetaData.php b/app/Console/Commands/Upgrade/UpgradesJournalMetaData.php
index 325de12feb..e6145dc023 100644
--- a/app/Console/Commands/Upgrade/UpgradesJournalMetaData.php
+++ b/app/Console/Commands/Upgrade/UpgradesJournalMetaData.php
@@ -68,7 +68,7 @@ class UpgradesJournalMetaData extends Command
private function isMigrated(): bool
{
- $configVar = app('fireflyconfig')->get(self::CONFIG_NAME, false);
+ $configVar = app('fireflyconfig')->get(UpgradesToGroups::CONFIG_NAME, false);
return (bool) $configVar->data;
}
diff --git a/app/Console/Commands/Upgrade/UpgradesJournalNotes.php b/app/Console/Commands/Upgrade/UpgradesJournalNotes.php
index e638b4144b..788cf1f6c1 100644
--- a/app/Console/Commands/Upgrade/UpgradesJournalNotes.php
+++ b/app/Console/Commands/Upgrade/UpgradesJournalNotes.php
@@ -72,9 +72,6 @@ class UpgradesJournalNotes extends Command
++$count;
}
- if (0 === $count) {
- $this->friendlyPositive('No notes to migrate.');
- }
if (0 !== $count) {
$this->friendlyInfo(sprintf('Migrated %d note(s).', $count));
}
diff --git a/app/Console/Commands/Upgrade/UpgradesRecurrenceMetaData.php b/app/Console/Commands/Upgrade/UpgradesRecurrenceMetaData.php
index 2f64a2bdd2..d20f763945 100644
--- a/app/Console/Commands/Upgrade/UpgradesRecurrenceMetaData.php
+++ b/app/Console/Commands/Upgrade/UpgradesRecurrenceMetaData.php
@@ -52,9 +52,6 @@ class UpgradesRecurrenceMetaData extends Command
}
$count = $this->migrateMetaData();
- if (0 === $count) {
- $this->friendlyPositive('No recurrence meta data migrated.');
- }
if ($count > 0) {
$this->friendlyInfo(sprintf('Migrated %d meta data entries', $count));
}
diff --git a/app/Console/Commands/Upgrade/UpgradesRecurrenceType.php b/app/Console/Commands/Upgrade/UpgradesRecurrenceType.php
deleted file mode 100644
index c03376af23..0000000000
--- a/app/Console/Commands/Upgrade/UpgradesRecurrenceType.php
+++ /dev/null
@@ -1,67 +0,0 @@
-.
- */
-
-declare(strict_types=1);
-
-namespace FireflyIII\Console\Commands\Upgrade;
-
-use FireflyIII\Console\Commands\ShowsFriendlyMessages;
-use Illuminate\Console\Command;
-
-class UpgradesRecurrenceType extends Command
-{
- use ShowsFriendlyMessages;
-
- public const string CONFIG_NAME = '550_migrate_recurrence_type';
-
- protected $description = 'Migrate transaction type of recurring transaction.';
-
- protected $signature = 'upgrade:550-recurrence-type {--F|force : Force the execution of this command.}';
-
- /**
- * Execute the console command.
- */
- public function handle(): int
- {
- if ($this->isExecuted() && true !== $this->option('force')) {
- $this->friendlyInfo('This command has already been executed.');
-
- return 0;
- }
- $this->friendlyWarning('This command has been disabled.');
- $this->markAsExecuted();
-
- return 0;
- }
-
- private function isExecuted(): bool
- {
- $configVar = app('fireflyconfig')->get(self::CONFIG_NAME, false);
-
- return (bool) $configVar?->data;
- }
-
- private function markAsExecuted(): void
- {
- app('fireflyconfig')->set(self::CONFIG_NAME, true);
- }
-}
diff --git a/app/Console/Commands/Upgrade/UpgradesToGroups.php b/app/Console/Commands/Upgrade/UpgradesToGroups.php
index c0c7cf3e10..bf3113f788 100644
--- a/app/Console/Commands/Upgrade/UpgradesToGroups.php
+++ b/app/Console/Commands/Upgrade/UpgradesToGroups.php
@@ -72,9 +72,6 @@ class UpgradesToGroups extends Command
if (0 !== $this->count) {
$this->friendlyInfo(sprintf('Migrated %d transaction journal(s).', $this->count));
}
- if (0 === $this->count) {
- $this->friendlyPositive('No journals to migrate to groups.');
- }
$this->markAsMigrated();
return 0;
@@ -363,9 +360,6 @@ class UpgradesToGroups extends Command
$this->giveGroup($array);
}
}
- if (0 === $total) {
- $this->friendlyPositive('No need to convert transaction journals.');
- }
}
private function giveGroup(array $array): void
diff --git a/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php b/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php
index a51ec5a95c..5fe4d06696 100644
--- a/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php
+++ b/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php
@@ -69,12 +69,6 @@ class UpgradesTransferCurrencies extends Command
$this->startUpdateRoutine();
$this->markAsExecuted();
- if (0 === $this->count) {
- $this->friendlyPositive('All transfers have correct currency information.');
-
- return 0;
- }
-
$this->friendlyInfo(sprintf('Verified currency information of %d transfer(s).', $this->count));
return 0;
diff --git a/app/Handlers/Observer/AccountObserver.php b/app/Handlers/Observer/AccountObserver.php
index a319fc79f5..e321b102e6 100644
--- a/app/Handlers/Observer/AccountObserver.php
+++ b/app/Handlers/Observer/AccountObserver.php
@@ -27,6 +27,7 @@ namespace FireflyIII\Handlers\Observer;
use FireflyIII\Models\Account;
use FireflyIII\Models\PiggyBank;
use FireflyIII\Repositories\UserGroups\Account\AccountRepositoryInterface;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Http\Api\ExchangeRateConverter;
use Illuminate\Support\Facades\Log;
@@ -43,6 +44,9 @@ class AccountObserver
private function updateNativeAmount(Account $account): void
{
+ if(!Amount::convertToNative($account->user)) {
+ return;
+ }
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($account->user->userGroup);
$repository = app(AccountRepositoryInterface::class);
$currency = $repository->getAccountCurrency($account);
diff --git a/app/Handlers/Observer/AutoBudgetObserver.php b/app/Handlers/Observer/AutoBudgetObserver.php
index 9193bc06a9..e4a911653f 100644
--- a/app/Handlers/Observer/AutoBudgetObserver.php
+++ b/app/Handlers/Observer/AutoBudgetObserver.php
@@ -25,6 +25,7 @@ declare(strict_types=1);
namespace FireflyIII\Handlers\Observer;
use FireflyIII\Models\AutoBudget;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Http\Api\ExchangeRateConverter;
use Illuminate\Support\Facades\Log;
@@ -44,6 +45,9 @@ class AutoBudgetObserver
private function updateNativeAmount(AutoBudget $autoBudget): void
{
+ if(!Amount::convertToNative($autoBudget->budget->user)) {
+ return;
+ }
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($autoBudget->budget->user->userGroup);
$autoBudget->native_amount = null;
if ($autoBudget->transactionCurrency->id !== $userCurrency->id) {
diff --git a/app/Handlers/Observer/AvailableBudgetObserver.php b/app/Handlers/Observer/AvailableBudgetObserver.php
index e7102aa6c5..d5d03fe31c 100644
--- a/app/Handlers/Observer/AvailableBudgetObserver.php
+++ b/app/Handlers/Observer/AvailableBudgetObserver.php
@@ -25,6 +25,7 @@ declare(strict_types=1);
namespace FireflyIII\Handlers\Observer;
use FireflyIII\Models\AvailableBudget;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Http\Api\ExchangeRateConverter;
use Illuminate\Support\Facades\Log;
@@ -44,6 +45,9 @@ class AvailableBudgetObserver
private function updateNativeAmount(AvailableBudget $availableBudget): void
{
+ if(!Amount::convertToNative($availableBudget->user)) {
+ return;
+ }
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($availableBudget->user->userGroup);
$availableBudget->native_amount = null;
if ($availableBudget->transactionCurrency->id !== $userCurrency->id) {
diff --git a/app/Handlers/Observer/BillObserver.php b/app/Handlers/Observer/BillObserver.php
index 5bcba3cfcf..262ed250bc 100644
--- a/app/Handlers/Observer/BillObserver.php
+++ b/app/Handlers/Observer/BillObserver.php
@@ -24,6 +24,7 @@ declare(strict_types=1);
namespace FireflyIII\Handlers\Observer;
use FireflyIII\Models\Bill;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Http\Api\ExchangeRateConverter;
use Illuminate\Support\Facades\Log;
@@ -55,6 +56,9 @@ class BillObserver
private function updateNativeAmount(Bill $bill): void
{
+ if(!Amount::convertToNative($bill->user)) {
+ return;
+ }
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($bill->user->userGroup);
$bill->native_amount_min = null;
$bill->native_amount_max = null;
diff --git a/app/Handlers/Observer/BudgetLimitObserver.php b/app/Handlers/Observer/BudgetLimitObserver.php
index ec3f49a209..e9e0cf5337 100644
--- a/app/Handlers/Observer/BudgetLimitObserver.php
+++ b/app/Handlers/Observer/BudgetLimitObserver.php
@@ -44,6 +44,9 @@ class BudgetLimitObserver
private function updateNativeAmount(BudgetLimit $budgetLimit): void
{
+ if(!Amount::convertToNative($budgetLimit->budget->user)) {
+ return;
+ }
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($budgetLimit->budget->user->userGroup);
$budgetLimit->native_amount = null;
if ($budgetLimit->transactionCurrency->id !== $userCurrency->id) {
diff --git a/app/Handlers/Observer/PiggyBankEventObserver.php b/app/Handlers/Observer/PiggyBankEventObserver.php
index 6afcf69f82..7ed4b2fae3 100644
--- a/app/Handlers/Observer/PiggyBankEventObserver.php
+++ b/app/Handlers/Observer/PiggyBankEventObserver.php
@@ -25,6 +25,7 @@ declare(strict_types=1);
namespace FireflyIII\Handlers\Observer;
use FireflyIII\Models\PiggyBankEvent;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Http\Api\ExchangeRateConverter;
use Illuminate\Support\Facades\Log;
@@ -44,6 +45,9 @@ class PiggyBankEventObserver
private function updateNativeAmount(PiggyBankEvent $event): void
{
+ if(!Amount::convertToNative($event->piggyBank->accounts()->first()->user)) {
+ return;
+ }
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($event->piggyBank->accounts()->first()->user->userGroup);
$event->native_amount = null;
if ($event->piggyBank->transactionCurrency->id !== $userCurrency->id) {
diff --git a/app/Handlers/Observer/PiggyBankObserver.php b/app/Handlers/Observer/PiggyBankObserver.php
index b66d5d7bd0..cd8acc327d 100644
--- a/app/Handlers/Observer/PiggyBankObserver.php
+++ b/app/Handlers/Observer/PiggyBankObserver.php
@@ -78,6 +78,7 @@ class PiggyBankObserver
if ($piggyBank->transactionCurrency->id !== $userCurrency->id) {
$converter = new ExchangeRateConverter();
$converter->setIgnoreSettings(true);
+ $converter->setUserGroup($group);
$piggyBank->native_target_amount = $converter->convert($piggyBank->transactionCurrency, $userCurrency, today(), $piggyBank->target_amount);
}
$piggyBank->saveQuietly();
diff --git a/app/Handlers/Observer/TransactionObserver.php b/app/Handlers/Observer/TransactionObserver.php
index 8c79d83ac5..d4d79548da 100644
--- a/app/Handlers/Observer/TransactionObserver.php
+++ b/app/Handlers/Observer/TransactionObserver.php
@@ -24,6 +24,7 @@ declare(strict_types=1);
namespace FireflyIII\Handlers\Observer;
use FireflyIII\Models\Transaction;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Http\Api\ExchangeRateConverter;
use FireflyIII\Support\Models\AccountBalanceCalculator;
use Illuminate\Support\Facades\Log;
@@ -67,6 +68,9 @@ class TransactionObserver
private function updateNativeAmount(Transaction $transaction): void
{
+ if(!Amount::convertToNative($transaction->transactionJournal->user)) {
+ return;
+ }
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($transaction->transactionJournal->user->userGroup);
$transaction->native_amount = null;
$transaction->native_foreign_amount = null;
diff --git a/app/Helpers/Report/NetWorth.php b/app/Helpers/Report/NetWorth.php
index 9b70e4b713..85bb500406 100644
--- a/app/Helpers/Report/NetWorth.php
+++ b/app/Helpers/Report/NetWorth.php
@@ -66,7 +66,7 @@ class NetWorth implements NetWorthInterface
public function byAccounts(Collection $accounts, Carbon $date): array
{
// start in the past, end in the future? use $date
- $convertToNative = app('preferences')->get('convert_to_native', false)->data;
+ $convertToNative = Amount::convertToNative();
$ids = implode(',', $accounts->pluck('id')->toArray());
$cache = new CacheProperties();
$cache->addProperty($date);
diff --git a/app/Http/Controllers/Controller.php b/app/Http/Controllers/Controller.php
index 7853d56457..1dcdbe3be8 100644
--- a/app/Http/Controllers/Controller.php
+++ b/app/Http/Controllers/Controller.php
@@ -24,6 +24,7 @@ declare(strict_types=1);
namespace FireflyIII\Http\Controllers;
use FireflyIII\Models\TransactionCurrency;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Facades\Steam;
use FireflyIII\Support\Http\Controllers\RequestInformation;
use FireflyIII\Support\Http\Controllers\UserNavigation;
@@ -121,7 +122,7 @@ abstract class Controller extends BaseController
$language = Steam::getLanguage();
$locale = Steam::getLocale();
$darkMode = app('preferences')->get('darkMode', 'browser')->data;
- $this->convertToNative =app('preferences')->get('convert_to_native', false)->data;
+ $this->convertToNative =Amount::convertToNative();
$page = $this->getPageName();
$shownDemo = $this->hasSeenDemo();
View::share('language', $language);
diff --git a/app/Http/Controllers/ExchangeRates/IndexController.php b/app/Http/Controllers/ExchangeRates/IndexController.php
index 793a8466db..880ed1ffd1 100644
--- a/app/Http/Controllers/ExchangeRates/IndexController.php
+++ b/app/Http/Controllers/ExchangeRates/IndexController.php
@@ -27,6 +27,7 @@ namespace FireflyIII\Http\Controllers\ExchangeRates;
use FireflyIII\Http\Controllers\Controller;
use FireflyIII\Models\TransactionCurrency;
use Illuminate\View\View;
+use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
class IndexController extends Controller
{
@@ -46,6 +47,9 @@ class IndexController extends Controller
return $next($request);
}
);
+ if(!config('cer.enabled')) {
+ throw new NotFoundHttpException();
+ }
}
public function index(): View
diff --git a/app/Repositories/Bill/BillRepository.php b/app/Repositories/Bill/BillRepository.php
index 955f8f1f16..5015776d3f 100644
--- a/app/Repositories/Bill/BillRepository.php
+++ b/app/Repositories/Bill/BillRepository.php
@@ -527,7 +527,7 @@ class BillRepository implements BillRepositoryInterface
Log::debug(sprintf('sumPaidInRange from %s to %s', $start->toW3cString(), $end->toW3cString()));
$bills = $this->getActiveBills();
$return = [];
- $convertToNative = app('preferences')->getForUser($this->user, 'convert_to_native', false)->data;
+ $convertToNative = Amount::convertToNative($this->user);
$default = app('amount')->getDefaultCurrency();
/** @var Bill $bill */
@@ -572,7 +572,7 @@ class BillRepository implements BillRepositoryInterface
app('log')->debug(sprintf('Now in sumUnpaidInRange("%s", "%s")', $start->format('Y-m-d'), $end->format('Y-m-d')));
$bills = $this->getActiveBills();
$return = [];
- $convertToNative = app('preferences')->getForUser($this->user, 'convert_to_native', false)->data;
+ $convertToNative = Amount::convertToNative($this->user);
$default = app('amount')->getDefaultCurrency();
/** @var Bill $bill */
diff --git a/app/Repositories/Budget/AvailableBudgetRepository.php b/app/Repositories/Budget/AvailableBudgetRepository.php
index ff14595d01..becbf2a079 100644
--- a/app/Repositories/Budget/AvailableBudgetRepository.php
+++ b/app/Repositories/Budget/AvailableBudgetRepository.php
@@ -27,6 +27,7 @@ namespace FireflyIII\Repositories\Budget;
use Carbon\Carbon;
use FireflyIII\Models\AvailableBudget;
use FireflyIII\Models\TransactionCurrency;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Database\Eloquent\Builder;
@@ -134,8 +135,8 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
;
// use native amount if necessary?
- $convertToNative = app('preferences')->getForUser($this->user, 'convert_to_native', false)->data;
- $default = app('amount')->getDefaultCurrency();
+ $convertToNative = Amount::convertToNative($this->user);
+ $default = Amount::getDefaultCurrency();
/** @var AvailableBudget $availableBudget */
foreach ($availableBudgets as $availableBudget) {
diff --git a/app/Repositories/Budget/OperationsRepository.php b/app/Repositories/Budget/OperationsRepository.php
index e222fa5f10..fe695fa062 100644
--- a/app/Repositories/Budget/OperationsRepository.php
+++ b/app/Repositories/Budget/OperationsRepository.php
@@ -223,8 +223,8 @@ class OperationsRepository implements OperationsRepositoryInterface
$selection = new Collection();
// default currency information for native stuff.
- $convertToNative = app('preferences')->get('convert_to_native', false)->data;
- $default = app('amount')->getDefaultCurrency();
+ $convertToNative = Amount::convertToNative($this->user);
+ $default = Amount::getDefaultCurrency();
/** @var Account $account */
foreach ($subset as $account) {
diff --git a/app/Repositories/Category/NoCategoryRepository.php b/app/Repositories/Category/NoCategoryRepository.php
index 9b6fca8aec..18a7b2a783 100644
--- a/app/Repositories/Category/NoCategoryRepository.php
+++ b/app/Repositories/Category/NoCategoryRepository.php
@@ -154,8 +154,8 @@ class NoCategoryRepository implements NoCategoryRepositoryInterface
$journals = $collector->getExtractedJournals();
$array = [];
// default currency information for native stuff.
- $convertToNative = app('preferences')->get('convert_to_native', false)->data;
- $default = app('amount')->getDefaultCurrency();
+ $convertToNative = Amount::convertToNative($this->user);;
+ $default = Amount::getDefaultCurrency();
foreach ($journals as $journal) {
// Almost the same as in \FireflyIII\Repositories\Budget\OperationsRepository::sumExpenses
diff --git a/app/Repositories/Category/OperationsRepository.php b/app/Repositories/Category/OperationsRepository.php
index bca0e084e0..598214e8b7 100644
--- a/app/Repositories/Category/OperationsRepository.php
+++ b/app/Repositories/Category/OperationsRepository.php
@@ -331,8 +331,8 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionTypeEnum::WITHDRAWAL->value]);
// default currency information for native stuff.
- $convertToNative = app('preferences')->get('convert_to_native', false)->data;
- $default = app('amount')->getDefaultCurrency();
+ $convertToNative = Amount::convertToNative($this->user);;
+ $default = Amount::getDefaultCurrency();
if (null !== $accounts && $accounts->count() > 0) {
$collector->setAccounts($accounts);
}
@@ -411,8 +411,8 @@ class OperationsRepository implements OperationsRepositoryInterface
}
$collector->setCategories($categories);
$journals = $collector->getExtractedJournals();
- $convertToNative = app('preferences')->get('convert_to_native', false)->data;
- $default = app('amount')->getDefaultCurrency();
+ $convertToNative = Amount::convertToNative($this->user);;
+ $default = Amount::getDefaultCurrency();
$array = [];
foreach ($journals as $journal) {
diff --git a/app/Support/Amount.php b/app/Support/Amount.php
index 2bfc6fb070..33ddc22b93 100644
--- a/app/Support/Amount.php
+++ b/app/Support/Amount.php
@@ -30,7 +30,6 @@ use FireflyIII\Models\TransactionJournal;
use FireflyIII\Models\UserGroup;
use FireflyIII\User;
use Illuminate\Support\Collection;
-use Illuminate\Support\Facades\Log;
/**
* Class Amount.
@@ -54,13 +53,13 @@ class Amount
*/
public function getAmountFromJournal(array $journal): string
{
- $convertToNative = app('preferences')->get('convert_to_native', false)->data;
- $currency = app('amount')->getDefaultCurrency();
+ $convertToNative = $this->convertToNative();
+ $currency = $this->getDefaultCurrency();
$field = $convertToNative && $currency->id !== $journal['currency_id'] ? 'native_amount' : 'amount';
$amount = $journal[$field] ?? '0';
// Log::debug(sprintf('Field is %s, amount is %s', $field, $amount));
// fallback, the transaction has a foreign amount in $currency.
- if ($convertToNative && null !== $journal['foreign_amount'] && $currency->id === (int)$journal['foreign_currency_id']) {
+ if ($convertToNative && null !== $journal['foreign_amount'] && $currency->id === (int) $journal['foreign_currency_id']) {
$amount = $journal['foreign_amount'];
// Log::debug(sprintf('Overruled, amount is now %s', $amount));
}
@@ -68,22 +67,30 @@ class Amount
return $amount;
}
+ public function convertToNative(?User $user = null): bool
+ {
+ if (null === $user) {
+ return \FireflyIII\Support\Facades\Preferences::get('convert_to_native', false)->data && config('cer.enabled');
+ }
+ return \FireflyIII\Support\Facades\Preferences::getForUser($user, 'convert_to_native', false)->data && config('cer.enabled');
+ }
+
/**
* Experimental function to see if we can quickly and quietly get the amount from a journal.
* This depends on the user's default currency and the wish to have it converted.
*/
public function getAmountFromJournalObject(TransactionJournal $journal): string
{
- $convertToNative = app('preferences')->get('convert_to_native', false)->data;
- $currency = app('amount')->getDefaultCurrency();
- $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
+ $convertToNative = $this->convertToNative();
+ $currency = $this->getDefaultCurrency();
+ $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
/** @var null|Transaction $sourceTransaction */
$sourceTransaction = $journal->transactions()->where('amount', '<', 0)->first();
if (null === $sourceTransaction) {
return '0';
}
- $amount = $sourceTransaction->{$field};
+ $amount = $sourceTransaction->{$field} ?? '0';
if ((int) $sourceTransaction->foreign_currency_id === $currency->id) {
// use foreign amount instead!
$amount = (string) $sourceTransaction->foreign_amount; // hard coded to be foreign amount.
@@ -102,15 +109,15 @@ class Amount
*/
public function formatFlat(string $symbol, int $decimalPlaces, string $amount, ?bool $coloured = null): string
{
- $locale = app('steam')->getLocale();
- $rounded = app('steam')->bcround($amount, $decimalPlaces);
+ $locale = app('steam')->getLocale();
+ $rounded = app('steam')->bcround($amount, $decimalPlaces);
$coloured ??= true;
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$fmt->setSymbol(\NumberFormatter::CURRENCY_SYMBOL, $symbol);
$fmt->setAttribute(\NumberFormatter::MIN_FRACTION_DIGITS, $decimalPlaces);
$fmt->setAttribute(\NumberFormatter::MAX_FRACTION_DIGITS, $decimalPlaces);
- $result = (string) $fmt->format((float) $rounded); // intentional float
+ $result = (string) $fmt->format((float) $rounded); // intentional float
if (true === $coloured) {
if (1 === bccomp($rounded, '0')) {
@@ -156,7 +163,7 @@ class Amount
public function getDefaultCurrencyByUserGroup(UserGroup $userGroup): TransactionCurrency
{
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty('getDefaultCurrencyByGroup');
$cache->addProperty($userGroup->id);
if ($cache->has()) {
@@ -219,20 +226,20 @@ class Amount
private function getLocaleInfo(): array
{
// get config from preference, not from translation:
- $locale = app('steam')->getLocale();
- $array = app('steam')->getLocaleArray($locale);
+ $locale = app('steam')->getLocale();
+ $array = app('steam')->getLocaleArray($locale);
setlocale(LC_MONETARY, $array);
- $info = localeconv();
+ $info = localeconv();
// correct variables
- $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
- $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
+ $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
+ $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
- $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
- $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
+ $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
+ $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$info['mon_decimal_point'] = $fmt->getSymbol(\NumberFormatter::MONETARY_SEPARATOR_SYMBOL);
$info['mon_thousands_sep'] = $fmt->getSymbol(\NumberFormatter::MONETARY_GROUPING_SEPARATOR_SYMBOL);
@@ -255,7 +262,7 @@ class Amount
public static function getAmountJsConfig(bool $sepBySpace, int $signPosn, string $sign, bool $csPrecedes): string
{
// negative first:
- $space = ' ';
+ $space = ' ';
// require space between symbol and amount?
if (false === $sepBySpace) {
@@ -264,11 +271,11 @@ class Amount
// there are five possible positions for the "+" or "-" sign (if it is even used)
// pos_a and pos_e could be the ( and ) symbol.
- $posA = ''; // before everything
- $posB = ''; // before currency symbol
- $posC = ''; // after currency symbol
- $posD = ''; // before amount
- $posE = ''; // after everything
+ $posA = ''; // before everything
+ $posB = ''; // before currency symbol
+ $posC = ''; // after currency symbol
+ $posD = ''; // before amount
+ $posE = ''; // after everything
// format would be (currency before amount)
// AB%sC_D%vE
@@ -310,11 +317,11 @@ class Amount
}
// default is amount before currency
- $format = $posA.$posD.'%v'.$space.$posB.'%s'.$posC.$posE;
+ $format = $posA . $posD . '%v' . $space . $posB . '%s' . $posC . $posE;
if ($csPrecedes) {
// alternative is currency before amount
- $format = $posA.$posB.'%s'.$posC.$space.$posD.'%v'.$posE;
+ $format = $posA . $posB . '%s' . $posC . $space . $posD . '%v' . $posE;
}
return $format;
diff --git a/app/Support/Http/Controllers/ChartGeneration.php b/app/Support/Http/Controllers/ChartGeneration.php
index 572f0b6044..e1c9aea6ca 100644
--- a/app/Support/Http/Controllers/ChartGeneration.php
+++ b/app/Support/Http/Controllers/ChartGeneration.php
@@ -30,6 +30,7 @@ use FireflyIII\Generator\Chart\Basic\GeneratorInterface;
use FireflyIII\Models\Account;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
use FireflyIII\Support\CacheProperties;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Facades\Steam;
use Illuminate\Support\Collection;
@@ -46,7 +47,7 @@ trait ChartGeneration
protected function accountBalanceChart(Collection $accounts, Carbon $start, Carbon $end): array // chart helper method.
{
// chart properties for cache:
- $convertToNative = app('preferences')->get('convert_to_native', false)->data;
+ $convertToNative = Amount::convertToNative();
$cache = new CacheProperties();
$cache->addProperty($start);
$cache->addProperty($end);
diff --git a/app/Support/Steam.php b/app/Support/Steam.php
index 1aa9f73bf7..d0734e1896 100644
--- a/app/Support/Steam.php
+++ b/app/Support/Steam.php
@@ -310,8 +310,8 @@ class Steam
public function finalAccountBalance(Account $account, Carbon $date): array
{
Log::debug(sprintf('Now in finalAccountBalance(#%d, "%s", "%s")', $account->id, $account->name, $date->format('Y-m-d H:i:s')));
- $native = app('amount')->getDefaultCurrencyByUserGroup($account->user->userGroup);
- $convertToNative = app('preferences')->getForUser($account->user, 'convert_to_native', false)->data;
+ $native = \FireflyIII\Support\Facades\Amount::getDefaultCurrencyByUserGroup($account->user->userGroup);
+ $convertToNative = \FireflyIII\Support\Facades\Amount::convertToNative($account->user);
$accountCurrency = $this->getAccountCurrency($account);
$hasCurrency = null !== $accountCurrency;
$currency = $hasCurrency ? $accountCurrency : $native;
diff --git a/app/Support/Twig/General.php b/app/Support/Twig/General.php
index 09e1e3118f..18b3d5bac7 100644
--- a/app/Support/Twig/General.php
+++ b/app/Support/Twig/General.php
@@ -70,7 +70,7 @@ class General extends AbstractExtension
$info = Steam::finalAccountBalance($account, $date);
$currency = Steam::getAccountCurrency($account);
$default = Amount::getDefaultCurrency();
- $convertToNative = app('preferences')->get('convert_to_native', false)->data;
+ $convertToNative = Amount::convertToNative();
$useNative = $convertToNative && $default->id !== $currency->id;
$strings = [];
foreach ($info as $key => $balance) {
diff --git a/resources/views/partials/menu-sidebar.twig b/resources/views/partials/menu-sidebar.twig
index 52f3024148..32fff07238 100644
--- a/resources/views/partials/menu-sidebar.twig
+++ b/resources/views/partials/menu-sidebar.twig
@@ -219,12 +219,14 @@
{{ 'currencies'|_ }}
+ {% if config('cer.enabled') %}
{{ 'menu_exchange_rates_index'|_ }}
+ {% endif %}
{% if hasRole('owner') %}
diff --git a/resources/views/preferences/index.twig b/resources/views/preferences/index.twig
index e8f16f4c32..d5b5b26907 100644
--- a/resources/views/preferences/index.twig
+++ b/resources/views/preferences/index.twig
@@ -100,7 +100,8 @@
{{ ExpandedForm.date('fiscalYearStart',fiscalYearStart,{ 'label' : 'pref_fiscal_year_start_label'|_ }) }}
- {# conversion back to natiev #}
+ {# conversion back to native #}
+ {% if config('cer.enabled') %}
{{ 'pref_convert_to_native'|_ }}
@@ -108,6 +109,7 @@
{{ ExpandedForm.checkbox('convertToNative','1',convertToNative,{ 'label' : 'pref_convert_native_help'|_ }) }}
+ {% endif %}
{# general settings column B #}
From 0d56b7d251d22b99640ae8c691f0a876d814e1dc Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 07:39:39 +0100
Subject: [PATCH 137/167] Ignore error. Must test more with sqlite.
---
database/migrations/2024_11_30_075826_multi_piggy.php | 6 +++++-
1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/database/migrations/2024_11_30_075826_multi_piggy.php b/database/migrations/2024_11_30_075826_multi_piggy.php
index bcd6cee9bc..09faaebcea 100644
--- a/database/migrations/2024_11_30_075826_multi_piggy.php
+++ b/database/migrations/2024_11_30_075826_multi_piggy.php
@@ -15,7 +15,11 @@ return new class () extends Migration {
// make account_id nullable and the relation also nullable.
Schema::table('piggy_banks', static function (Blueprint $table): void {
// 1. drop index
- $table->dropForeign('piggy_banks_account_id_foreign');
+ try {
+ $table->dropForeign('piggy_banks_account_id_foreign');
+ } catch(RuntimeException $e) {
+ // do nothing.
+ }
});
Schema::table('piggy_banks', static function (Blueprint $table): void {
// 2. make column nullable.
From da88e02be095bbb96a04880463c87c97a509d4d0 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 07:47:32 +0100
Subject: [PATCH 138/167] Catch exception.
---
.../migrations/2024_11_30_075826_multi_piggy.php | 14 +++++++-------
1 file changed, 7 insertions(+), 7 deletions(-)
diff --git a/database/migrations/2024_11_30_075826_multi_piggy.php b/database/migrations/2024_11_30_075826_multi_piggy.php
index 09faaebcea..f32628e86f 100644
--- a/database/migrations/2024_11_30_075826_multi_piggy.php
+++ b/database/migrations/2024_11_30_075826_multi_piggy.php
@@ -13,14 +13,14 @@ return new class () extends Migration {
public function up(): void
{
// make account_id nullable and the relation also nullable.
- Schema::table('piggy_banks', static function (Blueprint $table): void {
- // 1. drop index
- try {
+ try {
+ Schema::table('piggy_banks', static function (Blueprint $table): void {
+ // 1. drop index
$table->dropForeign('piggy_banks_account_id_foreign');
- } catch(RuntimeException $e) {
- // do nothing.
- }
- });
+ });
+ } catch (RuntimeException $e) {
+ \Illuminate\Support\Facades\Log::error('Could not drop foreign key "piggy_banks_account_id_foreign". Probably not an issue.');
+ }
Schema::table('piggy_banks', static function (Blueprint $table): void {
// 2. make column nullable.
$table->unsignedInteger('account_id')->nullable()->change();
From f2166b97b8f6c894f73d2caa78a9573db4f49220 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 10:52:46 +0100
Subject: [PATCH 139/167] Various fixes for sqlite databases
---
.../Correction/CorrectsNativeAmounts.php | 4 +--
.../Upgrade/UpgradesTransferCurrencies.php | 28 +++++++++----------
app/Handlers/Observer/BudgetLimitObserver.php | 1 +
app/Handlers/Observer/TransactionObserver.php | 2 +-
.../Controllers/Account/EditController.php | 3 +-
.../Http/Api/ExchangeRateConverter.php | 3 +-
app/Transformers/PiggyBankTransformer.php | 2 +-
resources/lang/en_US/firefly.php | 1 +
resources/views/accounts/edit.twig | 7 +++--
9 files changed, 28 insertions(+), 23 deletions(-)
diff --git a/app/Console/Commands/Correction/CorrectsNativeAmounts.php b/app/Console/Commands/Correction/CorrectsNativeAmounts.php
index bf5d7e98ec..eab4e97525 100644
--- a/app/Console/Commands/Correction/CorrectsNativeAmounts.php
+++ b/app/Console/Commands/Correction/CorrectsNativeAmounts.php
@@ -128,8 +128,8 @@ class CorrectsNativeAmounts extends Command
foreach ($piggyBank->accounts as $account) {
$account->pivot->native_current_amount = null;
- if (0 !== bccomp($account->pivot->current_amount, '0')) {
- $account->pivot->native_current_amount = $converter->convert($piggyBank->transactionCurrency, $currency, today(), $account->pivot->current_amount);
+ if (0 !== bccomp((string) $account->pivot->current_amount, '0')) {
+ $account->pivot->native_current_amount = $converter->convert($piggyBank->transactionCurrency, $currency, today(), (string) $account->pivot->current_amount);
}
$account->pivot->save();
}
diff --git a/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php b/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php
index 5fe4d06696..a58b1af8bf 100644
--- a/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php
+++ b/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php
@@ -39,8 +39,8 @@ class UpgradesTransferCurrencies extends Command
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '480_transfer_currencies';
- protected $description = 'Updates transfer currency information.';
- protected $signature = 'upgrade:480-transfer-currencies {--F|force : Force the execution of this command.}';
+ protected $description = 'Updates transfer currency information.';
+ protected $signature = 'upgrade:480-transfer-currencies {--F|force : Force the execution of this command.}';
private array $accountCurrencies;
private AccountRepositoryInterface $accountRepos;
private JournalCLIRepositoryInterface $cliRepos;
@@ -68,9 +68,9 @@ class UpgradesTransferCurrencies extends Command
$this->startUpdateRoutine();
$this->markAsExecuted();
-
- $this->friendlyInfo(sprintf('Verified currency information of %d transfer(s).', $this->count));
-
+ if ($this->count > 0) {
+ $this->friendlyInfo(sprintf('Verified currency information of %d transfer(s).', $this->count));
+ }
return 0;
}
@@ -211,14 +211,14 @@ class UpgradesTransferCurrencies extends Command
private function getCurrency(Account $account): ?TransactionCurrency
{
- $accountId = $account->id;
+ $accountId = $account->id;
if (array_key_exists($accountId, $this->accountCurrencies) && 0 === $this->accountCurrencies[$accountId]) {
return null;
}
if (array_key_exists($accountId, $this->accountCurrencies) && $this->accountCurrencies[$accountId] instanceof TransactionCurrency) {
return $this->accountCurrencies[$accountId];
}
- $currency = $this->accountRepos->getAccountCurrency($account);
+ $currency = $this->accountRepos->getAccountCurrency($account);
if (null === $currency) {
$this->accountCurrencies[$accountId] = 0;
@@ -290,8 +290,7 @@ class UpgradesTransferCurrencies extends Command
if (null === $this->sourceTransaction->transaction_currency_id && null !== $this->sourceCurrency) {
$this->sourceTransaction
->transaction_currency_id
- = $this->sourceCurrency->id
- ;
+ = $this->sourceCurrency->id;
$message = sprintf(
'Transaction #%d has no currency setting, now set to %s.',
$this->sourceTransaction->id,
@@ -313,7 +312,7 @@ class UpgradesTransferCurrencies extends Command
&& null === $this->sourceTransaction->foreign_amount
&& (int) $this->sourceTransaction->transaction_currency_id !== $this->sourceCurrency->id
) {
- $message = sprintf(
+ $message = sprintf(
'Transaction #%d has a currency setting #%d that should be #%d. Amount remains %s, currency is changed.',
$this->sourceTransaction->id,
$this->sourceTransaction->transaction_currency_id,
@@ -336,8 +335,7 @@ class UpgradesTransferCurrencies extends Command
if (null === $this->destinationTransaction->transaction_currency_id && null !== $this->destinationCurrency) {
$this->destinationTransaction
->transaction_currency_id
- = $this->destinationCurrency->id
- ;
+ = $this->destinationCurrency->id;
$message = sprintf(
'Transaction #%d has no currency setting, now set to %s.',
$this->destinationTransaction->id,
@@ -359,7 +357,7 @@ class UpgradesTransferCurrencies extends Command
&& null === $this->destinationTransaction->foreign_amount
&& (int) $this->destinationTransaction->transaction_currency_id !== $this->destinationCurrency->id
) {
- $message = sprintf(
+ $message = sprintf(
'Transaction #%d has a currency setting #%d that should be #%d. Amount remains %s, currency is changed.',
$this->destinationTransaction->id,
$this->destinationTransaction->transaction_currency_id,
@@ -382,8 +380,8 @@ class UpgradesTransferCurrencies extends Command
{
if ($this->destinationCurrency->id === $this->sourceCurrency->id) {
// update both transactions to match:
- $this->sourceTransaction->foreign_amount = null;
- $this->sourceTransaction->foreign_currency_id = null;
+ $this->sourceTransaction->foreign_amount = null;
+ $this->sourceTransaction->foreign_currency_id = null;
$this->destinationTransaction->foreign_amount = null;
$this->destinationTransaction->foreign_currency_id = null;
diff --git a/app/Handlers/Observer/BudgetLimitObserver.php b/app/Handlers/Observer/BudgetLimitObserver.php
index e9e0cf5337..e13bde9327 100644
--- a/app/Handlers/Observer/BudgetLimitObserver.php
+++ b/app/Handlers/Observer/BudgetLimitObserver.php
@@ -25,6 +25,7 @@ declare(strict_types=1);
namespace FireflyIII\Handlers\Observer;
use FireflyIII\Models\BudgetLimit;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Http\Api\ExchangeRateConverter;
use Illuminate\Support\Facades\Log;
diff --git a/app/Handlers/Observer/TransactionObserver.php b/app/Handlers/Observer/TransactionObserver.php
index d4d79548da..986cda6eeb 100644
--- a/app/Handlers/Observer/TransactionObserver.php
+++ b/app/Handlers/Observer/TransactionObserver.php
@@ -56,7 +56,7 @@ class TransactionObserver
public function updated(Transaction $transaction): void
{
- Log::debug('Observe "updated" of a transaction.');
+// Log::debug('Observe "updated" of a transaction.');
if (config('firefly.feature_flags.running_balance_column') && self::$recalculate) {
if (1 === bccomp($transaction->amount, '0')) {
Log::debug('Trigger recalculateForJournal');
diff --git a/app/Http/Controllers/Account/EditController.php b/app/Http/Controllers/Account/EditController.php
index 93a1603582..8d1b772256 100644
--- a/app/Http/Controllers/Account/EditController.php
+++ b/app/Http/Controllers/Account/EditController.php
@@ -90,6 +90,7 @@ class EditController extends Controller
$latitude = null !== $location ? $location->latitude : config('firefly.default_location.latitude');
$longitude = null !== $location ? $location->longitude : config('firefly.default_location.longitude');
$zoomLevel = null !== $location ? $location->zoom_level : config('firefly.default_location.zoom_level');
+ $canEditCurrency = $account->piggyBanks()->count() === 0;
$hasLocation = null !== $location;
$locations = [
'location' => [
@@ -162,7 +163,7 @@ class EditController extends Controller
$request->session()->flash('preFilled', $preFilled);
- return view('accounts.edit', compact('account', 'currency', 'showNetWorth', 'subTitle', 'subTitleIcon', 'locations', 'liabilityDirections', 'objectType', 'roles', 'preFilled', 'liabilityTypes', 'interestPeriods'));
+ return view('accounts.edit', compact('account', 'currency','canEditCurrency', 'showNetWorth', 'subTitle', 'subTitleIcon', 'locations', 'liabilityDirections', 'objectType', 'roles', 'preFilled', 'liabilityTypes', 'interestPeriods'));
}
/**
diff --git a/app/Support/Http/Api/ExchangeRateConverter.php b/app/Support/Http/Api/ExchangeRateConverter.php
index dfe9cd7753..c3d847179d 100644
--- a/app/Support/Http/Api/ExchangeRateConverter.php
+++ b/app/Support/Http/Api/ExchangeRateConverter.php
@@ -30,6 +30,7 @@ use FireflyIII\Models\CurrencyExchangeRate;
use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Models\UserGroup;
use FireflyIII\Support\CacheProperties;
+use FireflyIII\Support\Facades\Steam;
use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\Log;
@@ -72,7 +73,7 @@ class ExchangeRateConverter
}
$rate = $this->getCurrencyRate($from, $to, $date);
- return bcmul($amount, $rate);
+ return Steam::bcround(bcmul($amount, $rate), $to->decimal_places);
}
public function enabled(): bool
diff --git a/app/Transformers/PiggyBankTransformer.php b/app/Transformers/PiggyBankTransformer.php
index 6c76f73a7b..c1cf567fa3 100644
--- a/app/Transformers/PiggyBankTransformer.php
+++ b/app/Transformers/PiggyBankTransformer.php
@@ -136,7 +136,7 @@ class PiggyBankTransformer extends AbstractTransformer
$return[] = [
'id' => $account->id,
'name' => $account->name,
- 'current_amount' => $account->pivot->current_amount,
+ 'current_amount' => (string) $account->pivot->current_amount,
// TODO add balance, add left to save.
];
}
diff --git a/resources/lang/en_US/firefly.php b/resources/lang/en_US/firefly.php
index 5e5b8d5092..6921b61bb6 100644
--- a/resources/lang/en_US/firefly.php
+++ b/resources/lang/en_US/firefly.php
@@ -1913,6 +1913,7 @@ return [
'extension_date_is' => 'Extension date is {date}',
// accounts:
+ 'account_locked_currency' => 'The currency of this account must remain :name as long as piggy banks are linked to it.',
'i_am_owed_amount' => 'I am owed amount',
'i_owe_amount' => 'I owe amount',
'inactive_account_link' => 'You have :count inactive (archived) account, which you can view on this separate page.|You have :count inactive (archived) accounts, which you can view on this separate page.',
diff --git a/resources/views/accounts/edit.twig b/resources/views/accounts/edit.twig
index 9b9ce38834..e5cbdb0266 100644
--- a/resources/views/accounts/edit.twig
+++ b/resources/views/accounts/edit.twig
@@ -27,9 +27,12 @@
{{ ExpandedForm.text('name', account.name) }}
- {% if account.accountType.type == 'Default account' or account.accountType.type == 'Asset account' or objectType == 'liabilities' %}
+ {% if canEditCurrency and (account.accountType.type == 'Default account' or account.accountType.type == 'Asset account' or objectType == 'liabilities') %}
{{ CurrencyForm.currencyList('currency_id', null, {helpText:'account_default_currency'|_}) }}
-
+ {% endif %}
+ {% if not canEditCurrency and (account.accountType.type == 'Default account' or account.accountType.type == 'Asset account' or objectType == 'liabilities') %}
+
+ {{ ExpandedForm.staticText('currency_id', trans('firefly.account_locked_currency', {name: currency.name})) }}
{% endif %}
{% if objectType == 'liabilities' %}
From 6c655634bccf108ed9fd2781568c3668405fdd59 Mon Sep 17 00:00:00 2001
From: github-actions <41898282+github-actions[bot]@users.noreply.github.com>
Date: Sat, 28 Dec 2024 10:58:01 +0100
Subject: [PATCH 140/167] Auto commit for release 'develop' on 2024-12-28
---
.../Correction/CorrectsNativeAmounts.php | 3 +-
.../Upgrade/UpgradesTransferCurrencies.php | 23 ++++----
app/Exceptions/Handler.php | 4 +-
app/Handlers/Observer/AccountObserver.php | 2 +-
app/Handlers/Observer/AutoBudgetObserver.php | 2 +-
.../Observer/AvailableBudgetObserver.php | 2 +-
app/Handlers/Observer/BillObserver.php | 2 +-
app/Handlers/Observer/BudgetLimitObserver.php | 2 +-
.../Observer/PiggyBankEventObserver.php | 2 +-
app/Handlers/Observer/TransactionObserver.php | 4 +-
.../Controllers/Account/EditController.php | 4 +-
.../Controllers/Chart/CategoryController.php | 10 ++--
.../ExchangeRates/IndexController.php | 2 +-
.../Category/NoCategoryRepository.php | 2 +-
.../Category/OperationsRepository.php | 4 +-
app/Support/Amount.php | 56 ++++++++++---------
.../Http/Controllers/PeriodOverview.php | 14 ++---
app/Support/Steam.php | 5 +-
changelog.md | 18 +++---
config/firefly.php | 2 +-
.../2024_11_30_075826_multi_piggy.php | 3 +-
resources/lang/en_US/firefly.php | 2 +-
22 files changed, 87 insertions(+), 81 deletions(-)
diff --git a/app/Console/Commands/Correction/CorrectsNativeAmounts.php b/app/Console/Commands/Correction/CorrectsNativeAmounts.php
index eab4e97525..7cbab491fc 100644
--- a/app/Console/Commands/Correction/CorrectsNativeAmounts.php
+++ b/app/Console/Commands/Correction/CorrectsNativeAmounts.php
@@ -59,8 +59,9 @@ class CorrectsNativeAmounts extends Command
*/
public function handle(): int
{
- if(!config('cer.enabled')) {
+ if (!config('cer.enabled')) {
$this->friendlyInfo('This command will not run because currency exchange rates are disabled.');
+
return 0;
}
Log::debug('Will update all native amounts. This may take some time.');
diff --git a/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php b/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php
index a58b1af8bf..a16fe46351 100644
--- a/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php
+++ b/app/Console/Commands/Upgrade/UpgradesTransferCurrencies.php
@@ -39,8 +39,8 @@ class UpgradesTransferCurrencies extends Command
use ShowsFriendlyMessages;
public const string CONFIG_NAME = '480_transfer_currencies';
- protected $description = 'Updates transfer currency information.';
- protected $signature = 'upgrade:480-transfer-currencies {--F|force : Force the execution of this command.}';
+ protected $description = 'Updates transfer currency information.';
+ protected $signature = 'upgrade:480-transfer-currencies {--F|force : Force the execution of this command.}';
private array $accountCurrencies;
private AccountRepositoryInterface $accountRepos;
private JournalCLIRepositoryInterface $cliRepos;
@@ -71,6 +71,7 @@ class UpgradesTransferCurrencies extends Command
if ($this->count > 0) {
$this->friendlyInfo(sprintf('Verified currency information of %d transfer(s).', $this->count));
}
+
return 0;
}
@@ -211,14 +212,14 @@ class UpgradesTransferCurrencies extends Command
private function getCurrency(Account $account): ?TransactionCurrency
{
- $accountId = $account->id;
+ $accountId = $account->id;
if (array_key_exists($accountId, $this->accountCurrencies) && 0 === $this->accountCurrencies[$accountId]) {
return null;
}
if (array_key_exists($accountId, $this->accountCurrencies) && $this->accountCurrencies[$accountId] instanceof TransactionCurrency) {
return $this->accountCurrencies[$accountId];
}
- $currency = $this->accountRepos->getAccountCurrency($account);
+ $currency = $this->accountRepos->getAccountCurrency($account);
if (null === $currency) {
$this->accountCurrencies[$accountId] = 0;
@@ -290,7 +291,8 @@ class UpgradesTransferCurrencies extends Command
if (null === $this->sourceTransaction->transaction_currency_id && null !== $this->sourceCurrency) {
$this->sourceTransaction
->transaction_currency_id
- = $this->sourceCurrency->id;
+ = $this->sourceCurrency->id
+ ;
$message = sprintf(
'Transaction #%d has no currency setting, now set to %s.',
$this->sourceTransaction->id,
@@ -312,7 +314,7 @@ class UpgradesTransferCurrencies extends Command
&& null === $this->sourceTransaction->foreign_amount
&& (int) $this->sourceTransaction->transaction_currency_id !== $this->sourceCurrency->id
) {
- $message = sprintf(
+ $message = sprintf(
'Transaction #%d has a currency setting #%d that should be #%d. Amount remains %s, currency is changed.',
$this->sourceTransaction->id,
$this->sourceTransaction->transaction_currency_id,
@@ -335,7 +337,8 @@ class UpgradesTransferCurrencies extends Command
if (null === $this->destinationTransaction->transaction_currency_id && null !== $this->destinationCurrency) {
$this->destinationTransaction
->transaction_currency_id
- = $this->destinationCurrency->id;
+ = $this->destinationCurrency->id
+ ;
$message = sprintf(
'Transaction #%d has no currency setting, now set to %s.',
$this->destinationTransaction->id,
@@ -357,7 +360,7 @@ class UpgradesTransferCurrencies extends Command
&& null === $this->destinationTransaction->foreign_amount
&& (int) $this->destinationTransaction->transaction_currency_id !== $this->destinationCurrency->id
) {
- $message = sprintf(
+ $message = sprintf(
'Transaction #%d has a currency setting #%d that should be #%d. Amount remains %s, currency is changed.',
$this->destinationTransaction->id,
$this->destinationTransaction->transaction_currency_id,
@@ -380,8 +383,8 @@ class UpgradesTransferCurrencies extends Command
{
if ($this->destinationCurrency->id === $this->sourceCurrency->id) {
// update both transactions to match:
- $this->sourceTransaction->foreign_amount = null;
- $this->sourceTransaction->foreign_currency_id = null;
+ $this->sourceTransaction->foreign_amount = null;
+ $this->sourceTransaction->foreign_currency_id = null;
$this->destinationTransaction->foreign_amount = null;
$this->destinationTransaction->foreign_currency_id = null;
diff --git a/app/Exceptions/Handler.php b/app/Exceptions/Handler.php
index e8352aa791..60d31fa76f 100644
--- a/app/Exceptions/Handler.php
+++ b/app/Exceptions/Handler.php
@@ -68,9 +68,7 @@ class Handler extends ExceptionHandler
/**
* Register the exception handling callbacks for the application.
*/
- public function register(): void
- {
- }
+ public function register(): void {}
/**
* Render an exception into an HTTP response. It's complex but lucky for us, we never use it because
diff --git a/app/Handlers/Observer/AccountObserver.php b/app/Handlers/Observer/AccountObserver.php
index e321b102e6..fc839ec78b 100644
--- a/app/Handlers/Observer/AccountObserver.php
+++ b/app/Handlers/Observer/AccountObserver.php
@@ -44,7 +44,7 @@ class AccountObserver
private function updateNativeAmount(Account $account): void
{
- if(!Amount::convertToNative($account->user)) {
+ if (!Amount::convertToNative($account->user)) {
return;
}
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($account->user->userGroup);
diff --git a/app/Handlers/Observer/AutoBudgetObserver.php b/app/Handlers/Observer/AutoBudgetObserver.php
index e4a911653f..6109617b52 100644
--- a/app/Handlers/Observer/AutoBudgetObserver.php
+++ b/app/Handlers/Observer/AutoBudgetObserver.php
@@ -45,7 +45,7 @@ class AutoBudgetObserver
private function updateNativeAmount(AutoBudget $autoBudget): void
{
- if(!Amount::convertToNative($autoBudget->budget->user)) {
+ if (!Amount::convertToNative($autoBudget->budget->user)) {
return;
}
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($autoBudget->budget->user->userGroup);
diff --git a/app/Handlers/Observer/AvailableBudgetObserver.php b/app/Handlers/Observer/AvailableBudgetObserver.php
index d5d03fe31c..3017450bd3 100644
--- a/app/Handlers/Observer/AvailableBudgetObserver.php
+++ b/app/Handlers/Observer/AvailableBudgetObserver.php
@@ -45,7 +45,7 @@ class AvailableBudgetObserver
private function updateNativeAmount(AvailableBudget $availableBudget): void
{
- if(!Amount::convertToNative($availableBudget->user)) {
+ if (!Amount::convertToNative($availableBudget->user)) {
return;
}
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($availableBudget->user->userGroup);
diff --git a/app/Handlers/Observer/BillObserver.php b/app/Handlers/Observer/BillObserver.php
index 262ed250bc..3dcc1ac5a5 100644
--- a/app/Handlers/Observer/BillObserver.php
+++ b/app/Handlers/Observer/BillObserver.php
@@ -56,7 +56,7 @@ class BillObserver
private function updateNativeAmount(Bill $bill): void
{
- if(!Amount::convertToNative($bill->user)) {
+ if (!Amount::convertToNative($bill->user)) {
return;
}
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($bill->user->userGroup);
diff --git a/app/Handlers/Observer/BudgetLimitObserver.php b/app/Handlers/Observer/BudgetLimitObserver.php
index e13bde9327..af029db737 100644
--- a/app/Handlers/Observer/BudgetLimitObserver.php
+++ b/app/Handlers/Observer/BudgetLimitObserver.php
@@ -45,7 +45,7 @@ class BudgetLimitObserver
private function updateNativeAmount(BudgetLimit $budgetLimit): void
{
- if(!Amount::convertToNative($budgetLimit->budget->user)) {
+ if (!Amount::convertToNative($budgetLimit->budget->user)) {
return;
}
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($budgetLimit->budget->user->userGroup);
diff --git a/app/Handlers/Observer/PiggyBankEventObserver.php b/app/Handlers/Observer/PiggyBankEventObserver.php
index 7ed4b2fae3..b764fed9d6 100644
--- a/app/Handlers/Observer/PiggyBankEventObserver.php
+++ b/app/Handlers/Observer/PiggyBankEventObserver.php
@@ -45,7 +45,7 @@ class PiggyBankEventObserver
private function updateNativeAmount(PiggyBankEvent $event): void
{
- if(!Amount::convertToNative($event->piggyBank->accounts()->first()->user)) {
+ if (!Amount::convertToNative($event->piggyBank->accounts()->first()->user)) {
return;
}
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($event->piggyBank->accounts()->first()->user->userGroup);
diff --git a/app/Handlers/Observer/TransactionObserver.php b/app/Handlers/Observer/TransactionObserver.php
index 986cda6eeb..ebf2fca3c8 100644
--- a/app/Handlers/Observer/TransactionObserver.php
+++ b/app/Handlers/Observer/TransactionObserver.php
@@ -56,7 +56,7 @@ class TransactionObserver
public function updated(Transaction $transaction): void
{
-// Log::debug('Observe "updated" of a transaction.');
+ // Log::debug('Observe "updated" of a transaction.');
if (config('firefly.feature_flags.running_balance_column') && self::$recalculate) {
if (1 === bccomp($transaction->amount, '0')) {
Log::debug('Trigger recalculateForJournal');
@@ -68,7 +68,7 @@ class TransactionObserver
private function updateNativeAmount(Transaction $transaction): void
{
- if(!Amount::convertToNative($transaction->transactionJournal->user)) {
+ if (!Amount::convertToNative($transaction->transactionJournal->user)) {
return;
}
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($transaction->transactionJournal->user->userGroup);
diff --git a/app/Http/Controllers/Account/EditController.php b/app/Http/Controllers/Account/EditController.php
index 8d1b772256..ca674eb407 100644
--- a/app/Http/Controllers/Account/EditController.php
+++ b/app/Http/Controllers/Account/EditController.php
@@ -90,7 +90,7 @@ class EditController extends Controller
$latitude = null !== $location ? $location->latitude : config('firefly.default_location.latitude');
$longitude = null !== $location ? $location->longitude : config('firefly.default_location.longitude');
$zoomLevel = null !== $location ? $location->zoom_level : config('firefly.default_location.zoom_level');
- $canEditCurrency = $account->piggyBanks()->count() === 0;
+ $canEditCurrency = 0 === $account->piggyBanks()->count();
$hasLocation = null !== $location;
$locations = [
'location' => [
@@ -163,7 +163,7 @@ class EditController extends Controller
$request->session()->flash('preFilled', $preFilled);
- return view('accounts.edit', compact('account', 'currency','canEditCurrency', 'showNetWorth', 'subTitle', 'subTitleIcon', 'locations', 'liabilityDirections', 'objectType', 'roles', 'preFilled', 'liabilityTypes', 'interestPeriods'));
+ return view('accounts.edit', compact('account', 'currency', 'canEditCurrency', 'showNetWorth', 'subTitle', 'subTitleIcon', 'locations', 'liabilityDirections', 'objectType', 'roles', 'preFilled', 'liabilityTypes', 'interestPeriods'));
}
/**
diff --git a/app/Http/Controllers/Chart/CategoryController.php b/app/Http/Controllers/Chart/CategoryController.php
index 9c9fc19ead..79979e6a70 100644
--- a/app/Http/Controllers/Chart/CategoryController.php
+++ b/app/Http/Controllers/Chart/CategoryController.php
@@ -197,11 +197,11 @@ class CategoryController extends Controller
$chartData[$inKey]
= [
- 'label' => sprintf('%s (%s)', (string) trans('firefly.earned'), $currencyInfo['currency_name']),
- 'entries' => [],
- 'type' => 'bar',
- 'backgroundColor' => 'rgba(0, 141, 76, 0.5)', // green
- ];
+ 'label' => sprintf('%s (%s)', (string) trans('firefly.earned'), $currencyInfo['currency_name']),
+ 'entries' => [],
+ 'type' => 'bar',
+ 'backgroundColor' => 'rgba(0, 141, 76, 0.5)', // green
+ ];
// loop empty periods:
foreach (array_keys($periods) as $period) {
$label = $periods[$period];
diff --git a/app/Http/Controllers/ExchangeRates/IndexController.php b/app/Http/Controllers/ExchangeRates/IndexController.php
index 880ed1ffd1..4cff4418e2 100644
--- a/app/Http/Controllers/ExchangeRates/IndexController.php
+++ b/app/Http/Controllers/ExchangeRates/IndexController.php
@@ -47,7 +47,7 @@ class IndexController extends Controller
return $next($request);
}
);
- if(!config('cer.enabled')) {
+ if (!config('cer.enabled')) {
throw new NotFoundHttpException();
}
}
diff --git a/app/Repositories/Category/NoCategoryRepository.php b/app/Repositories/Category/NoCategoryRepository.php
index 18a7b2a783..810fc178b3 100644
--- a/app/Repositories/Category/NoCategoryRepository.php
+++ b/app/Repositories/Category/NoCategoryRepository.php
@@ -154,7 +154,7 @@ class NoCategoryRepository implements NoCategoryRepositoryInterface
$journals = $collector->getExtractedJournals();
$array = [];
// default currency information for native stuff.
- $convertToNative = Amount::convertToNative($this->user);;
+ $convertToNative = Amount::convertToNative($this->user);
$default = Amount::getDefaultCurrency();
foreach ($journals as $journal) {
diff --git a/app/Repositories/Category/OperationsRepository.php b/app/Repositories/Category/OperationsRepository.php
index 598214e8b7..6d4615b3f4 100644
--- a/app/Repositories/Category/OperationsRepository.php
+++ b/app/Repositories/Category/OperationsRepository.php
@@ -331,7 +331,7 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionTypeEnum::WITHDRAWAL->value]);
// default currency information for native stuff.
- $convertToNative = Amount::convertToNative($this->user);;
+ $convertToNative = Amount::convertToNative($this->user);
$default = Amount::getDefaultCurrency();
if (null !== $accounts && $accounts->count() > 0) {
$collector->setAccounts($accounts);
@@ -411,7 +411,7 @@ class OperationsRepository implements OperationsRepositoryInterface
}
$collector->setCategories($categories);
$journals = $collector->getExtractedJournals();
- $convertToNative = Amount::convertToNative($this->user);;
+ $convertToNative = Amount::convertToNative($this->user);
$default = Amount::getDefaultCurrency();
$array = [];
diff --git a/app/Support/Amount.php b/app/Support/Amount.php
index 33ddc22b93..1d55989e52 100644
--- a/app/Support/Amount.php
+++ b/app/Support/Amount.php
@@ -30,6 +30,7 @@ use FireflyIII\Models\TransactionJournal;
use FireflyIII\Models\UserGroup;
use FireflyIII\User;
use Illuminate\Support\Collection;
+use FireflyIII\Support\Facades\Preferences;
/**
* Class Amount.
@@ -70,9 +71,10 @@ class Amount
public function convertToNative(?User $user = null): bool
{
if (null === $user) {
- return \FireflyIII\Support\Facades\Preferences::get('convert_to_native', false)->data && config('cer.enabled');
+ return Preferences::get('convert_to_native', false)->data && config('cer.enabled');
}
- return \FireflyIII\Support\Facades\Preferences::getForUser($user, 'convert_to_native', false)->data && config('cer.enabled');
+
+ return Preferences::getForUser($user, 'convert_to_native', false)->data && config('cer.enabled');
}
/**
@@ -81,16 +83,16 @@ class Amount
*/
public function getAmountFromJournalObject(TransactionJournal $journal): string
{
- $convertToNative = $this->convertToNative();
- $currency = $this->getDefaultCurrency();
- $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
+ $convertToNative = $this->convertToNative();
+ $currency = $this->getDefaultCurrency();
+ $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
/** @var null|Transaction $sourceTransaction */
$sourceTransaction = $journal->transactions()->where('amount', '<', 0)->first();
if (null === $sourceTransaction) {
return '0';
}
- $amount = $sourceTransaction->{$field} ?? '0';
+ $amount = $sourceTransaction->{$field} ?? '0';
if ((int) $sourceTransaction->foreign_currency_id === $currency->id) {
// use foreign amount instead!
$amount = (string) $sourceTransaction->foreign_amount; // hard coded to be foreign amount.
@@ -109,15 +111,15 @@ class Amount
*/
public function formatFlat(string $symbol, int $decimalPlaces, string $amount, ?bool $coloured = null): string
{
- $locale = app('steam')->getLocale();
- $rounded = app('steam')->bcround($amount, $decimalPlaces);
+ $locale = app('steam')->getLocale();
+ $rounded = app('steam')->bcround($amount, $decimalPlaces);
$coloured ??= true;
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$fmt->setSymbol(\NumberFormatter::CURRENCY_SYMBOL, $symbol);
$fmt->setAttribute(\NumberFormatter::MIN_FRACTION_DIGITS, $decimalPlaces);
$fmt->setAttribute(\NumberFormatter::MAX_FRACTION_DIGITS, $decimalPlaces);
- $result = (string) $fmt->format((float) $rounded); // intentional float
+ $result = (string) $fmt->format((float) $rounded); // intentional float
if (true === $coloured) {
if (1 === bccomp($rounded, '0')) {
@@ -163,7 +165,7 @@ class Amount
public function getDefaultCurrencyByUserGroup(UserGroup $userGroup): TransactionCurrency
{
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty('getDefaultCurrencyByGroup');
$cache->addProperty($userGroup->id);
if ($cache->has()) {
@@ -226,20 +228,20 @@ class Amount
private function getLocaleInfo(): array
{
// get config from preference, not from translation:
- $locale = app('steam')->getLocale();
- $array = app('steam')->getLocaleArray($locale);
+ $locale = app('steam')->getLocale();
+ $array = app('steam')->getLocaleArray($locale);
setlocale(LC_MONETARY, $array);
- $info = localeconv();
+ $info = localeconv();
// correct variables
- $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
- $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
+ $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
+ $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
- $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
- $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
+ $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
+ $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$info['mon_decimal_point'] = $fmt->getSymbol(\NumberFormatter::MONETARY_SEPARATOR_SYMBOL);
$info['mon_thousands_sep'] = $fmt->getSymbol(\NumberFormatter::MONETARY_GROUPING_SEPARATOR_SYMBOL);
@@ -262,7 +264,7 @@ class Amount
public static function getAmountJsConfig(bool $sepBySpace, int $signPosn, string $sign, bool $csPrecedes): string
{
// negative first:
- $space = ' ';
+ $space = ' ';
// require space between symbol and amount?
if (false === $sepBySpace) {
@@ -271,11 +273,11 @@ class Amount
// there are five possible positions for the "+" or "-" sign (if it is even used)
// pos_a and pos_e could be the ( and ) symbol.
- $posA = ''; // before everything
- $posB = ''; // before currency symbol
- $posC = ''; // after currency symbol
- $posD = ''; // before amount
- $posE = ''; // after everything
+ $posA = ''; // before everything
+ $posB = ''; // before currency symbol
+ $posC = ''; // after currency symbol
+ $posD = ''; // before amount
+ $posE = ''; // after everything
// format would be (currency before amount)
// AB%sC_D%vE
@@ -317,11 +319,11 @@ class Amount
}
// default is amount before currency
- $format = $posA . $posD . '%v' . $space . $posB . '%s' . $posC . $posE;
+ $format = $posA.$posD.'%v'.$space.$posB.'%s'.$posC.$posE;
if ($csPrecedes) {
// alternative is currency before amount
- $format = $posA . $posB . '%s' . $posC . $space . $posD . '%v' . $posE;
+ $format = $posA.$posB.'%s'.$posC.$space.$posD.'%v'.$posE;
}
return $format;
diff --git a/app/Support/Http/Controllers/PeriodOverview.php b/app/Support/Http/Controllers/PeriodOverview.php
index b66ba5747c..632f5088cf 100644
--- a/app/Support/Http/Controllers/PeriodOverview.php
+++ b/app/Support/Http/Controllers/PeriodOverview.php
@@ -576,13 +576,13 @@ trait PeriodOverview
}
$entries[]
= [
- 'title' => $title,
- 'route' => route('transactions.index', [$transactionType, $currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]),
- 'total_transactions' => count($spent) + count($earned) + count($transferred),
- 'spent' => $this->groupByCurrency($spent),
- 'earned' => $this->groupByCurrency($earned),
- 'transferred' => $this->groupByCurrency($transferred),
- ];
+ 'title' => $title,
+ 'route' => route('transactions.index', [$transactionType, $currentDate['start']->format('Y-m-d'), $currentDate['end']->format('Y-m-d')]),
+ 'total_transactions' => count($spent) + count($earned) + count($transferred),
+ 'spent' => $this->groupByCurrency($spent),
+ 'earned' => $this->groupByCurrency($earned),
+ 'transferred' => $this->groupByCurrency($transferred),
+ ];
}
return $entries;
diff --git a/app/Support/Steam.php b/app/Support/Steam.php
index d0734e1896..d6e9e96b9a 100644
--- a/app/Support/Steam.php
+++ b/app/Support/Steam.php
@@ -31,6 +31,7 @@ use FireflyIII\Models\TransactionCurrency;
use Illuminate\Support\Collection;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Log;
+use FireflyIII\Support\Facades\Amount;
/**
* Class Steam.
@@ -310,8 +311,8 @@ class Steam
public function finalAccountBalance(Account $account, Carbon $date): array
{
Log::debug(sprintf('Now in finalAccountBalance(#%d, "%s", "%s")', $account->id, $account->name, $date->format('Y-m-d H:i:s')));
- $native = \FireflyIII\Support\Facades\Amount::getDefaultCurrencyByUserGroup($account->user->userGroup);
- $convertToNative = \FireflyIII\Support\Facades\Amount::convertToNative($account->user);
+ $native = Amount::getDefaultCurrencyByUserGroup($account->user->userGroup);
+ $convertToNative = Amount::convertToNative($account->user);
$accountCurrency = $this->getAccountCurrency($account);
$hasCurrency = null !== $accountCurrency;
$currency = $hasCurrency ? $accountCurrency : $native;
diff --git a/changelog.md b/changelog.md
index 450bc5b765..da0a52fce3 100644
--- a/changelog.md
+++ b/changelog.md
@@ -10,17 +10,17 @@ This project adheres to [Semantic Versioning](http://semver.org/).
- Multi-currency support. If you set `ENABLE_EXCHANGE_RATES=true` and optionally `ENABLE_EXTERNAL_RATES=true` Firefly III will try to calculate all foreign currencies back to your native currency. This is a work in progress, not all fields and all places will support this yet. Please check out the [documentation](https://docs.firefly-iii.org/explanation/financial-concepts/exchange-rates/).
- Notifications support Nfty, Pushover, Slack and Discord.
- Many new security related notifications.
-- #5523
-- #8531
-- #8307
-- #7945
-- #6760
-- #6557
+- [Issue 5523](https://github.com/firefly-iii/firefly-iii/issues/5523) (Add comment on a budget for a given month) reported by @n-serrette
+- [Issue 8531](https://github.com/firefly-iii/firefly-iii/issues/8531) (Add `notes` to transaction audit report) reported by @clouserw
+- [Issue 8307](https://github.com/firefly-iii/firefly-iii/issues/8307) (Notification support for Ntfy (and other push notification tools)) reported by @ragnarkarlsson
+- [Issue 7945](https://github.com/firefly-iii/firefly-iii/issues/7945) ("Rules" that only trigger manually) reported by @SekoiaTree
+- [Issue 6760](https://github.com/firefly-iii/firefly-iii/issues/6760) (Add a new trigger for automated rules) reported by @Gsyltc
+- [Issue 6557](https://github.com/firefly-iii/firefly-iii/issues/6557) (Piggy Banks - Draw Funds from Multiple Accounts) reported by @BugPhobic
### Changed
- Firefly III requires PHP 8.4.
-- #9501
+- [Issue 9501](https://github.com/firefly-iii/firefly-iii/issues/9501) (PHP8.4 support) reported by @JC5
- Docker container no longer runs under root.
- "Bills" are now called "subscriptions" to better reflect their purpose.
@@ -31,8 +31,8 @@ This project adheres to [Semantic Versioning](http://semver.org/).
### Fixed
-- #9532
-- #7288
+- [Issue 9532](https://github.com/firefly-iii/firefly-iii/issues/9532) (ReportSum Integrity Check fails due to empty foreign_amount) reported by @SircasticFox
+- [Issue 7288](https://github.com/firefly-iii/firefly-iii/issues/7288) (currentMonthStart/currentMonthEnd not working for no-budget view) reported by @bradsk88
### API
diff --git a/config/firefly.php b/config/firefly.php
index 5968f7c992..4f59a04af3 100644
--- a/config/firefly.php
+++ b/config/firefly.php
@@ -81,7 +81,7 @@ return [
'running_balance_column' => env('USE_RUNNING_BALANCE', false),
// see cer.php for exchange rates feature flag.
],
- 'version' => 'develop/2024-12-27',
+ 'version' => 'develop/2024-12-28',
'api_version' => '2.1.0', // field is no longer used.
'db_version' => 25,
diff --git a/database/migrations/2024_11_30_075826_multi_piggy.php b/database/migrations/2024_11_30_075826_multi_piggy.php
index f32628e86f..86af179a03 100644
--- a/database/migrations/2024_11_30_075826_multi_piggy.php
+++ b/database/migrations/2024_11_30_075826_multi_piggy.php
@@ -5,6 +5,7 @@ declare(strict_types=1);
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
+use Illuminate\Support\Facades\Log;
return new class () extends Migration {
/**
@@ -19,7 +20,7 @@ return new class () extends Migration {
$table->dropForeign('piggy_banks_account_id_foreign');
});
} catch (RuntimeException $e) {
- \Illuminate\Support\Facades\Log::error('Could not drop foreign key "piggy_banks_account_id_foreign". Probably not an issue.');
+ Log::error('Could not drop foreign key "piggy_banks_account_id_foreign". Probably not an issue.');
}
Schema::table('piggy_banks', static function (Blueprint $table): void {
// 2. make column nullable.
diff --git a/resources/lang/en_US/firefly.php b/resources/lang/en_US/firefly.php
index 6921b61bb6..e4490fba3f 100644
--- a/resources/lang/en_US/firefly.php
+++ b/resources/lang/en_US/firefly.php
@@ -1913,7 +1913,7 @@ return [
'extension_date_is' => 'Extension date is {date}',
// accounts:
- 'account_locked_currency' => 'The currency of this account must remain :name as long as piggy banks are linked to it.',
+ 'account_locked_currency' => 'The currency of this account must remain :name as long as piggy banks are linked to it.',
'i_am_owed_amount' => 'I am owed amount',
'i_owe_amount' => 'I owe amount',
'inactive_account_link' => 'You have :count inactive (archived) account, which you can view on this separate page.|You have :count inactive (archived) accounts, which you can view on this separate page.',
From 42dc8486e97d2f92f0c4ee0f2ecedaa2c9010633 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 11:16:55 +0100
Subject: [PATCH 141/167] Fix string.
---
resources/lang/en_US/firefly.php | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/resources/lang/en_US/firefly.php b/resources/lang/en_US/firefly.php
index e4490fba3f..3e4e0de345 100644
--- a/resources/lang/en_US/firefly.php
+++ b/resources/lang/en_US/firefly.php
@@ -1468,7 +1468,7 @@ return [
'exchange_rates_intro' => 'Firefly III supports downloading and using exchange rates. Read more about this in the documentation.',
'exchange_rates_from_to' => 'Between {from} and {to} (and the other way around)',
'header_exchange_rates_rates' => 'Exchange rates',
- 'exchange_rates_intro_rates' => 'Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.',
+ 'exchange_rates_intro_rates' => 'Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate "1" will be used.',
'header_exchange_rates_table' => 'Table with exchange rates',
'help_rate_form' => 'On this day, how many {to} will you get for one {from}?',
'save_new_rate' => 'Save new rate',
From 507040f1fdb7d1b7e2d41ecddc6827b1c715a104 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 13:36:25 +0100
Subject: [PATCH 142/167] Update various code for sqlite compatibility.
---
.../Controllers/Summary/BasicController.php | 10 +--
.../Commands/Integrity/ReportsIntegrity.php | 1 -
.../Events/Model/BudgetLimitHandler.php | 51 ++++++++--------
.../Observer/AvailableBudgetObserver.php | 1 +
app/Handlers/Observer/BudgetLimitObserver.php | 1 +
.../Controllers/System/InstallController.php | 4 +-
.../Budget/AvailableBudgetRepository.php | 12 ++--
.../Budget/OperationsRepository.php | 2 +-
app/Support/Amount.php | 61 ++++++++++---------
9 files changed, 76 insertions(+), 67 deletions(-)
diff --git a/app/Api/V1/Controllers/Summary/BasicController.php b/app/Api/V1/Controllers/Summary/BasicController.php
index 9dcb45b576..eadf5e01f6 100644
--- a/app/Api/V1/Controllers/Summary/BasicController.php
+++ b/app/Api/V1/Controllers/Summary/BasicController.php
@@ -103,10 +103,10 @@ class BasicController extends Controller
$billData = $this->getBillInformation($start, $end);
$spentData = $this->getLeftToSpendInfo($start, $end);
$netWorthData = $this->getNetWorthInfo($start, $end);
- // $balanceData = [];
- // $billData = [];
- // $spentData = [];
- // $netWorthData = [];
+// $balanceData = [];
+// $billData = [];
+// $spentData = [];
+// $netWorthData = [];
$total = array_merge($balanceData, $billData, $spentData, $netWorthData);
// give new keys
@@ -276,13 +276,13 @@ class BasicController extends Controller
*/
private function getLeftToSpendInfo(Carbon $start, Carbon $end): array
{
+ Log::debug(sprintf('Now in getLeftToSpendInfo("%s", "%s")', $start->format('Y-m-d H:i:s'), $end->format('Y-m-d H:i:s')));
$return = [];
$today = today(config('app.timezone'));
$available = $this->abRepository->getAvailableBudgetWithCurrency($start, $end);
$budgets = $this->budgetRepository->getActiveBudgets();
$spent = $this->opsRepository->sumExpenses($start, $end, null, $budgets);
$days = (int) $today->diffInDays($end, true) + 1;
- Log::debug(sprintf('Now in getLeftToSpendInfo("%s", "%s")', $start->format('Y-m-d H:i:s'), $end->format('Y-m-d H:i:s')));
foreach ($spent as $row) {
// either an amount was budgeted or 0 is available.
diff --git a/app/Console/Commands/Integrity/ReportsIntegrity.php b/app/Console/Commands/Integrity/ReportsIntegrity.php
index 1d180a31e6..2ac856b24b 100644
--- a/app/Console/Commands/Integrity/ReportsIntegrity.php
+++ b/app/Console/Commands/Integrity/ReportsIntegrity.php
@@ -45,7 +45,6 @@ class ReportsIntegrity extends Command
return 1;
}
$commands = [
- // 'firefly-iii:add-timezones-to-dates',
'integrity:empty-objects',
'integrity:total-sums',
];
diff --git a/app/Handlers/Events/Model/BudgetLimitHandler.php b/app/Handlers/Events/Model/BudgetLimitHandler.php
index e1b807d185..6164460cdd 100644
--- a/app/Handlers/Events/Model/BudgetLimitHandler.php
+++ b/app/Handlers/Events/Model/BudgetLimitHandler.php
@@ -32,6 +32,7 @@ use FireflyIII\Models\Budget;
use FireflyIII\Models\BudgetLimit;
use FireflyIII\Repositories\Budget\BudgetLimitRepositoryInterface;
use FireflyIII\User;
+use Illuminate\Support\Facades\Log;
use Psr\Container\ContainerExceptionInterface;
use Psr\Container\NotFoundExceptionInterface;
use Spatie\Period\Boundaries;
@@ -45,20 +46,20 @@ class BudgetLimitHandler
{
public function created(Created $event): void
{
- app('log')->debug(sprintf('BudgetLimitHandler::created(#%s)', $event->budgetLimit->id));
+ Log::debug(sprintf('BudgetLimitHandler::created(#%s)', $event->budgetLimit->id));
$this->updateAvailableBudget($event->budgetLimit);
}
private function updateAvailableBudget(BudgetLimit $budgetLimit): void
{
- app('log')->debug(sprintf('Now in updateAvailableBudget(#%d)', $budgetLimit->id));
+ Log::debug(sprintf('Now in updateAvailableBudget(limit #%d)', $budgetLimit->id));
$budget = Budget::find($budgetLimit->budget_id);
if (null === $budget) {
- app('log')->warning('Budget is null, probably deleted, find deleted version.');
+ Log::warning('Budget is null, probably deleted, find deleted version.');
$budget = Budget::withTrashed()->find($budgetLimit->budget_id);
}
if (null === $budget) {
- app('log')->warning('Budget is still null, cannot continue, will delete budget limit.');
+ Log::warning('Budget is still null, cannot continue, will delete budget limit.');
$budgetLimit->forceDelete();
return;
@@ -69,7 +70,7 @@ class BudgetLimitHandler
// sanity check. It happens when the budget has been deleted so the original user is unknown.
if (null === $user) {
- app('log')->warning('User is null, cannot continue.');
+ Log::warning('User is null, cannot continue.');
$budgetLimit->forceDelete();
return;
@@ -82,7 +83,7 @@ class BudgetLimitHandler
try {
$viewRange = app('preferences')->getForUser($user, 'viewRange', '1M')->data;
} catch (ContainerExceptionInterface|NotFoundExceptionInterface $e) {
- app('log')->error($e->getMessage());
+ Log::error($e->getMessage());
$viewRange = '1M';
}
// safety catch
@@ -97,7 +98,7 @@ class BudgetLimitHandler
// limit period in total is:
$limitPeriod = Period::make($start, $end, precision: Precision::DAY(), boundaries: Boundaries::EXCLUDE_NONE());
- app('log')->debug(sprintf('Limit period is from %s to %s', $start->format('Y-m-d'), $end->format('Y-m-d')));
+ Log::debug(sprintf('Limit period is from %s to %s', $start->format('Y-m-d'), $end->format('Y-m-d')));
// from the start until the end of the budget limit, need to loop!
$current = clone $start;
@@ -106,16 +107,14 @@ class BudgetLimitHandler
// create or find AB for this particular period, and set the amount accordingly.
/** @var null|AvailableBudget $availableBudget */
- $availableBudget = $user->availableBudgets()->where('start_date', $current->format('Y-m-d'))->where(
- 'end_date',
- $currentEnd->format('Y-m-d')
- )->where('transaction_currency_id', $budgetLimit->transaction_currency_id)->first();
+ $availableBudget = $user->availableBudgets()->where('start_date', $current->format('Y-m-d'))->where('end_date', $currentEnd->format('Y-m-d'))->where('transaction_currency_id', $budgetLimit->transaction_currency_id)->first();
if (null !== $availableBudget) {
- app('log')->debug('Found 1 AB, will update.');
+ Log::debug('Found 1 AB, will update.');
$this->calculateAmount($availableBudget);
}
if (null === $availableBudget) {
+ Log::debug('No AB found, will create.');
// if not exists:
$currentPeriod = Period::make($current, $currentEnd, precision: Precision::DAY(), boundaries: Boundaries::EXCLUDE_NONE());
$daily = $this->getDailyAmount($budgetLimit);
@@ -126,10 +125,10 @@ class BudgetLimitHandler
$amount = 0 === $budgetLimit->id ? '0' : $budgetLimit->amount;
}
if (0 === bccomp($amount, '0')) {
- app('log')->debug('Amount is zero, will not create AB.');
+ Log::debug('Amount is zero, will not create AB.');
}
if (0 !== bccomp($amount, '0')) {
- app('log')->debug(sprintf('Will create AB for period %s to %s', $current->format('Y-m-d'), $currentEnd->format('Y-m-d')));
+ Log::debug(sprintf('Will create AB for period %s to %s', $current->format('Y-m-d'), $currentEnd->format('Y-m-d')));
$availableBudget = new AvailableBudget(
[
'user_id' => $user->id,
@@ -143,7 +142,7 @@ class BudgetLimitHandler
]
);
$availableBudget->save();
- app('log')->debug(sprintf('ID of new AB is #%d', $availableBudget->id));
+ Log::debug(sprintf('ID of new AB is #%d', $availableBudget->id));
}
}
@@ -158,7 +157,7 @@ class BudgetLimitHandler
$repository->setUser($availableBudget->user);
$newAmount = '0';
$abPeriod = Period::make($availableBudget->start_date, $availableBudget->end_date, Precision::DAY());
- app('log')->debug(
+ Log::debug(
sprintf(
'Now at AB #%d, ("%s" to "%s")',
$availableBudget->id,
@@ -168,11 +167,11 @@ class BudgetLimitHandler
);
// have to recalculate everything just in case.
$set = $repository->getAllBudgetLimitsByCurrency($availableBudget->transactionCurrency, $availableBudget->start_date, $availableBudget->end_date);
- app('log')->debug(sprintf('Found %d interesting budget limit(s).', $set->count()));
+ Log::debug(sprintf('Found %d interesting budget limit(s).', $set->count()));
/** @var BudgetLimit $budgetLimit */
foreach ($set as $budgetLimit) {
- app('log')->debug(
+ Log::debug(
sprintf(
'Found interesting budget limit #%d ("%s" to "%s")',
$budgetLimit->id,
@@ -189,16 +188,16 @@ class BudgetLimitHandler
);
// if both equal each other, amount from this BL must be added to the AB
if ($limitPeriod->equals($abPeriod)) {
- app('log')->debug('This budget limit is equal to the available budget period.');
+ Log::debug('This budget limit is equal to the available budget period.');
$newAmount = bcadd($newAmount, $budgetLimit->amount);
}
// if budget limit period is inside AB period, it can be added in full.
if (!$limitPeriod->equals($abPeriod) && $abPeriod->contains($limitPeriod)) {
- app('log')->debug('This budget limit is smaller than the available budget period.');
+ Log::debug('This budget limit is smaller than the available budget period.');
$newAmount = bcadd($newAmount, $budgetLimit->amount);
}
if (!$limitPeriod->equals($abPeriod) && !$abPeriod->contains($limitPeriod) && $abPeriod->overlapsWith($limitPeriod)) {
- app('log')->debug('This budget limit is something else entirely!');
+ Log::debug('This budget limit is something else entirely!');
$overlap = $abPeriod->overlap($limitPeriod);
if (null !== $overlap) {
$length = $overlap->length();
@@ -208,12 +207,12 @@ class BudgetLimitHandler
}
}
if (0 === bccomp('0', $newAmount)) {
- app('log')->debug('New amount is zero, deleting AB.');
+ Log::debug('New amount is zero, deleting AB.');
$availableBudget->delete();
return;
}
- app('log')->debug(sprintf('Concluded new amount for this AB must be %s', $newAmount));
+ Log::debug(sprintf('Concluded new amount for this AB must be %s', $newAmount));
$availableBudget->amount = app('steam')->bcround($newAmount, $availableBudget->transactionCurrency->decimal_places);
$availableBudget->save();
}
@@ -231,7 +230,7 @@ class BudgetLimitHandler
);
$days = $limitPeriod->length();
$amount = bcdiv($budgetLimit->amount, (string) $days, 12);
- app('log')->debug(
+ Log::debug(
sprintf('Total amount for budget limit #%d is %s. Nr. of days is %d. Amount per day is %s', $budgetLimit->id, $budgetLimit->amount, $days, $amount)
);
@@ -240,7 +239,7 @@ class BudgetLimitHandler
public function deleted(Deleted $event): void
{
- app('log')->debug(sprintf('BudgetLimitHandler::deleted(#%s)', $event->budgetLimit->id));
+ Log::debug(sprintf('BudgetLimitHandler::deleted(#%s)', $event->budgetLimit->id));
$budgetLimit = $event->budgetLimit;
$budgetLimit->id = 0;
$this->updateAvailableBudget($event->budgetLimit);
@@ -248,7 +247,7 @@ class BudgetLimitHandler
public function updated(Updated $event): void
{
- app('log')->debug(sprintf('BudgetLimitHandler::updated(#%s)', $event->budgetLimit->id));
+ Log::debug(sprintf('BudgetLimitHandler::updated(#%s)', $event->budgetLimit->id));
$this->updateAvailableBudget($event->budgetLimit);
}
}
diff --git a/app/Handlers/Observer/AvailableBudgetObserver.php b/app/Handlers/Observer/AvailableBudgetObserver.php
index 3017450bd3..4e9b8cb57a 100644
--- a/app/Handlers/Observer/AvailableBudgetObserver.php
+++ b/app/Handlers/Observer/AvailableBudgetObserver.php
@@ -46,6 +46,7 @@ class AvailableBudgetObserver
private function updateNativeAmount(AvailableBudget $availableBudget): void
{
if (!Amount::convertToNative($availableBudget->user)) {
+ Log::debug('Do not update native available amount of the available budget.');
return;
}
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($availableBudget->user->userGroup);
diff --git a/app/Handlers/Observer/BudgetLimitObserver.php b/app/Handlers/Observer/BudgetLimitObserver.php
index af029db737..78ed28846d 100644
--- a/app/Handlers/Observer/BudgetLimitObserver.php
+++ b/app/Handlers/Observer/BudgetLimitObserver.php
@@ -46,6 +46,7 @@ class BudgetLimitObserver
private function updateNativeAmount(BudgetLimit $budgetLimit): void
{
if (!Amount::convertToNative($budgetLimit->budget->user)) {
+ Log::debug('Do not update native amount of the budget limit.');
return;
}
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($budgetLimit->budget->user->userGroup);
diff --git a/app/Http/Controllers/System/InstallController.php b/app/Http/Controllers/System/InstallController.php
index c40c2a73bc..c2f41df459 100644
--- a/app/Http/Controllers/System/InstallController.php
+++ b/app/Http/Controllers/System/InstallController.php
@@ -62,8 +62,8 @@ class InstallController extends Controller
'migrate' => ['--seed' => true, '--force' => true],
'generate-keys' => [], // an exception :(
'firefly-iii:upgrade-database' => [],
- 'firefly-iii:correct-database' => [],
- 'firefly-iii:report-integrity' => [],
+ //'firefly-iii:correct-database' => [],
+ //'firefly-iii:report-integrity' => [],
'firefly-iii:set-latest-version' => ['--james-is-cool' => true],
'firefly-iii:verify-security-alerts' => [],
];
diff --git a/app/Repositories/Budget/AvailableBudgetRepository.php b/app/Repositories/Budget/AvailableBudgetRepository.php
index becbf2a079..b985a4e25f 100644
--- a/app/Repositories/Budget/AvailableBudgetRepository.php
+++ b/app/Repositories/Budget/AvailableBudgetRepository.php
@@ -68,8 +68,8 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
if (null !== $start && null !== $end) {
$query->where(
static function (Builder $q1) use ($start, $end): void { // @phpstan-ignore-line
- $q1->where('start_date', '=', $start->format('Y-m-d'));
- $q1->where('end_date', '=', $end->format('Y-m-d'));
+ $q1->where('start_date', '=', $start->format('Y-m-d H:i:s'));
+ $q1->where('end_date', '=', $end->format('Y-m-d H:i:s'));
}
);
}
@@ -128,12 +128,15 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
public function getAvailableBudgetWithCurrency(Carbon $start, Carbon $end): array
{
+ Log::debug(sprintf('Now in %s(%s, %s)',__METHOD__, $start->format('Y-m-d H:i:s'), $end->format('Y-m-d H:i:s')));
$return = [];
$availableBudgets = $this->user->availableBudgets()
- ->where('start_date', $start->format('Y-m-d'))
- ->where('end_date', $end->format('Y-m-d'))->get()
+ ->where('start_date', $start->format('Y-m-d H:i:s'))
+ ->where('end_date', $end->format('Y-m-d H:i:s'))->get()
;
+ Log::debug(sprintf('Found %d available budgets', $availableBudgets->count()));
+
// use native amount if necessary?
$convertToNative = Amount::convertToNative($this->user);
$default = Amount::getDefaultCurrency();
@@ -144,6 +147,7 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
$field = $convertToNative && $availableBudget->transaction_currency_id !== $default->id ? 'native_amount' : 'amount';
$return[$currencyId] ??= '0';
$return[$currencyId] = bcadd($return[$currencyId], $availableBudget->{$field});
+ Log::debug(sprintf('Add #%d %s (%s) for a total of %s', $currencyId, $availableBudget->{$field}, $field, $return[$currencyId]));
}
return $return;
diff --git a/app/Repositories/Budget/OperationsRepository.php b/app/Repositories/Budget/OperationsRepository.php
index fe695fa062..75404c40c8 100644
--- a/app/Repositories/Budget/OperationsRepository.php
+++ b/app/Repositories/Budget/OperationsRepository.php
@@ -211,7 +211,7 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $budgets = null,
?TransactionCurrency $currency = null
): array {
- Log::debug('Start of sumExpenses.');
+ Log::debug(sprintf('Start of %s.', __METHOD__));
// this collector excludes all transfers TO liabilities (which are also withdrawals)
// because those expenses only become expenses once they move from the liability to the friend.
diff --git a/app/Support/Amount.php b/app/Support/Amount.php
index 1d55989e52..a5e5806a50 100644
--- a/app/Support/Amount.php
+++ b/app/Support/Amount.php
@@ -28,9 +28,10 @@ use FireflyIII\Models\Transaction;
use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Models\TransactionJournal;
use FireflyIII\Models\UserGroup;
+use FireflyIII\Support\Facades\Preferences;
use FireflyIII\User;
use Illuminate\Support\Collection;
-use FireflyIII\Support\Facades\Preferences;
+use Illuminate\Support\Facades\Log;
/**
* Class Amount.
@@ -71,10 +72,14 @@ class Amount
public function convertToNative(?User $user = null): bool
{
if (null === $user) {
- return Preferences::get('convert_to_native', false)->data && config('cer.enabled');
+ $result = Preferences::get('convert_to_native', false)->data && config('cer.enabled');
+// Log::debug(sprintf('convertToNative [a]: %s', var_export($result, true)));
+ return $result;
}
- return Preferences::getForUser($user, 'convert_to_native', false)->data && config('cer.enabled');
+ $result = Preferences::getForUser($user, 'convert_to_native', false)->data && config('cer.enabled');
+ //Log::debug(sprintf('convertToNative [b]: %s', var_export($result, true)));
+ return $result;
}
/**
@@ -83,16 +88,16 @@ class Amount
*/
public function getAmountFromJournalObject(TransactionJournal $journal): string
{
- $convertToNative = $this->convertToNative();
- $currency = $this->getDefaultCurrency();
- $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
+ $convertToNative = $this->convertToNative();
+ $currency = $this->getDefaultCurrency();
+ $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
/** @var null|Transaction $sourceTransaction */
$sourceTransaction = $journal->transactions()->where('amount', '<', 0)->first();
if (null === $sourceTransaction) {
return '0';
}
- $amount = $sourceTransaction->{$field} ?? '0';
+ $amount = $sourceTransaction->{$field} ?? '0';
if ((int) $sourceTransaction->foreign_currency_id === $currency->id) {
// use foreign amount instead!
$amount = (string) $sourceTransaction->foreign_amount; // hard coded to be foreign amount.
@@ -111,15 +116,15 @@ class Amount
*/
public function formatFlat(string $symbol, int $decimalPlaces, string $amount, ?bool $coloured = null): string
{
- $locale = app('steam')->getLocale();
- $rounded = app('steam')->bcround($amount, $decimalPlaces);
+ $locale = app('steam')->getLocale();
+ $rounded = app('steam')->bcround($amount, $decimalPlaces);
$coloured ??= true;
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$fmt->setSymbol(\NumberFormatter::CURRENCY_SYMBOL, $symbol);
$fmt->setAttribute(\NumberFormatter::MIN_FRACTION_DIGITS, $decimalPlaces);
$fmt->setAttribute(\NumberFormatter::MAX_FRACTION_DIGITS, $decimalPlaces);
- $result = (string) $fmt->format((float) $rounded); // intentional float
+ $result = (string) $fmt->format((float) $rounded); // intentional float
if (true === $coloured) {
if (1 === bccomp($rounded, '0')) {
@@ -165,7 +170,7 @@ class Amount
public function getDefaultCurrencyByUserGroup(UserGroup $userGroup): TransactionCurrency
{
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty('getDefaultCurrencyByGroup');
$cache->addProperty($userGroup->id);
if ($cache->has()) {
@@ -228,20 +233,20 @@ class Amount
private function getLocaleInfo(): array
{
// get config from preference, not from translation:
- $locale = app('steam')->getLocale();
- $array = app('steam')->getLocaleArray($locale);
+ $locale = app('steam')->getLocale();
+ $array = app('steam')->getLocaleArray($locale);
setlocale(LC_MONETARY, $array);
- $info = localeconv();
+ $info = localeconv();
// correct variables
- $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
- $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
+ $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
+ $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
- $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
- $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
+ $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
+ $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$info['mon_decimal_point'] = $fmt->getSymbol(\NumberFormatter::MONETARY_SEPARATOR_SYMBOL);
$info['mon_thousands_sep'] = $fmt->getSymbol(\NumberFormatter::MONETARY_GROUPING_SEPARATOR_SYMBOL);
@@ -264,7 +269,7 @@ class Amount
public static function getAmountJsConfig(bool $sepBySpace, int $signPosn, string $sign, bool $csPrecedes): string
{
// negative first:
- $space = ' ';
+ $space = ' ';
// require space between symbol and amount?
if (false === $sepBySpace) {
@@ -273,11 +278,11 @@ class Amount
// there are five possible positions for the "+" or "-" sign (if it is even used)
// pos_a and pos_e could be the ( and ) symbol.
- $posA = ''; // before everything
- $posB = ''; // before currency symbol
- $posC = ''; // after currency symbol
- $posD = ''; // before amount
- $posE = ''; // after everything
+ $posA = ''; // before everything
+ $posB = ''; // before currency symbol
+ $posC = ''; // after currency symbol
+ $posD = ''; // before amount
+ $posE = ''; // after everything
// format would be (currency before amount)
// AB%sC_D%vE
@@ -319,11 +324,11 @@ class Amount
}
// default is amount before currency
- $format = $posA.$posD.'%v'.$space.$posB.'%s'.$posC.$posE;
+ $format = $posA . $posD . '%v' . $space . $posB . '%s' . $posC . $posE;
if ($csPrecedes) {
// alternative is currency before amount
- $format = $posA.$posB.'%s'.$posC.$space.$posD.'%v'.$posE;
+ $format = $posA . $posB . '%s' . $posC . $space . $posD . '%v' . $posE;
}
return $format;
From 82abee37de05e238d30b6a027e95c7f7612e36f3 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 13:45:45 +0100
Subject: [PATCH 143/167] Fix a string of text.
---
resources/lang/en_US/firefly.php | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/resources/lang/en_US/firefly.php b/resources/lang/en_US/firefly.php
index 3e4e0de345..bd38b2404d 100644
--- a/resources/lang/en_US/firefly.php
+++ b/resources/lang/en_US/firefly.php
@@ -1258,8 +1258,8 @@ return [
'rule_trigger_not_source_balance_gt' => 'Source account balance is less than or equal to :trigger_value',
'rule_trigger_not_source_balance_gte' => 'Source account balance is less than :trigger_value',
'rule_trigger_not_source_balance_is' => 'Source account balance is not :trigger_value',
- 'rule_trigger_not_source_balance_lt' => 'Source account balance is greater than or equal to :trigger_value',
- 'rule_trigger_not_source_balance_lte' => 'Source account balance is greater than :trigger_value',
+ 'rule_trigger_not_source_balance_lt' => 'Source account balance is more than or equal to :trigger_value',
+ 'rule_trigger_not_source_balance_lte' => 'Source account balance is more than :trigger_value',
// Ignore this comment
From 0f68735e1ce3f3abe60996357a66db1e83098561 Mon Sep 17 00:00:00 2001
From: github-actions <41898282+github-actions[bot]@users.noreply.github.com>
Date: Sat, 28 Dec 2024 13:59:31 +0100
Subject: [PATCH 144/167] Auto commit for release 'develop' on 2024-12-28
---
.../Controllers/Summary/BasicController.php | 8 +--
.../Observer/AvailableBudgetObserver.php | 1 +
app/Handlers/Observer/BudgetLimitObserver.php | 1 +
.../Controllers/System/InstallController.php | 4 +-
.../Budget/AvailableBudgetRepository.php | 2 +-
app/Support/Amount.php | 60 +++++++++----------
composer.lock | 14 ++---
resources/assets/v1/src/locales/bg.json | 2 +-
resources/assets/v1/src/locales/ca.json | 2 +-
resources/assets/v1/src/locales/cs.json | 2 +-
resources/assets/v1/src/locales/da.json | 2 +-
resources/assets/v1/src/locales/de.json | 6 +-
resources/assets/v1/src/locales/el.json | 2 +-
resources/assets/v1/src/locales/en-gb.json | 2 +-
resources/assets/v1/src/locales/en.json | 2 +-
resources/assets/v1/src/locales/es.json | 2 +-
resources/assets/v1/src/locales/fi.json | 2 +-
resources/assets/v1/src/locales/fr.json | 2 +-
resources/assets/v1/src/locales/hu.json | 2 +-
resources/assets/v1/src/locales/id.json | 2 +-
resources/assets/v1/src/locales/it.json | 2 +-
resources/assets/v1/src/locales/ja.json | 2 +-
resources/assets/v1/src/locales/ko.json | 2 +-
resources/assets/v1/src/locales/nb.json | 2 +-
resources/assets/v1/src/locales/nl.json | 22 +++----
resources/assets/v1/src/locales/nn.json | 2 +-
resources/assets/v1/src/locales/pl.json | 2 +-
resources/assets/v1/src/locales/pt-br.json | 2 +-
resources/assets/v1/src/locales/pt.json | 2 +-
resources/assets/v1/src/locales/ro.json | 2 +-
resources/assets/v1/src/locales/ru.json | 2 +-
resources/assets/v1/src/locales/sk.json | 2 +-
resources/assets/v1/src/locales/sl.json | 2 +-
resources/assets/v1/src/locales/sv.json | 2 +-
resources/assets/v1/src/locales/tr.json | 2 +-
resources/assets/v1/src/locales/uk.json | 2 +-
resources/assets/v1/src/locales/vi.json | 2 +-
resources/assets/v1/src/locales/zh-cn.json | 2 +-
resources/assets/v1/src/locales/zh-tw.json | 2 +-
39 files changed, 89 insertions(+), 89 deletions(-)
diff --git a/app/Api/V1/Controllers/Summary/BasicController.php b/app/Api/V1/Controllers/Summary/BasicController.php
index eadf5e01f6..cea491fc4d 100644
--- a/app/Api/V1/Controllers/Summary/BasicController.php
+++ b/app/Api/V1/Controllers/Summary/BasicController.php
@@ -103,10 +103,10 @@ class BasicController extends Controller
$billData = $this->getBillInformation($start, $end);
$spentData = $this->getLeftToSpendInfo($start, $end);
$netWorthData = $this->getNetWorthInfo($start, $end);
-// $balanceData = [];
-// $billData = [];
-// $spentData = [];
-// $netWorthData = [];
+ // $balanceData = [];
+ // $billData = [];
+ // $spentData = [];
+ // $netWorthData = [];
$total = array_merge($balanceData, $billData, $spentData, $netWorthData);
// give new keys
diff --git a/app/Handlers/Observer/AvailableBudgetObserver.php b/app/Handlers/Observer/AvailableBudgetObserver.php
index 4e9b8cb57a..68de9677b4 100644
--- a/app/Handlers/Observer/AvailableBudgetObserver.php
+++ b/app/Handlers/Observer/AvailableBudgetObserver.php
@@ -47,6 +47,7 @@ class AvailableBudgetObserver
{
if (!Amount::convertToNative($availableBudget->user)) {
Log::debug('Do not update native available amount of the available budget.');
+
return;
}
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($availableBudget->user->userGroup);
diff --git a/app/Handlers/Observer/BudgetLimitObserver.php b/app/Handlers/Observer/BudgetLimitObserver.php
index 78ed28846d..dbc3493415 100644
--- a/app/Handlers/Observer/BudgetLimitObserver.php
+++ b/app/Handlers/Observer/BudgetLimitObserver.php
@@ -47,6 +47,7 @@ class BudgetLimitObserver
{
if (!Amount::convertToNative($budgetLimit->budget->user)) {
Log::debug('Do not update native amount of the budget limit.');
+
return;
}
$userCurrency = app('amount')->getDefaultCurrencyByUserGroup($budgetLimit->budget->user->userGroup);
diff --git a/app/Http/Controllers/System/InstallController.php b/app/Http/Controllers/System/InstallController.php
index c2f41df459..fef4db461e 100644
--- a/app/Http/Controllers/System/InstallController.php
+++ b/app/Http/Controllers/System/InstallController.php
@@ -62,8 +62,8 @@ class InstallController extends Controller
'migrate' => ['--seed' => true, '--force' => true],
'generate-keys' => [], // an exception :(
'firefly-iii:upgrade-database' => [],
- //'firefly-iii:correct-database' => [],
- //'firefly-iii:report-integrity' => [],
+ // 'firefly-iii:correct-database' => [],
+ // 'firefly-iii:report-integrity' => [],
'firefly-iii:set-latest-version' => ['--james-is-cool' => true],
'firefly-iii:verify-security-alerts' => [],
];
diff --git a/app/Repositories/Budget/AvailableBudgetRepository.php b/app/Repositories/Budget/AvailableBudgetRepository.php
index b985a4e25f..a1a23eb093 100644
--- a/app/Repositories/Budget/AvailableBudgetRepository.php
+++ b/app/Repositories/Budget/AvailableBudgetRepository.php
@@ -128,7 +128,7 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
public function getAvailableBudgetWithCurrency(Carbon $start, Carbon $end): array
{
- Log::debug(sprintf('Now in %s(%s, %s)',__METHOD__, $start->format('Y-m-d H:i:s'), $end->format('Y-m-d H:i:s')));
+ Log::debug(sprintf('Now in %s(%s, %s)', __METHOD__, $start->format('Y-m-d H:i:s'), $end->format('Y-m-d H:i:s')));
$return = [];
$availableBudgets = $this->user->availableBudgets()
->where('start_date', $start->format('Y-m-d H:i:s'))
diff --git a/app/Support/Amount.php b/app/Support/Amount.php
index a5e5806a50..aea73d2114 100644
--- a/app/Support/Amount.php
+++ b/app/Support/Amount.php
@@ -72,14 +72,12 @@ class Amount
public function convertToNative(?User $user = null): bool
{
if (null === $user) {
- $result = Preferences::get('convert_to_native', false)->data && config('cer.enabled');
-// Log::debug(sprintf('convertToNative [a]: %s', var_export($result, true)));
- return $result;
+ return Preferences::get('convert_to_native', false)->data && config('cer.enabled');
+ // Log::debug(sprintf('convertToNative [a]: %s', var_export($result, true)));
}
- $result = Preferences::getForUser($user, 'convert_to_native', false)->data && config('cer.enabled');
- //Log::debug(sprintf('convertToNative [b]: %s', var_export($result, true)));
- return $result;
+ return Preferences::getForUser($user, 'convert_to_native', false)->data && config('cer.enabled');
+ // Log::debug(sprintf('convertToNative [b]: %s', var_export($result, true)));
}
/**
@@ -88,16 +86,16 @@ class Amount
*/
public function getAmountFromJournalObject(TransactionJournal $journal): string
{
- $convertToNative = $this->convertToNative();
- $currency = $this->getDefaultCurrency();
- $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
+ $convertToNative = $this->convertToNative();
+ $currency = $this->getDefaultCurrency();
+ $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
/** @var null|Transaction $sourceTransaction */
$sourceTransaction = $journal->transactions()->where('amount', '<', 0)->first();
if (null === $sourceTransaction) {
return '0';
}
- $amount = $sourceTransaction->{$field} ?? '0';
+ $amount = $sourceTransaction->{$field} ?? '0';
if ((int) $sourceTransaction->foreign_currency_id === $currency->id) {
// use foreign amount instead!
$amount = (string) $sourceTransaction->foreign_amount; // hard coded to be foreign amount.
@@ -116,15 +114,15 @@ class Amount
*/
public function formatFlat(string $symbol, int $decimalPlaces, string $amount, ?bool $coloured = null): string
{
- $locale = app('steam')->getLocale();
- $rounded = app('steam')->bcround($amount, $decimalPlaces);
+ $locale = app('steam')->getLocale();
+ $rounded = app('steam')->bcround($amount, $decimalPlaces);
$coloured ??= true;
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$fmt->setSymbol(\NumberFormatter::CURRENCY_SYMBOL, $symbol);
$fmt->setAttribute(\NumberFormatter::MIN_FRACTION_DIGITS, $decimalPlaces);
$fmt->setAttribute(\NumberFormatter::MAX_FRACTION_DIGITS, $decimalPlaces);
- $result = (string) $fmt->format((float) $rounded); // intentional float
+ $result = (string) $fmt->format((float) $rounded); // intentional float
if (true === $coloured) {
if (1 === bccomp($rounded, '0')) {
@@ -170,7 +168,7 @@ class Amount
public function getDefaultCurrencyByUserGroup(UserGroup $userGroup): TransactionCurrency
{
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty('getDefaultCurrencyByGroup');
$cache->addProperty($userGroup->id);
if ($cache->has()) {
@@ -233,20 +231,20 @@ class Amount
private function getLocaleInfo(): array
{
// get config from preference, not from translation:
- $locale = app('steam')->getLocale();
- $array = app('steam')->getLocaleArray($locale);
+ $locale = app('steam')->getLocale();
+ $array = app('steam')->getLocaleArray($locale);
setlocale(LC_MONETARY, $array);
- $info = localeconv();
+ $info = localeconv();
// correct variables
- $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
- $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
+ $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
+ $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
- $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
- $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
+ $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
+ $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$info['mon_decimal_point'] = $fmt->getSymbol(\NumberFormatter::MONETARY_SEPARATOR_SYMBOL);
$info['mon_thousands_sep'] = $fmt->getSymbol(\NumberFormatter::MONETARY_GROUPING_SEPARATOR_SYMBOL);
@@ -269,7 +267,7 @@ class Amount
public static function getAmountJsConfig(bool $sepBySpace, int $signPosn, string $sign, bool $csPrecedes): string
{
// negative first:
- $space = ' ';
+ $space = ' ';
// require space between symbol and amount?
if (false === $sepBySpace) {
@@ -278,11 +276,11 @@ class Amount
// there are five possible positions for the "+" or "-" sign (if it is even used)
// pos_a and pos_e could be the ( and ) symbol.
- $posA = ''; // before everything
- $posB = ''; // before currency symbol
- $posC = ''; // after currency symbol
- $posD = ''; // before amount
- $posE = ''; // after everything
+ $posA = ''; // before everything
+ $posB = ''; // before currency symbol
+ $posC = ''; // after currency symbol
+ $posD = ''; // before amount
+ $posE = ''; // after everything
// format would be (currency before amount)
// AB%sC_D%vE
@@ -324,11 +322,11 @@ class Amount
}
// default is amount before currency
- $format = $posA . $posD . '%v' . $space . $posB . '%s' . $posC . $posE;
+ $format = $posA.$posD.'%v'.$space.$posB.'%s'.$posC.$posE;
if ($csPrecedes) {
// alternative is currency before amount
- $format = $posA . $posB . '%s' . $posC . $space . $posD . '%v' . $posE;
+ $format = $posA.$posB.'%s'.$posC.$space.$posD.'%v'.$posE;
}
return $format;
diff --git a/composer.lock b/composer.lock
index d034bb85d7..ae1a0ee832 100644
--- a/composer.lock
+++ b/composer.lock
@@ -10287,16 +10287,16 @@
},
{
"name": "barryvdh/reflection-docblock",
- "version": "v2.1.3",
+ "version": "v2.2.0",
"source": {
"type": "git",
"url": "https://github.com/barryvdh/ReflectionDocBlock.git",
- "reference": "c6fad15f7c878be21650c51e1f841bca7e49752e"
+ "reference": "db125e8df4329bd45f2da405aab007f502f38531"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/barryvdh/ReflectionDocBlock/zipball/c6fad15f7c878be21650c51e1f841bca7e49752e",
- "reference": "c6fad15f7c878be21650c51e1f841bca7e49752e",
+ "url": "https://api.github.com/repos/barryvdh/ReflectionDocBlock/zipball/db125e8df4329bd45f2da405aab007f502f38531",
+ "reference": "db125e8df4329bd45f2da405aab007f502f38531",
"shasum": ""
},
"require": {
@@ -10312,7 +10312,7 @@
"type": "library",
"extra": {
"branch-alias": {
- "dev-master": "2.0.x-dev"
+ "dev-master": "2.2.x-dev"
}
},
"autoload": {
@@ -10333,9 +10333,9 @@
}
],
"support": {
- "source": "https://github.com/barryvdh/ReflectionDocBlock/tree/v2.1.3"
+ "source": "https://github.com/barryvdh/ReflectionDocBlock/tree/v2.2.0"
},
- "time": "2024-10-23T11:41:03+00:00"
+ "time": "2024-12-28T10:00:03+00:00"
},
{
"name": "cloudcreativity/json-api-testing",
diff --git a/resources/assets/v1/src/locales/bg.json b/resources/assets/v1/src/locales/bg.json
index 5005a763fa..ae549a681c 100644
--- a/resources/assets/v1/src/locales/bg.json
+++ b/resources/assets/v1/src/locales/bg.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/ca.json b/resources/assets/v1/src/locales/ca.json
index f806299f74..09c54614ca 100644
--- a/resources/assets/v1/src/locales/ca.json
+++ b/resources/assets/v1/src/locales/ca.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/cs.json b/resources/assets/v1/src/locales/cs.json
index 2090047177..c2bfa03955 100644
--- a/resources/assets/v1/src/locales/cs.json
+++ b/resources/assets/v1/src/locales/cs.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/da.json b/resources/assets/v1/src/locales/da.json
index fab68136ae..c938f942c4 100644
--- a/resources/assets/v1/src/locales/da.json
+++ b/resources/assets/v1/src/locales/da.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/de.json b/resources/assets/v1/src/locales/de.json
index d4f79c8e01..46ba8f5c04 100644
--- a/resources/assets/v1/src/locales/de.json
+++ b/resources/assets/v1/src/locales/de.json
@@ -36,7 +36,7 @@
"is_reconciled_fields_dropped": "Da diese Buchung abgeglichen ist, k\u00f6nnen Sie weder die Konten noch den\/die Betrag\/Betr\u00e4ge aktualisieren.",
"tags": "Schlagw\u00f6rter",
"no_budget": "(kein Budget)",
- "no_bill": "(no subscription)",
+ "no_bill": "(kein Abonnement)",
"category": "Kategorie",
"attachments": "Anh\u00e4nge",
"notes": "Notizen",
@@ -52,7 +52,7 @@
"destination_account_reconciliation": "Sie k\u00f6nnen das Zielkonto einer Kontenausgleichsbuchung nicht bearbeiten.",
"source_account_reconciliation": "Sie k\u00f6nnen das Quellkonto einer Kontenausgleichsbuchung nicht bearbeiten.",
"budget": "Budget",
- "bill": "Subscription",
+ "bill": "Abonnement",
"you_create_withdrawal": "Sie haben eine Ausgabe erstellt.",
"you_create_transfer": "Sie erstellen eine Umbuchung.",
"you_create_deposit": "Sie haben eine Einnahme erstellt.",
@@ -133,7 +133,7 @@
"header_exchange_rates": "Wechselkurse",
"exchange_rates_intro": "Firefly III unterst\u00fctzt das Herunterladen und Verwenden von Wechselkursen. Lesen Sie mehr dar\u00fcber in der Dokumentation<\/a>.",
"exchange_rates_from_to": "Zwischen {from} und {to} (und umgekehrt)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Wechselkurse",
"header_exchange_rates_table": "Tabelle mit Wechselkursen",
"help_rate_form": "An diesem Tag, wie viele {to} werden Sie f\u00fcr {from} bekommen?",
diff --git a/resources/assets/v1/src/locales/el.json b/resources/assets/v1/src/locales/el.json
index d4a7fa3bb2..326ff98aab 100644
--- a/resources/assets/v1/src/locales/el.json
+++ b/resources/assets/v1/src/locales/el.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/en-gb.json b/resources/assets/v1/src/locales/en-gb.json
index 14faf5f9f1..d4d66a3e07 100644
--- a/resources/assets/v1/src/locales/en-gb.json
+++ b/resources/assets/v1/src/locales/en-gb.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/en.json b/resources/assets/v1/src/locales/en.json
index fe325fa19d..6581de5727 100644
--- a/resources/assets/v1/src/locales/en.json
+++ b/resources/assets/v1/src/locales/en.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/es.json b/resources/assets/v1/src/locales/es.json
index 9cfcc89bbb..0d8fce0071 100644
--- a/resources/assets/v1/src/locales/es.json
+++ b/resources/assets/v1/src/locales/es.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/fi.json b/resources/assets/v1/src/locales/fi.json
index e03bda98ce..9390460c6e 100644
--- a/resources/assets/v1/src/locales/fi.json
+++ b/resources/assets/v1/src/locales/fi.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/fr.json b/resources/assets/v1/src/locales/fr.json
index fbe06bd6d9..845809188f 100644
--- a/resources/assets/v1/src/locales/fr.json
+++ b/resources/assets/v1/src/locales/fr.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/hu.json b/resources/assets/v1/src/locales/hu.json
index 966ab04c23..d1b1f4a337 100644
--- a/resources/assets/v1/src/locales/hu.json
+++ b/resources/assets/v1/src/locales/hu.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/id.json b/resources/assets/v1/src/locales/id.json
index fb7a4cb267..e6b57a34e8 100644
--- a/resources/assets/v1/src/locales/id.json
+++ b/resources/assets/v1/src/locales/id.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/it.json b/resources/assets/v1/src/locales/it.json
index 67ba00c2f9..d7fa97f7d7 100644
--- a/resources/assets/v1/src/locales/it.json
+++ b/resources/assets/v1/src/locales/it.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/ja.json b/resources/assets/v1/src/locales/ja.json
index 3f863a0243..6a89c8c388 100644
--- a/resources/assets/v1/src/locales/ja.json
+++ b/resources/assets/v1/src/locales/ja.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/ko.json b/resources/assets/v1/src/locales/ko.json
index 80fd02b692..2c90553265 100644
--- a/resources/assets/v1/src/locales/ko.json
+++ b/resources/assets/v1/src/locales/ko.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/nb.json b/resources/assets/v1/src/locales/nb.json
index a24603dfc1..b23203f225 100644
--- a/resources/assets/v1/src/locales/nb.json
+++ b/resources/assets/v1/src/locales/nb.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/nl.json b/resources/assets/v1/src/locales/nl.json
index e453472574..2c3f7a6ae4 100644
--- a/resources/assets/v1/src/locales/nl.json
+++ b/resources/assets/v1/src/locales/nl.json
@@ -21,7 +21,7 @@
"apply_rules_checkbox": "Regels toepassen",
"fire_webhooks_checkbox": "Webhooks starten",
"no_budget_pointer": "Je hebt nog geen budgetten. Maak er een aantal op de budgetten<\/a>-pagina. Met budgetten kan je je uitgaven beter bijhouden.",
- "no_bill_pointer": "You seem to have no subscription yet. You should create some on the subscription<\/a>-page. Subscriptions can help you keep track of expenses.",
+ "no_bill_pointer": "Je hebt nog geen abonnementen. Maak er een aantal op de abonnementenpagina<\/a>. Met abonnementen kan je uitgaven bijhouden.",
"source_account": "Bronrekening",
"hidden_fields_preferences": "Je kan meer transactieopties inschakelen in je instellingen<\/a>.",
"destination_account": "Doelrekening",
@@ -130,15 +130,15 @@
"response": "Reactie",
"visit_webhook_url": "Bezoek URL van webhook",
"reset_webhook_secret": "Reset webhook-geheim",
- "header_exchange_rates": "Exchange rates",
- "exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
- "exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
- "header_exchange_rates_rates": "Exchange rates",
- "header_exchange_rates_table": "Table with exchange rates",
- "help_rate_form": "On this day, how many {to} will you get for one {from}?",
- "add_new_rate": "Add a new exchange rate",
- "save_new_rate": "Save new rate"
+ "header_exchange_rates": "Wisselkoersen",
+ "exchange_rates_intro": "Firefly III kan wisselkoersen downloaden en gebruiken. Lees hier meer over in de documentatie<\/a>.",
+ "exchange_rates_from_to": "Tussen {from} en {to} (en andersom)",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
+ "header_exchange_rates_rates": "Wisselkoersen",
+ "header_exchange_rates_table": "Tabel met wisselkoersen",
+ "help_rate_form": "Hoeveel {to} krijg je op deze dag voor \u00e9\u00e9n {from}?",
+ "add_new_rate": "Nieuwe wisselkoers toevoegen",
+ "save_new_rate": "Nieuwe wisselkoers opslaan"
},
"form": {
"url": "URL",
@@ -158,7 +158,7 @@
"webhook_delivery": "Bericht",
"from_currency_to_currency": "{from} → {to}",
"to_currency_from_currency": "{to} → {from}",
- "rate": "Tarief"
+ "rate": "Wisselkoers"
},
"list": {
"active": "Actief?",
diff --git a/resources/assets/v1/src/locales/nn.json b/resources/assets/v1/src/locales/nn.json
index 372e12b563..7e54e42824 100644
--- a/resources/assets/v1/src/locales/nn.json
+++ b/resources/assets/v1/src/locales/nn.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/pl.json b/resources/assets/v1/src/locales/pl.json
index b8be4db26c..e9a0327069 100644
--- a/resources/assets/v1/src/locales/pl.json
+++ b/resources/assets/v1/src/locales/pl.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/pt-br.json b/resources/assets/v1/src/locales/pt-br.json
index 94fb1e6ab2..3043c3c96a 100644
--- a/resources/assets/v1/src/locales/pt-br.json
+++ b/resources/assets/v1/src/locales/pt-br.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/pt.json b/resources/assets/v1/src/locales/pt.json
index 554b3ce031..956a62cfe6 100644
--- a/resources/assets/v1/src/locales/pt.json
+++ b/resources/assets/v1/src/locales/pt.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/ro.json b/resources/assets/v1/src/locales/ro.json
index 8767dbf3eb..e4129a99ec 100644
--- a/resources/assets/v1/src/locales/ro.json
+++ b/resources/assets/v1/src/locales/ro.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/ru.json b/resources/assets/v1/src/locales/ru.json
index 0bd9448e6a..5bd6948f95 100644
--- a/resources/assets/v1/src/locales/ru.json
+++ b/resources/assets/v1/src/locales/ru.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/sk.json b/resources/assets/v1/src/locales/sk.json
index 2b2d16d716..81ce869c5b 100644
--- a/resources/assets/v1/src/locales/sk.json
+++ b/resources/assets/v1/src/locales/sk.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/sl.json b/resources/assets/v1/src/locales/sl.json
index 9dd0deea47..0f5be1c16f 100644
--- a/resources/assets/v1/src/locales/sl.json
+++ b/resources/assets/v1/src/locales/sl.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/sv.json b/resources/assets/v1/src/locales/sv.json
index a79d228596..bb4dd88b7f 100644
--- a/resources/assets/v1/src/locales/sv.json
+++ b/resources/assets/v1/src/locales/sv.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/tr.json b/resources/assets/v1/src/locales/tr.json
index 9e0c3d1aeb..768c6f0bac 100644
--- a/resources/assets/v1/src/locales/tr.json
+++ b/resources/assets/v1/src/locales/tr.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/uk.json b/resources/assets/v1/src/locales/uk.json
index 9825ea43ee..254e22f5b4 100644
--- a/resources/assets/v1/src/locales/uk.json
+++ b/resources/assets/v1/src/locales/uk.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/vi.json b/resources/assets/v1/src/locales/vi.json
index 2b9e5fda6b..5e2e002e84 100644
--- a/resources/assets/v1/src/locales/vi.json
+++ b/resources/assets/v1/src/locales/vi.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/zh-cn.json b/resources/assets/v1/src/locales/zh-cn.json
index cc823d9749..55f1f1559b 100644
--- a/resources/assets/v1/src/locales/zh-cn.json
+++ b/resources/assets/v1/src/locales/zh-cn.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
diff --git a/resources/assets/v1/src/locales/zh-tw.json b/resources/assets/v1/src/locales/zh-tw.json
index 7fedbcdf69..5dc911c6b5 100644
--- a/resources/assets/v1/src/locales/zh-tw.json
+++ b/resources/assets/v1/src/locales/zh-tw.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Exchange rates",
"exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
"exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
- "exchange_rates_intro_rates": "Firefly III bla bla bla exchange rates. Inverse is automatically calculated if not provided. Will go back to last found rate.",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
"header_exchange_rates_rates": "Exchange rates",
"header_exchange_rates_table": "Table with exchange rates",
"help_rate_form": "On this day, how many {to} will you get for one {from}?",
From 79ca1b5f4ef7cb2d337bf5d415ba7825546e0430 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 14:08:34 +0100
Subject: [PATCH 145/167] Change some CS fixer settings.
---
.ci/php-cs-fixer/.php-cs-fixer.php | 2 +-
changelog.md | 2 ++
2 files changed, 3 insertions(+), 1 deletion(-)
diff --git a/.ci/php-cs-fixer/.php-cs-fixer.php b/.ci/php-cs-fixer/.php-cs-fixer.php
index 6d71a455ff..f178a4cf10 100644
--- a/.ci/php-cs-fixer/.php-cs-fixer.php
+++ b/.ci/php-cs-fixer/.php-cs-fixer.php
@@ -29,7 +29,7 @@ $paths = [
$current . '/../../database',
$current . '/../../routes',
$current . '/../../tests',
- $current . '/../../resources/lang',
+ $current . '/../../resources/lang/en',
];
$finder = PhpCsFixer\Finder::create()
diff --git a/changelog.md b/changelog.md
index da0a52fce3..601e222e19 100644
--- a/changelog.md
+++ b/changelog.md
@@ -16,6 +16,8 @@ This project adheres to [Semantic Versioning](http://semver.org/).
- [Issue 7945](https://github.com/firefly-iii/firefly-iii/issues/7945) ("Rules" that only trigger manually) reported by @SekoiaTree
- [Issue 6760](https://github.com/firefly-iii/firefly-iii/issues/6760) (Add a new trigger for automated rules) reported by @Gsyltc
- [Issue 6557](https://github.com/firefly-iii/firefly-iii/issues/6557) (Piggy Banks - Draw Funds from Multiple Accounts) reported by @BugPhobic
+- #5532
+- #6314
### Changed
From d96c235ffe212cedfec6668785a9b5d9235cd273 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 14:09:22 +0100
Subject: [PATCH 146/167] Fix path
---
.ci/php-cs-fixer/.php-cs-fixer.php | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/.ci/php-cs-fixer/.php-cs-fixer.php b/.ci/php-cs-fixer/.php-cs-fixer.php
index f178a4cf10..6193477e73 100644
--- a/.ci/php-cs-fixer/.php-cs-fixer.php
+++ b/.ci/php-cs-fixer/.php-cs-fixer.php
@@ -29,7 +29,7 @@ $paths = [
$current . '/../../database',
$current . '/../../routes',
$current . '/../../tests',
- $current . '/../../resources/lang/en',
+ $current . '/../../resources/lang/en_US',
];
$finder = PhpCsFixer\Finder::create()
From a1241ebedb37a7806c203c00c12062326871e7a4 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sat, 28 Dec 2024 18:38:19 +0100
Subject: [PATCH 147/167] Various multi-currency things in the autocomplete
API.
---
.../Autocomplete/AccountController.php | 37 ++++++++++---------
app/Api/V1/Controllers/Controller.php | 7 +++-
app/Api/V2/Controllers/Controller.php | 4 +-
app/Factory/PiggyBankFactory.php | 2 +-
4 files changed, 27 insertions(+), 23 deletions(-)
diff --git a/app/Api/V1/Controllers/Autocomplete/AccountController.php b/app/Api/V1/Controllers/Autocomplete/AccountController.php
index 739e99408e..fdbf680486 100644
--- a/app/Api/V1/Controllers/Autocomplete/AccountController.php
+++ b/app/Api/V1/Controllers/Autocomplete/AccountController.php
@@ -26,6 +26,7 @@ namespace FireflyIII\Api\V1\Controllers\Autocomplete;
use FireflyIII\Api\V1\Controllers\Controller;
use FireflyIII\Api\V1\Requests\Autocomplete\AutocompleteRequest;
+use FireflyIII\Enums\AccountTypeEnum;
use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Models\Account;
use FireflyIII\Models\AccountType;
@@ -62,7 +63,7 @@ class AccountController extends Controller
return $next($request);
}
);
- $this->balanceTypes = [AccountType::ASSET, AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE];
+ $this->balanceTypes = [AccountTypeEnum::ASSET->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::MORTGAGE->value];
}
/**
@@ -74,40 +75,40 @@ class AccountController extends Controller
*/
public function accounts(AutocompleteRequest $request): JsonResponse
{
- $data = $request->getData();
- $types = $data['types'];
- $query = $data['query'];
- $date = $data['date'] ?? today(config('app.timezone'));
- $return = [];
- $result = $this->repository->searchAccount((string) $query, $types, $this->parameters->get('limit'));
-
- // TODO this code is duplicated in the V2 Autocomplete controller, which means this code is due to be deprecated.
- $defaultCurrency = app('amount')->getDefaultCurrency();
+ $data = $request->getData();
+ $types = $data['types'];
+ $query = $data['query'];
+ $date = $data['date'] ?? today(config('app.timezone'));
+ $return = [];
+ $result = $this->repository->searchAccount((string) $query, $types, $this->parameters->get('limit'));
/** @var Account $account */
foreach ($result as $account) {
$nameWithBalance = $account->name;
- $currency = $this->repository->getAccountCurrency($account) ?? $defaultCurrency;
+ $currency = $this->repository->getAccountCurrency($account) ?? $this->defaultCurrency;
if (in_array($account->accountType->type, $this->balanceTypes, true)) {
$balance = Steam::finalAccountBalance($account, $date);
+ $key = $this->convertToNative && $currency->id !== $this->defaultCurrency->id ? 'native_balance' : 'balance';
+ $useCurrency = $this->convertToNative && $currency->id !== $this->defaultCurrency->id ? $this->defaultCurrency : $currency;
+ $amount = $balance[$key] ?? '0';
$nameWithBalance = sprintf(
'%s (%s)',
$account->name,
- app('amount')->formatAnything($currency, $balance['balance'], false)
+ app('amount')->formatAnything($useCurrency, $amount, false)
);
}
- $return[] = [
+ $return[] = [
'id' => (string) $account->id,
'name' => $account->name,
'name_with_balance' => $nameWithBalance,
'type' => $account->accountType->type,
- 'currency_id' => (string) $currency->id,
- 'currency_name' => $currency->name,
- 'currency_code' => $currency->code,
- 'currency_symbol' => $currency->symbol,
- 'currency_decimal_places' => $currency->decimal_places,
+ 'currency_id' => (string) $useCurrency->id,
+ 'currency_name' => $useCurrency->name,
+ 'currency_code' => $useCurrency->code,
+ 'currency_symbol' => $useCurrency->symbol,
+ 'currency_decimal_places' => $useCurrency->decimal_places,
];
}
diff --git a/app/Api/V1/Controllers/Controller.php b/app/Api/V1/Controllers/Controller.php
index 862fa08867..5f710f1220 100644
--- a/app/Api/V1/Controllers/Controller.php
+++ b/app/Api/V1/Controllers/Controller.php
@@ -28,6 +28,7 @@ use Carbon\Carbon;
use Carbon\Exceptions\InvalidDateException;
use Carbon\Exceptions\InvalidFormatException;
use FireflyIII\Models\Preference;
+use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Facades\Steam;
use FireflyIII\User;
@@ -58,6 +59,7 @@ abstract class Controller extends BaseController
protected array $allowedSort;
protected ParameterBag $parameters;
protected bool $convertToNative = false;
+ protected TransactionCurrency $defaultCurrency;
/**
* Controller constructor.
@@ -72,6 +74,7 @@ abstract class Controller extends BaseController
if (auth()->check()) {
$language = Steam::getLanguage();
$this->convertToNative = Amount::convertToNative();
+ $this->defaultCurrency = Amount::getDefaultCurrency();
app()->setLocale($language);
}
@@ -91,8 +94,8 @@ abstract class Controller extends BaseController
if ($page < 1) {
$page = 1;
}
- if ($page > 2 ** 16) {
- $page = 2 ** 16;
+ if ($page > pow(2,16)) {
+ $page = pow(2, 16);
}
$bag->set('page', $page);
diff --git a/app/Api/V2/Controllers/Controller.php b/app/Api/V2/Controllers/Controller.php
index ee8d782e48..24499ef3b5 100644
--- a/app/Api/V2/Controllers/Controller.php
+++ b/app/Api/V2/Controllers/Controller.php
@@ -93,8 +93,8 @@ class Controller extends BaseController
if ($page < 1) {
$page = 1;
}
- if ($page > 2 ** 16) {
- $page = 2 ** 16;
+ if ($page > pow(2,16)) {
+ $page = pow(2, 16);
}
$bag->set('page', $page);
diff --git a/app/Factory/PiggyBankFactory.php b/app/Factory/PiggyBankFactory.php
index e4a09ca535..fead291f9b 100644
--- a/app/Factory/PiggyBankFactory.php
+++ b/app/Factory/PiggyBankFactory.php
@@ -44,7 +44,7 @@ class PiggyBankFactory
public User $user {
set(User $value) {
$this->user = $value;
- $this->currencyRepository->setUser($value);
+ $this->currencyRepository->setUser($value);
$this->accountRepository->setUser($value);
$this->piggyBankRepository->setUser($value);
}
From ee3c6187978bf04c4b5fd91061dbe2a6ef244459 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 05:55:49 +0100
Subject: [PATCH 148/167] Fix
https://github.com/firefly-iii/firefly-iii/issues/9586
---
resources/views/emails/registered.blade.php | 4 +---
1 file changed, 1 insertion(+), 3 deletions(-)
diff --git a/resources/views/emails/registered.blade.php b/resources/views/emails/registered.blade.php
index e4a4032838..b9563a99ce 100644
--- a/resources/views/emails/registered.blade.php
+++ b/resources/views/emails/registered.blade.php
@@ -1,9 +1,7 @@
@component('mail::message')
{{ trans('email.registered_welcome') }}
-* {{ trans('email.registered_pw', ['address' => $address]) }}
-* {{ trans('email.registered_help') }}
-* {{ trans('email.registered_doc_text') }}
+{{ trans('email.registered_pw', ['address' => $address]) }} {{ trans('email.registered_help') }}
{{ trans('email.registered_closing') }}
From 7248a76c63875a909bec9ccebed0c5727e6df3c0 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 05:58:12 +0100
Subject: [PATCH 149/167] Fix chart, expand changelog.
---
.../V1/Controllers/Chart/AccountController.php | 15 ++++++---------
app/Http/Controllers/Chart/BudgetController.php | 12 ++++++------
changelog.md | 1 +
3 files changed, 13 insertions(+), 15 deletions(-)
diff --git a/app/Api/V1/Controllers/Chart/AccountController.php b/app/Api/V1/Controllers/Chart/AccountController.php
index 3739d82f5a..992477bdee 100644
--- a/app/Api/V1/Controllers/Chart/AccountController.php
+++ b/app/Api/V1/Controllers/Chart/AccountController.php
@@ -27,6 +27,7 @@ namespace FireflyIII\Api\V1\Controllers\Chart;
use Carbon\Carbon;
use FireflyIII\Api\V1\Controllers\Controller;
use FireflyIII\Api\V1\Requests\Data\DateRequest;
+use FireflyIII\Enums\AccountTypeEnum;
use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Models\Account;
use FireflyIII\Models\AccountType;
@@ -81,11 +82,10 @@ class AccountController extends Controller
$end = $dates['end'];
// user's preferences
- $defaultSet = $this->repository->getAccountsByType([AccountType::ASSET])->pluck('id')->toArray();
+ $defaultSet = $this->repository->getAccountsByType([AccountTypeEnum::ASSET->value])->pluck('id')->toArray();
/** @var Preference $frontpage */
$frontpage = app('preferences')->get('frontpageAccounts', $defaultSet);
- $default = app('amount')->getDefaultCurrency();
if (!(is_array($frontpage->data) && count($frontpage->data) > 0)) {
$frontpage->data = $defaultSet;
@@ -98,10 +98,8 @@ class AccountController extends Controller
/** @var Account $account */
foreach ($accounts as $account) {
- $currency = $this->repository->getAccountCurrency($account);
- if (null === $currency) {
- $currency = $default;
- }
+ $currency = $this->repository->getAccountCurrency($account) ?? $this->defaultCurrency;
+ $field = $this->convertToNative ? 'native_balance' : 'balance';
$currentSet = [
'label' => $account->name,
'currency_id' => (string) $currency->id,
@@ -117,12 +115,11 @@ class AccountController extends Controller
// TODO this code is also present in the V2 chart account controller so this method is due to be deprecated.
$currentStart = clone $start;
$range = app('steam')->finalAccountBalanceInRange($account, $start, clone $end, $this->convertToNative);
- // 2022-10-11 this method no longer converts to float.
- $previous = array_values($range)[0];
+ $previous = array_values($range)[0][$field];
while ($currentStart <= $end) {
$format = $currentStart->format('Y-m-d');
$label = $currentStart->toAtomString();
- $balance = array_key_exists($format, $range) ? $range[$format]['balance'] : $previous;
+ $balance = array_key_exists($format, $range) ? $range[$format][$field] : $previous;
$previous = $balance;
$currentStart->addDay();
$currentSet['entries'][$label] = $balance;
diff --git a/app/Http/Controllers/Chart/BudgetController.php b/app/Http/Controllers/Chart/BudgetController.php
index 3f92b2dabb..961c8daac5 100644
--- a/app/Http/Controllers/Chart/BudgetController.php
+++ b/app/Http/Controllers/Chart/BudgetController.php
@@ -234,8 +234,12 @@ class BudgetController extends Controller
$key = sprintf('%d-%d', $journal['source_account_id'], $journal['currency_id']);
$amount = $journal['amount'];
+ $symbol = $journal['currency_symbol'];
+ $code = $journal['currency_code'];
+ $name = $journal['currency_name'];
+
// if convert to native, use the native things, unless it's the foreign amount which is in the native currency.
- if ($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] !== $this->defaultCurrency->id) {
+ if ($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id) {
$key = sprintf('%d-%d', $journal['source_account_id'], $this->defaultCurrency->id);
$symbol = $this->defaultCurrency->symbol;
$code = $this->defaultCurrency->code;
@@ -243,11 +247,7 @@ class BudgetController extends Controller
$amount = $journal['native_amount'];
}
- if ($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id && $journal['foreign_currency_id'] === $this->defaultCurrency->id) {
- $key = sprintf('%d-%d', $journal['source_account_id'], $this->defaultCurrency->id);
- $symbol = $this->defaultCurrency->symbol;
- $code = $this->defaultCurrency->code;
- $name = $this->defaultCurrency->name;
+ if ($journal['foreign_currency_id'] === $this->defaultCurrency->id) {
$amount = $journal['foreign_amount'];
}
diff --git a/changelog.md b/changelog.md
index 601e222e19..a19fb17aa2 100644
--- a/changelog.md
+++ b/changelog.md
@@ -18,6 +18,7 @@ This project adheres to [Semantic Versioning](http://semver.org/).
- [Issue 6557](https://github.com/firefly-iii/firefly-iii/issues/6557) (Piggy Banks - Draw Funds from Multiple Accounts) reported by @BugPhobic
- #5532
- #6314
+- #9586
### Changed
From fe00c4c3738cbcda564834da666d63e50bab9beb Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 06:08:35 +0100
Subject: [PATCH 150/167] Fix unauthenticated get default currency.
---
app/Support/Amount.php | 10 ++++++----
1 file changed, 6 insertions(+), 4 deletions(-)
diff --git a/app/Support/Amount.php b/app/Support/Amount.php
index aea73d2114..13f399e5cc 100644
--- a/app/Support/Amount.php
+++ b/app/Support/Amount.php
@@ -160,10 +160,12 @@ class Amount
public function getDefaultCurrency(): TransactionCurrency
{
- /** @var User $user */
- $user = auth()->user();
-
- return $this->getDefaultCurrencyByUserGroup($user->userGroup);
+ if(auth()->check()) {
+ /** @var User $user */
+ $user = auth()->user();
+ return $this->getDefaultCurrencyByUserGroup($user->userGroup);
+ }
+ return $this->getSystemCurrency();
}
public function getDefaultCurrencyByUserGroup(UserGroup $userGroup): TransactionCurrency
From 41fa2a6208ea653f32a0fd9c933fb23063a8022e Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 06:10:54 +0100
Subject: [PATCH 151/167] Include user group in test set.
---
.../Models/TransactionCurrency/ShowController.php | 5 ++---
tests/integration/TestCase.php | 2 ++
2 files changed, 4 insertions(+), 3 deletions(-)
diff --git a/app/Api/V1/Controllers/Models/TransactionCurrency/ShowController.php b/app/Api/V1/Controllers/Models/TransactionCurrency/ShowController.php
index 363d599869..8d9cec0f1f 100644
--- a/app/Api/V1/Controllers/Models/TransactionCurrency/ShowController.php
+++ b/app/Api/V1/Controllers/Models/TransactionCurrency/ShowController.php
@@ -107,8 +107,7 @@ class ShowController extends Controller
/** @var User $user */
$user = auth()->user();
$manager = $this->getManager();
- $defaultCurrency = app('amount')->getDefaultCurrencyByUserGroup($user->userGroup);
- $this->parameters->set('defaultCurrency', $defaultCurrency);
+ $this->parameters->set('defaultCurrency', $this->defaultCurrency);
// update fields with user info.
$currency->refreshForUser($user);
@@ -135,7 +134,7 @@ class ShowController extends Controller
/** @var User $user */
$user = auth()->user();
$manager = $this->getManager();
- $currency = app('amount')->getDefaultCurrencyByUserGroup($user->userGroup);
+ $currency = $this->defaultCurrency;
// update fields with user info.
$currency->refreshForUser($user);
diff --git a/tests/integration/TestCase.php b/tests/integration/TestCase.php
index 967b8d68a7..0f73fc5894 100644
--- a/tests/integration/TestCase.php
+++ b/tests/integration/TestCase.php
@@ -52,9 +52,11 @@ abstract class TestCase extends BaseTestCase
protected function createAuthenticatedUser(): User
{
+ $group = UserGroup::create(['title' => 'test@email.com']);
return User::create([
'email' => 'test@email.com',
'password' => 'password',
+ 'user_group_id' => $group->id,
]);
}
}
From b407d8d3150cd67e5593863110350e45df03b42d Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 06:14:40 +0100
Subject: [PATCH 152/167] Add usergroup, clean up some code.
---
.../Controllers/Chart/AccountController.php | 29 +++++++++----------
.../views/emails/token-created.blade.php | 1 +
tests/integration/TestCase.php | 1 +
3 files changed, 16 insertions(+), 15 deletions(-)
diff --git a/app/Api/V1/Controllers/Chart/AccountController.php b/app/Api/V1/Controllers/Chart/AccountController.php
index 992477bdee..3f86521a4f 100644
--- a/app/Api/V1/Controllers/Chart/AccountController.php
+++ b/app/Api/V1/Controllers/Chart/AccountController.php
@@ -30,7 +30,6 @@ use FireflyIII\Api\V1\Requests\Data\DateRequest;
use FireflyIII\Enums\AccountTypeEnum;
use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Models\Account;
-use FireflyIII\Models\AccountType;
use FireflyIII\Models\Preference;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
use FireflyIII\Support\Http\Api\ApiSupport;
@@ -73,19 +72,19 @@ class AccountController extends Controller
public function overview(DateRequest $request): JsonResponse
{
// parameters for chart:
- $dates = $request->getAll();
+ $dates = $request->getAll();
/** @var Carbon $start */
- $start = $dates['start'];
+ $start = $dates['start'];
/** @var Carbon $end */
- $end = $dates['end'];
+ $end = $dates['end'];
// user's preferences
$defaultSet = $this->repository->getAccountsByType([AccountTypeEnum::ASSET->value])->pluck('id')->toArray();
/** @var Preference $frontpage */
- $frontpage = app('preferences')->get('frontpageAccounts', $defaultSet);
+ $frontpage = app('preferences')->get('frontpageAccounts', $defaultSet);
if (!(is_array($frontpage->data) && count($frontpage->data) > 0)) {
$frontpage->data = $defaultSet;
@@ -93,14 +92,14 @@ class AccountController extends Controller
}
// get accounts:
- $accounts = $this->repository->getAccountsById($frontpage->data);
- $chartData = [];
+ $accounts = $this->repository->getAccountsById($frontpage->data);
+ $chartData = [];
/** @var Account $account */
foreach ($accounts as $account) {
- $currency = $this->repository->getAccountCurrency($account) ?? $this->defaultCurrency;
- $field = $this->convertToNative ? 'native_balance' : 'balance';
- $currentSet = [
+ $currency = $this->repository->getAccountCurrency($account) ?? $this->defaultCurrency;
+ $field = $this->convertToNative && $currency->id !== $this->defaultCurrency->id ? 'native_balance' : 'balance';
+ $currentSet = [
'label' => $account->name,
'currency_id' => (string) $currency->id,
'currency_code' => $currency->code,
@@ -117,14 +116,14 @@ class AccountController extends Controller
$range = app('steam')->finalAccountBalanceInRange($account, $start, clone $end, $this->convertToNative);
$previous = array_values($range)[0][$field];
while ($currentStart <= $end) {
- $format = $currentStart->format('Y-m-d');
- $label = $currentStart->toAtomString();
- $balance = array_key_exists($format, $range) ? $range[$format][$field] : $previous;
- $previous = $balance;
+ $format = $currentStart->format('Y-m-d');
+ $label = $currentStart->toAtomString();
+ $balance = array_key_exists($format, $range) ? $range[$format][$field] : $previous;
+ $previous = $balance;
$currentStart->addDay();
$currentSet['entries'][$label] = $balance;
}
- $chartData[] = $currentSet;
+ $chartData[] = $currentSet;
}
return response()->json($chartData);
diff --git a/resources/views/emails/token-created.blade.php b/resources/views/emails/token-created.blade.php
index 57561e0c10..7d113cddca 100644
--- a/resources/views/emails/token-created.blade.php
+++ b/resources/views/emails/token-created.blade.php
@@ -10,4 +10,5 @@
- {{ trans('email.date_time') }}: {{ $time }}
- {{ trans('email.user_agent') }}: {{ $userAgent }}
+
@endcomponent
diff --git a/tests/integration/TestCase.php b/tests/integration/TestCase.php
index 0f73fc5894..bb85425ea0 100644
--- a/tests/integration/TestCase.php
+++ b/tests/integration/TestCase.php
@@ -23,6 +23,7 @@ declare(strict_types=1);
namespace Tests\integration;
+use FireflyIII\Models\UserGroup;
use FireflyIII\User;
use Illuminate\Foundation\Testing\TestCase as BaseTestCase;
use Tests\integration\Traits\CollectsValues;
From 7189986c033351ba4c2139a9de9620d93a94f06b Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 06:15:42 +0100
Subject: [PATCH 153/167] Remove some debug logging.
---
app/Support/Navigation.php | 4 ++--
1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/app/Support/Navigation.php b/app/Support/Navigation.php
index 6f3b2ae8c9..a0e3b458b6 100644
--- a/app/Support/Navigation.php
+++ b/app/Support/Navigation.php
@@ -507,12 +507,12 @@ class Navigation
$diff = $start->diffInMonths($end, true);
Log::debug(sprintf('preferredCarbonFormat(%s, %s) = %f', $start->format('Y-m-d'), $end->format('Y-m-d'), $diff));
if ($diff >= 1.001) {
- Log::debug(sprintf('Return Y-m because %s', $diff));
+// Log::debug(sprintf('Return Y-m because %s', $diff));
$format = 'Y-m';
}
if ($diff >= 12.001) {
- Log::debug(sprintf('Return Y because %s', $diff));
+// Log::debug(sprintf('Return Y because %s', $diff));
$format = 'Y';
}
From 9a9dd9e075f54b1a38cb5a4ee6bf58fc7cd343ac Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 06:17:29 +0100
Subject: [PATCH 154/167] Double fix. Not sure yet what causes this.
---
app/Support/Amount.php | 57 +++++++++++++++++++++---------------------
1 file changed, 29 insertions(+), 28 deletions(-)
diff --git a/app/Support/Amount.php b/app/Support/Amount.php
index 13f399e5cc..06a7659929 100644
--- a/app/Support/Amount.php
+++ b/app/Support/Amount.php
@@ -31,7 +31,6 @@ use FireflyIII\Models\UserGroup;
use FireflyIII\Support\Facades\Preferences;
use FireflyIII\User;
use Illuminate\Support\Collection;
-use Illuminate\Support\Facades\Log;
/**
* Class Amount.
@@ -86,16 +85,16 @@ class Amount
*/
public function getAmountFromJournalObject(TransactionJournal $journal): string
{
- $convertToNative = $this->convertToNative();
- $currency = $this->getDefaultCurrency();
- $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
+ $convertToNative = $this->convertToNative();
+ $currency = $this->getDefaultCurrency();
+ $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
/** @var null|Transaction $sourceTransaction */
$sourceTransaction = $journal->transactions()->where('amount', '<', 0)->first();
if (null === $sourceTransaction) {
return '0';
}
- $amount = $sourceTransaction->{$field} ?? '0';
+ $amount = $sourceTransaction->{$field} ?? '0';
if ((int) $sourceTransaction->foreign_currency_id === $currency->id) {
// use foreign amount instead!
$amount = (string) $sourceTransaction->foreign_amount; // hard coded to be foreign amount.
@@ -114,15 +113,15 @@ class Amount
*/
public function formatFlat(string $symbol, int $decimalPlaces, string $amount, ?bool $coloured = null): string
{
- $locale = app('steam')->getLocale();
- $rounded = app('steam')->bcround($amount, $decimalPlaces);
+ $locale = app('steam')->getLocale();
+ $rounded = app('steam')->bcround($amount, $decimalPlaces);
$coloured ??= true;
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$fmt->setSymbol(\NumberFormatter::CURRENCY_SYMBOL, $symbol);
$fmt->setAttribute(\NumberFormatter::MIN_FRACTION_DIGITS, $decimalPlaces);
$fmt->setAttribute(\NumberFormatter::MAX_FRACTION_DIGITS, $decimalPlaces);
- $result = (string) $fmt->format((float) $rounded); // intentional float
+ $result = (string) $fmt->format((float) $rounded); // intentional float
if (true === $coloured) {
if (1 === bccomp($rounded, '0')) {
@@ -160,17 +159,19 @@ class Amount
public function getDefaultCurrency(): TransactionCurrency
{
- if(auth()->check()) {
+ if (auth()->check()) {
/** @var User $user */
$user = auth()->user();
- return $this->getDefaultCurrencyByUserGroup($user->userGroup);
+ if (null !== $user->userGroup) {
+ return $this->getDefaultCurrencyByUserGroup($user->userGroup);
+ }
}
return $this->getSystemCurrency();
}
public function getDefaultCurrencyByUserGroup(UserGroup $userGroup): TransactionCurrency
{
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty('getDefaultCurrencyByGroup');
$cache->addProperty($userGroup->id);
if ($cache->has()) {
@@ -233,20 +234,20 @@ class Amount
private function getLocaleInfo(): array
{
// get config from preference, not from translation:
- $locale = app('steam')->getLocale();
- $array = app('steam')->getLocaleArray($locale);
+ $locale = app('steam')->getLocale();
+ $array = app('steam')->getLocaleArray($locale);
setlocale(LC_MONETARY, $array);
- $info = localeconv();
+ $info = localeconv();
// correct variables
- $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
- $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
+ $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
+ $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
- $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
- $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
+ $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
+ $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$info['mon_decimal_point'] = $fmt->getSymbol(\NumberFormatter::MONETARY_SEPARATOR_SYMBOL);
$info['mon_thousands_sep'] = $fmt->getSymbol(\NumberFormatter::MONETARY_GROUPING_SEPARATOR_SYMBOL);
@@ -269,7 +270,7 @@ class Amount
public static function getAmountJsConfig(bool $sepBySpace, int $signPosn, string $sign, bool $csPrecedes): string
{
// negative first:
- $space = ' ';
+ $space = ' ';
// require space between symbol and amount?
if (false === $sepBySpace) {
@@ -278,11 +279,11 @@ class Amount
// there are five possible positions for the "+" or "-" sign (if it is even used)
// pos_a and pos_e could be the ( and ) symbol.
- $posA = ''; // before everything
- $posB = ''; // before currency symbol
- $posC = ''; // after currency symbol
- $posD = ''; // before amount
- $posE = ''; // after everything
+ $posA = ''; // before everything
+ $posB = ''; // before currency symbol
+ $posC = ''; // after currency symbol
+ $posD = ''; // before amount
+ $posE = ''; // after everything
// format would be (currency before amount)
// AB%sC_D%vE
@@ -324,11 +325,11 @@ class Amount
}
// default is amount before currency
- $format = $posA.$posD.'%v'.$space.$posB.'%s'.$posC.$posE;
+ $format = $posA . $posD . '%v' . $space . $posB . '%s' . $posC . $posE;
if ($csPrecedes) {
// alternative is currency before amount
- $format = $posA.$posB.'%s'.$posC.$space.$posD.'%v'.$posE;
+ $format = $posA . $posB . '%s' . $posC . $space . $posD . '%v' . $posE;
}
return $format;
From 3c20e5f3af0e8446ae7929abf07d44a5f9677a8e Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 06:32:50 +0100
Subject: [PATCH 155/167] Make sure integers are converted to strings because
sqlite sucks.
---
app/Console/Commands/Correction/CorrectsDatabase.php | 2 +-
app/Http/Controllers/DebugController.php | 4 ++--
app/Models/Account.php | 1 +
app/Models/AutoBudget.php | 9 +++++----
app/Models/AvailableBudget.php | 3 ++-
app/Models/BudgetLimit.php | 1 +
app/Models/PiggyBank.php | 3 ++-
app/Models/PiggyBankEvent.php | 3 ++-
app/Repositories/Bill/BillRepository.php | 2 +-
app/Support/Amount.php | 2 +-
app/Support/Chart/Budget/FrontpageChartGenerator.php | 5 +++--
11 files changed, 21 insertions(+), 14 deletions(-)
diff --git a/app/Console/Commands/Correction/CorrectsDatabase.php b/app/Console/Commands/Correction/CorrectsDatabase.php
index 4e03e756f1..1d9ea62112 100644
--- a/app/Console/Commands/Correction/CorrectsDatabase.php
+++ b/app/Console/Commands/Correction/CorrectsDatabase.php
@@ -74,7 +74,7 @@ class CorrectsDatabase extends Command
'correction:recalculates-liabilities',
'correction:preferences',
// 'correction:transaction-types', // resource heavy, disabled.
- // 'correction:recalculate-native-amounts', // not necessary, disabled.
+ 'correction:recalculate-native-amounts', // not necessary, disabled.
'firefly-iii:report-integrity',
];
foreach ($commands as $command) {
diff --git a/app/Http/Controllers/DebugController.php b/app/Http/Controllers/DebugController.php
index 510a4ca910..db80fd18b4 100644
--- a/app/Http/Controllers/DebugController.php
+++ b/app/Http/Controllers/DebugController.php
@@ -160,8 +160,8 @@ class DebugController extends Controller
Artisan::call('view:clear');
// also do some recalculations.
- Artisan::call('firefly-iii:trigger-credit-recalculation');
- AccountBalanceCalculator::recalculateAll(true);
+ Artisan::call('correction:recalculates-liabilities');
+ AccountBalanceCalculator::recalculateAll(false);
try {
Artisan::call('twig:clean');
diff --git a/app/Models/Account.php b/app/Models/Account.php
index dbe1dd9388..03d87fc708 100644
--- a/app/Models/Account.php
+++ b/app/Models/Account.php
@@ -57,6 +57,7 @@ class Account extends Model
'active' => 'boolean',
'encrypted' => 'boolean',
'virtual_balance' => 'string',
+ 'native_virtual_balance' => 'string',
];
protected $fillable = ['user_id', 'user_group_id', 'account_type_id', 'name', 'active', 'virtual_balance', 'iban', 'native_virtual_balance'];
diff --git a/app/Models/AutoBudget.php b/app/Models/AutoBudget.php
index 5adcd34e4d..a2d475c176 100644
--- a/app/Models/AutoBudget.php
+++ b/app/Models/AutoBudget.php
@@ -38,19 +38,20 @@ class AutoBudget extends Model
use ReturnsIntegerIdTrait;
use SoftDeletes;
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const int AUTO_BUDGET_ADJUSTED = 3;
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const int AUTO_BUDGET_RESET = 1;
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const int AUTO_BUDGET_ROLLOVER = 2;
protected $casts
= [
'amount' => 'string',
+ 'native_amount' => 'string',
];
- protected $fillable = ['budget_id', 'amount', 'period'];
+ protected $fillable = ['budget_id', 'amount', 'period','native_amount'];
public function budget(): BelongsTo
{
diff --git a/app/Models/AvailableBudget.php b/app/Models/AvailableBudget.php
index d2b8abc7a1..eef99656af 100644
--- a/app/Models/AvailableBudget.php
+++ b/app/Models/AvailableBudget.php
@@ -50,9 +50,10 @@ class AvailableBudget extends Model
'end_date' => 'date',
'transaction_currency_id' => 'int',
'amount' => 'string',
+ 'native_amount' => 'string',
];
- protected $fillable = ['user_id', 'user_group_id', 'transaction_currency_id', 'amount', 'start_date', 'end_date', 'start_date_tz', 'end_date_tz'];
+ protected $fillable = ['user_id', 'user_group_id', 'transaction_currency_id', 'amount', 'start_date', 'end_date', 'start_date_tz', 'end_date_tz','native_amount'];
/**
* Route binder. Converts the key in the URL to the specified object (or throw 404).
diff --git a/app/Models/BudgetLimit.php b/app/Models/BudgetLimit.php
index 8e69f95d15..b2a652db14 100644
--- a/app/Models/BudgetLimit.php
+++ b/app/Models/BudgetLimit.php
@@ -49,6 +49,7 @@ class BudgetLimit extends Model
'end_date' => SeparateTimezoneCaster::class,
'auto_budget' => 'boolean',
'amount' => 'string',
+ 'native_amount' => 'string',
];
protected $dispatchesEvents
= [
diff --git a/app/Models/PiggyBank.php b/app/Models/PiggyBank.php
index 7ffa94029d..58c9a25697 100644
--- a/app/Models/PiggyBank.php
+++ b/app/Models/PiggyBank.php
@@ -53,9 +53,10 @@ class PiggyBank extends Model
'active' => 'boolean',
'encrypted' => 'boolean',
'target_amount' => 'string',
+ 'native_target_amount' => 'string',
];
- protected $fillable = ['name', 'order', 'target_amount', 'start_date', 'start_date_tz', 'target_date', 'target_date_tz', 'active', 'transaction_currency_id'];
+ protected $fillable = ['name', 'order', 'target_amount', 'start_date', 'start_date_tz', 'target_date', 'target_date_tz', 'active', 'transaction_currency_id','native_target_amount'];
/**
* Route binder. Converts the key in the URL to the specified object (or throw 404).
diff --git a/app/Models/PiggyBankEvent.php b/app/Models/PiggyBankEvent.php
index 41df8cb704..059768e70b 100644
--- a/app/Models/PiggyBankEvent.php
+++ b/app/Models/PiggyBankEvent.php
@@ -42,9 +42,10 @@ class PiggyBankEvent extends Model
'updated_at' => 'datetime',
'date' => SeparateTimezoneCaster::class,
'amount' => 'string',
+ 'amount' => 'native_string',
];
- protected $fillable = ['piggy_bank_id', 'transaction_journal_id', 'date', 'date_tz', 'amount'];
+ protected $fillable = ['piggy_bank_id', 'transaction_journal_id', 'date', 'date_tz', 'amount','native_amount'];
protected $hidden = ['amount_encrypted'];
diff --git a/app/Repositories/Bill/BillRepository.php b/app/Repositories/Bill/BillRepository.php
index 5015776d3f..185fc700be 100644
--- a/app/Repositories/Bill/BillRepository.php
+++ b/app/Repositories/Bill/BillRepository.php
@@ -586,7 +586,7 @@ class BillRepository implements BillRepositoryInterface
$minField = $convertToNative && $bill->transactionCurrency->id !== $default->id ? 'native_amount_min' : 'amount_min';
$maxField = $convertToNative && $bill->transactionCurrency->id !== $default->id ? 'native_amount_max' : 'amount_max';
- // Log::debug(sprintf('min field is %s, max field is %s', $minField, $maxField));
+ Log::debug(sprintf('min field is %s, max field is %s', $minField, $maxField));
if ($total > 0) {
$currency = $convertToNative && $bill->transactionCurrency->id !== $default->id ? $default : $bill->transactionCurrency;
diff --git a/app/Support/Amount.php b/app/Support/Amount.php
index 06a7659929..9d21ef4e67 100644
--- a/app/Support/Amount.php
+++ b/app/Support/Amount.php
@@ -65,7 +65,7 @@ class Amount
// Log::debug(sprintf('Overruled, amount is now %s', $amount));
}
- return $amount;
+ return (string) $amount;
}
public function convertToNative(?User $user = null): bool
diff --git a/app/Support/Chart/Budget/FrontpageChartGenerator.php b/app/Support/Chart/Budget/FrontpageChartGenerator.php
index 0481718c47..5c96be4488 100644
--- a/app/Support/Chart/Budget/FrontpageChartGenerator.php
+++ b/app/Support/Chart/Budget/FrontpageChartGenerator.php
@@ -198,8 +198,10 @@ class FrontpageChartGenerator
}
$useNative = $this->convertToNative && $this->default->id !== $limit->transaction_currency_id;
$amount = $limit->amount;
- if ($useNative) {
+ Log::debug(sprintf('Amount is "%s".', $amount));
+ if ($useNative && $limit->transaction_currency_id !== $this->default->id) {
$amount = $limit->native_amount;
+ Log::debug(sprintf('Amount is now "%s".', $amount));
}
@@ -208,7 +210,6 @@ class FrontpageChartGenerator
$data[1]['entries'][$title] ??= '0';
$data[2]['entries'][$title] ??= '0';
-
$data[0]['entries'][$title] = bcadd($data[0]['entries'][$title], 1 === bccomp($sumSpent, $amount) ? $amount : $sumSpent); // spent
$data[1]['entries'][$title] = bcadd($data[1]['entries'][$title], 1 === bccomp($amount, $sumSpent) ? bcadd($entry['sum'], $amount) : '0'); // left to spent
$data[2]['entries'][$title] = bcadd($data[2]['entries'][$title], 1 === bccomp($amount, $sumSpent) ? '0' : bcmul(bcadd($entry['sum'], $amount), '-1')); // overspent
From 03e31ebb5ee0577e40b6d0fd5c74d541d6d2e3a1 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 06:36:49 +0100
Subject: [PATCH 156/167] Clean up endpoint.
---
.../V1/Controllers/Data/DestroyController.php | 22 +++++++++----------
1 file changed, 11 insertions(+), 11 deletions(-)
diff --git a/app/Api/V1/Controllers/Data/DestroyController.php b/app/Api/V1/Controllers/Data/DestroyController.php
index 8296d0ee68..3a73ec08d5 100644
--- a/app/Api/V1/Controllers/Data/DestroyController.php
+++ b/app/Api/V1/Controllers/Data/DestroyController.php
@@ -26,10 +26,10 @@ namespace FireflyIII\Api\V1\Controllers\Data;
use FireflyIII\Api\V1\Controllers\Controller;
use FireflyIII\Api\V1\Requests\Data\DestroyRequest;
+use FireflyIII\Enums\AccountTypeEnum;
use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Models\Account;
-use FireflyIII\Models\AccountType;
use FireflyIII\Models\TransactionJournal;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
use FireflyIII\Repositories\Bill\BillRepositoryInterface;
@@ -63,12 +63,12 @@ class DestroyController extends Controller
*/
public function destroy(DestroyRequest $request): JsonResponse
{
- $objects = $request->getObjects();
- $this->unused = $request->boolean('unused', false);
+ $objects = $request->getObjects();
+ $this->unused = $request->boolean('unused', false);
- $allExceptAssets = [AccountType::BENEFICIARY, AccountType::CASH, AccountType::CREDITCARD, AccountType::DEFAULT, AccountType::EXPENSE, AccountType::IMPORT, AccountType::INITIAL_BALANCE, AccountType::LIABILITY_CREDIT, AccountType::RECONCILIATION, AccountType::REVENUE];
- $all = [AccountType::ASSET, AccountType::BENEFICIARY, AccountType::CASH, AccountType::CREDITCARD, AccountType::DEBT, AccountType::DEFAULT, AccountType::EXPENSE, AccountType::IMPORT, AccountType::INITIAL_BALANCE, AccountType::LIABILITY_CREDIT, AccountType::LOAN, AccountType::MORTGAGE, AccountType::RECONCILIATION];
- $liabilities = [AccountType::DEBT, AccountType::LOAN, AccountType::MORTGAGE, AccountType::CREDITCARD];
+ $allExceptAssets = [AccountTypeEnum::BENEFICIARY->value, AccountTypeEnum::CASH->value, AccountTypeEnum::CREDITCARD->value, AccountTypeEnum::DEFAULT->value, AccountTypeEnum::EXPENSE->value, AccountTypeEnum::IMPORT->value, AccountTypeEnum::INITIAL_BALANCE->value, AccountTypeEnum::LIABILITY_CREDIT->value, AccountTypeEnum::RECONCILIATION->value, AccountTypeEnum::REVENUE->value];
+ $all = [AccountTypeEnum::ASSET->value, AccountTypeEnum::BENEFICIARY->value, AccountTypeEnum::CASH->value, AccountTypeEnum::CREDITCARD->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::DEFAULT->value, AccountTypeEnum::EXPENSE->value, AccountTypeEnum::IMPORT->value, AccountTypeEnum::INITIAL_BALANCE->value, AccountTypeEnum::LIABILITY_CREDIT->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::MORTGAGE->value, AccountTypeEnum::RECONCILIATION->value];
+ $liabilities = [AccountTypeEnum::DEBT->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::MORTGAGE->value, AccountTypeEnum::CREDITCARD->value];
$transactions = [TransactionTypeEnum::WITHDRAWAL->value, TransactionTypeEnum::DEPOSIT->value, TransactionTypeEnum::TRANSFER->value, TransactionTypeEnum::RECONCILIATION->value];
match ($objects) {
@@ -82,9 +82,9 @@ class DestroyController extends Controller
'object_groups' => $this->destroyObjectGroups(),
'not_assets_liabilities' => $this->destroyAccounts($allExceptAssets),
'accounts' => $this->destroyAccounts($all),
- 'asset_accounts' => $this->destroyAccounts([AccountType::ASSET, AccountType::DEFAULT]),
- 'expense_accounts' => $this->destroyAccounts([AccountType::BENEFICIARY, AccountType::EXPENSE]),
- 'revenue_accounts' => $this->destroyAccounts([AccountType::REVENUE]),
+ 'asset_accounts' => $this->destroyAccounts([AccountTypeEnum::ASSET->value, AccountTypeEnum::DEFAULT->value]),
+ 'expense_accounts' => $this->destroyAccounts([AccountTypeEnum::BENEFICIARY->value, AccountTypeEnum::EXPENSE->value]),
+ 'revenue_accounts' => $this->destroyAccounts([AccountTypeEnum::REVENUE->value]),
'liabilities' => $this->destroyAccounts($liabilities),
'transactions' => $this->destroyTransactions($transactions),
'withdrawals' => $this->destroyTransactions([TransactionTypeEnum::WITHDRAWAL->value]),
@@ -101,11 +101,11 @@ class DestroyController extends Controller
private function destroyBudgets(): void
{
/** @var AvailableBudgetRepositoryInterface $abRepository */
- $abRepository = app(AvailableBudgetRepositoryInterface::class);
+ $abRepository = app(AvailableBudgetRepositoryInterface::class);
$abRepository->destroyAll();
/** @var BudgetLimitRepositoryInterface $blRepository */
- $blRepository = app(BudgetLimitRepositoryInterface::class);
+ $blRepository = app(BudgetLimitRepositoryInterface::class);
$blRepository->destroyAll();
/** @var BudgetRepositoryInterface $budgetRepository */
From c21a79e0299585f4562f3b8568cfe922b40bef3a Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 08:16:27 +0100
Subject: [PATCH 157/167] Better, but not perfect, currency switch.
---
.../Events/PreferencesEventHandler.php | 26 +++++++++++--------
public/v1/js/ff/currencies/index.js | 9 +++++++
2 files changed, 24 insertions(+), 11 deletions(-)
diff --git a/app/Handlers/Events/PreferencesEventHandler.php b/app/Handlers/Events/PreferencesEventHandler.php
index e18fd2de3b..28d4e5c5e8 100644
--- a/app/Handlers/Events/PreferencesEventHandler.php
+++ b/app/Handlers/Events/PreferencesEventHandler.php
@@ -30,7 +30,9 @@ use FireflyIII\Models\PiggyBank;
use FireflyIII\Models\UserGroup;
use FireflyIII\Repositories\UserGroups\Budget\BudgetRepositoryInterface;
use FireflyIII\Repositories\UserGroups\PiggyBank\PiggyBankRepositoryInterface;
+use FireflyIII\Support\Facades\Amount;
use Illuminate\Database\Query\Builder;
+use Illuminate\Support\Facades\Artisan;
use Illuminate\Support\Facades\DB;
use Illuminate\Support\Facades\Log;
@@ -57,6 +59,10 @@ class PreferencesEventHandler
$this->resetPiggyBanks($event->userGroup);
$this->resetBudgets($event->userGroup);
$this->resetTransactions($event->userGroup);
+ // fire laravel command to recalculate them all.
+ if (Amount::convertToNative()) {
+ Artisan::call('correction:recalculate-native-amounts');
+ }
}
private function resetPiggyBanks(UserGroup $userGroup): void
@@ -93,7 +99,7 @@ class PreferencesEventHandler
{
$repository = app(BudgetRepositoryInterface::class);
$repository->setUserGroup($userGroup);
- $set = $repository->getBudgets();
+ $set = $repository->getBudgets();
/** @var Budget $budget */
foreach ($set as $budget) {
@@ -121,15 +127,13 @@ class PreferencesEventHandler
{
// custom query because of the potential size of this update.
$success = DB::table('transactions')
- ->join('transaction_journals', 'transaction_journals.id', '=', 'transactions.transaction_journal_id')
- ->where('transaction_journals.user_group_id', $userGroup->id)
- ->where(static function (Builder $q): void {
- $q->whereNotNull('native_amount')
- ->orWhereNotNull('native_foreign_amount')
- ;
- })
- ->update(['native_amount' => null, 'native_foreign_amount' => null])
- ;
- Log::debug(sprintf('Updated %d transactions.', $success));
+ ->join('transaction_journals', 'transaction_journals.id', '=', 'transactions.transaction_journal_id')
+ ->where('transaction_journals.user_group_id', $userGroup->id)
+ ->where(static function (Builder $q): void {
+ $q->whereNotNull('native_amount')
+ ->orWhereNotNull('native_foreign_amount');
+ })
+ ->update(['native_amount' => null, 'native_foreign_amount' => null]);
+ Log::debug(sprintf('Reset %d transactions.', $success));
}
}
diff --git a/public/v1/js/ff/currencies/index.js b/public/v1/js/ff/currencies/index.js
index 99ecaf7e24..d8b670c18b 100644
--- a/public/v1/js/ff/currencies/index.js
+++ b/public/v1/js/ff/currencies/index.js
@@ -26,10 +26,19 @@ $(function () {
$('.make_default').on('click', setDefaultCurrency);
$('.enable-currency').on('click', enableCurrency);
$('.disable-currency').on('click', disableCurrency);
+ console.log('Loaded3');
});
function setDefaultCurrency(e) {
+ console.log('Setting default currency');
var button = $(e.currentTarget);
+ // disable everything.
+ button.prop('disabled', true);
+ $('a').css('pointer-events', 'none');
+
+ // change cursor to hourglass
+ $('body').css('cursor', 'wait');
+
var currencyCode = button.data('code');
var params = {
From fa2149f957f5f35c761c4555a6df0e474b5db727 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 13:47:48 +0100
Subject: [PATCH 158/167] Update API to convert to native.
---
.../Insight/Expense/BillController.php | 100 ++++++-----
.../Observer/AvailableBudgetObserver.php | 2 +-
.../Account/OperationsRepository.php | 164 +++++++++++-------
composer.lock | 12 +-
public/v1/js/ff/currencies/index.js | 2 +-
5 files changed, 164 insertions(+), 116 deletions(-)
diff --git a/app/Api/V1/Controllers/Insight/Expense/BillController.php b/app/Api/V1/Controllers/Insight/Expense/BillController.php
index 6ff74baef4..bd6bff441e 100644
--- a/app/Api/V1/Controllers/Insight/Expense/BillController.php
+++ b/app/Api/V1/Controllers/Insight/Expense/BillController.php
@@ -29,7 +29,9 @@ use FireflyIII\Api\V1\Requests\Insight\GenericRequest;
use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Repositories\Bill\BillRepositoryInterface;
+use FireflyIII\Support\Facades\Amount;
use Illuminate\Http\JsonResponse;
+use Illuminate\Support\Facades\Log;
/**
* Class BillController
@@ -63,11 +65,13 @@ class BillController extends Controller
*/
public function bill(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $bills = $request->getBills();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $bills = $request->getBills();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $convertToNative = Amount::convertToNative();
+ $default = Amount::getDefaultCurrency();
+ $response = [];
// get all bills:
if (0 === $bills->count()) {
@@ -75,40 +79,43 @@ class BillController extends Controller
}
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::WITHDRAWAL->value])->setRange($start, $end)->setSourceAccounts($accounts);
$collector->setBills($bills);
$genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
- $billId = (int) $journal['bill_id'];
- $currencyId = (int) $journal['currency_id'];
- $foreignCurrencyId = (int) $journal['foreign_currency_id'];
- $key = sprintf('%d-%d', $billId, $currencyId);
- $foreignKey = sprintf('%d-%d', $billId, $foreignCurrencyId);
+ $billId = (int) $journal['bill_id'];
+ $currencyId = (int) $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ $field = 'amount';
+
+ // use the native amount if the user wants to convert to native currency
+ if ($convertToNative && $currencyId !== $default->id) {
+ $currencyId = $default->id;
+ $currencyCode = $default->code;
+ $field = 'native_amount';
+ }
+ // use foreign amount when the foreign currency IS the default currency.
+ if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
+ $field = 'foreign_amount';
+ }
+ Log::debug(sprintf('Journal #%d in bill #%d will use %s (%s %s)', $journal['transaction_group_id'], $billId, $field, $currencyCode, $journal[$field] ?? '0'));
+
+ $key = sprintf('%d-%d', $billId, $currencyId);
if (0 !== $currencyId) {
- $response[$key] ??= [
+ $response[$key] ??= [
'id' => (string) $billId,
'name' => $journal['bill_name'],
'difference' => '0',
'difference_float' => 0,
'currency_id' => (string) $currencyId,
- 'currency_code' => $journal['currency_code'],
+ 'currency_code' => $currencyCode,
];
- $response[$key]['difference'] = bcadd($response[$key]['difference'], $journal['amount']);
+ $response[$key]['difference'] = bcadd($response[$key]['difference'], (string) ($journal[$field] ?? '0'));
$response[$key]['difference_float'] = (float) $response[$key]['difference']; // intentional float
}
- if (0 !== $foreignCurrencyId) {
- $response[$foreignKey] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $foreignCurrencyId,
- 'currency_code' => $journal['foreign_currency_code'],
- ];
- $response[$foreignKey]['difference'] = bcadd($response[$foreignKey]['difference'], $journal['foreign_amount']);
- $response[$foreignKey]['difference_float'] = (float) $response[$foreignKey]['difference']; // intentional float
- }
}
return response()->json(array_values($response));
@@ -122,42 +129,47 @@ class BillController extends Controller
*/
public function noBill(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $convertToNative = Amount::convertToNative();
+ $default = Amount::getDefaultCurrency();
+ $response = [];
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::WITHDRAWAL->value])->setRange($start, $end)->setSourceAccounts($accounts);
$collector->withoutBill();
$genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $foreignCurrencyId = (int) $journal['foreign_currency_id'];
+ $currencyId = (int) $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ $field = 'amount';
+
+ // use the native amount if the user wants to convert to native currency
+ if ($convertToNative && $currencyId !== $default->id) {
+ $currencyId = $default->id;
+ $currencyCode = $default->code;
+ $field = 'native_amount';
+ }
+ // use foreign amount when the foreign currency IS the default currency.
+ if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
+ $field = 'foreign_amount';
+ }
+ Log::debug(sprintf('Journal #%d will use %s (%s %s)', $journal['transaction_group_id'], $field, $currencyCode, $journal[$field] ?? '0'));
if (0 !== $currencyId) {
- $response[$currencyId] ??= [
+ $response[$currencyId] ??= [
'difference' => '0',
'difference_float' => 0,
'currency_id' => (string) $currencyId,
- 'currency_code' => $journal['currency_code'],
+ 'currency_code' => $currencyCode,
];
- $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], $journal['amount']);
+ $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], (string) ($journal[$field] ?? '0'));
$response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference']; // intentional float
}
- if (0 !== $foreignCurrencyId) {
- $response[$foreignCurrencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $foreignCurrencyId,
- 'currency_code' => $journal['foreign_currency_code'],
- ];
- $response[$foreignCurrencyId]['difference'] = bcadd($response[$foreignCurrencyId]['difference'], $journal['foreign_amount']);
- $response[$foreignCurrencyId]['difference_float'] = (float) $response[$foreignCurrencyId]['difference']; // intentional float
- }
}
return response()->json(array_values($response));
diff --git a/app/Handlers/Observer/AvailableBudgetObserver.php b/app/Handlers/Observer/AvailableBudgetObserver.php
index 68de9677b4..6bf610c0a8 100644
--- a/app/Handlers/Observer/AvailableBudgetObserver.php
+++ b/app/Handlers/Observer/AvailableBudgetObserver.php
@@ -39,7 +39,7 @@ class AvailableBudgetObserver
public function updated(AvailableBudget $availableBudget): void
{
- Log::debug('Observe "updated" of an available budget.');
+ //Log::debug('Observe "updated" of an available budget.');
$this->updateNativeAmount($availableBudget);
}
diff --git a/app/Repositories/Account/OperationsRepository.php b/app/Repositories/Account/OperationsRepository.php
index 9902a5778a..3656222061 100644
--- a/app/Repositories/Account/OperationsRepository.php
+++ b/app/Repositories/Account/OperationsRepository.php
@@ -25,12 +25,14 @@ declare(strict_types=1);
namespace FireflyIII\Repositories\Account;
use Carbon\Carbon;
+use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Models\TransactionCurrency;
-use FireflyIII\Models\TransactionType;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Support\Collection;
+use Illuminate\Support\Facades\Log;
/**
* Class OperationsRepository
@@ -46,7 +48,7 @@ class OperationsRepository implements OperationsRepositoryInterface
*/
public function listExpenses(Carbon $start, Carbon $end, Collection $accounts): array
{
- $journals = $this->getTransactions($start, $end, $accounts, TransactionType::WITHDRAWAL);
+ $journals = $this->getTransactions($start, $end, $accounts, TransactionTypeEnum::WITHDRAWAL->value);
return $this->sortByCurrency($journals, 'negative');
}
@@ -65,7 +67,7 @@ class OperationsRepository implements OperationsRepositoryInterface
return $collector->getExtractedJournals();
}
- public function setUser(null|Authenticatable|User $user): void
+ public function setUser(null | Authenticatable | User $user): void
{
if ($user instanceof User) {
$this->user = $user;
@@ -76,8 +78,8 @@ class OperationsRepository implements OperationsRepositoryInterface
{
$array = [];
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $journalId = (int) $journal['transaction_journal_id'];
+ $currencyId = (int) $journal['currency_id'];
+ $journalId = (int) $journal['transaction_journal_id'];
$array[$currencyId] ??= [
'currency_id' => $journal['currency_id'],
'currency_name' => $journal['currency_name'],
@@ -115,7 +117,7 @@ class OperationsRepository implements OperationsRepositoryInterface
*/
public function listIncome(Carbon $start, Carbon $end, ?Collection $accounts = null): array
{
- $journals = $this->getTransactions($start, $end, $accounts, TransactionType::DEPOSIT);
+ $journals = $this->getTransactions($start, $end, $accounts, TransactionTypeEnum::DEPOSIT->value);
return $this->sortByCurrency($journals, 'positive');
}
@@ -129,8 +131,9 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $expense = null,
?TransactionCurrency $currency = null
- ): array {
- $journals = $this->getTransactionsForSum(TransactionType::WITHDRAWAL, $start, $end, $accounts, $expense, $currency);
+ ): array
+ {
+ $journals = $this->getTransactionsForSum(TransactionTypeEnum::WITHDRAWAL->value, $start, $end, $accounts, $expense, $currency);
return $this->groupByCurrency($journals, 'negative');
}
@@ -146,7 +149,8 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $opposing = null,
?TransactionCurrency $currency = null
- ): array {
+ ): array
+ {
$start->startOfDay();
$end->endOfDay();
@@ -155,7 +159,7 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setUser($this->user)->setRange($start, $end)->setTypes([$type])->withAccountInformation();
// depends on transaction type:
- if (TransactionType::WITHDRAWAL === $type) {
+ if (TransactionTypeEnum::WITHDRAWAL->value === $type) {
if (null !== $accounts) {
$collector->setSourceAccounts($accounts);
}
@@ -163,7 +167,7 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setDestinationAccounts($opposing);
}
}
- if (TransactionType::DEPOSIT === $type) {
+ if (TransactionTypeEnum::DEPOSIT->value === $type) {
if (null !== $accounts) {
$collector->setDestinationAccounts($accounts);
}
@@ -172,23 +176,22 @@ class OperationsRepository implements OperationsRepositoryInterface
}
}
// supports only accounts, not opposing.
- if (TransactionType::TRANSFER === $type && null !== $accounts) {
+ if (TransactionTypeEnum::TRANSFER->value === $type && null !== $accounts) {
$collector->setAccounts($accounts);
}
if (null !== $currency) {
$collector->setCurrency($currency);
}
- $journals = $collector->getExtractedJournals();
+ $journals = $collector->getExtractedJournals();
// same but for foreign currencies:
if (null !== $currency) {
/** @var GroupCollectorInterface $collector */
$collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([$type])->withAccountInformation()
- ->setForeignCurrency($currency)
- ;
- if (TransactionType::WITHDRAWAL === $type) {
+ ->setForeignCurrency($currency);
+ if (TransactionTypeEnum::WITHDRAWAL->value === $type) {
if (null !== $accounts) {
$collector->setSourceAccounts($accounts);
}
@@ -196,7 +199,7 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setDestinationAccounts($opposing);
}
}
- if (TransactionType::DEPOSIT === $type) {
+ if (TransactionTypeEnum::DEPOSIT->value === $type) {
if (null !== $accounts) {
$collector->setDestinationAccounts($accounts);
}
@@ -205,10 +208,10 @@ class OperationsRepository implements OperationsRepositoryInterface
}
}
- $result = $collector->getExtractedJournals();
+ $result = $collector->getExtractedJournals();
// do not use array_merge because you want keys to overwrite (otherwise you get double results):
- $journals = $result + $journals;
+ $journals = $result + $journals;
}
return $journals;
@@ -220,7 +223,7 @@ class OperationsRepository implements OperationsRepositoryInterface
foreach ($journals as $journal) {
$currencyId = (int) $journal['currency_id'];
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'sum' => '0',
'currency_id' => $currencyId,
'currency_name' => $journal['currency_name'],
@@ -231,9 +234,9 @@ class OperationsRepository implements OperationsRepositoryInterface
$array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->{$direction}($journal['amount'])); // @phpstan-ignore-line
// also do foreign amount:
- $foreignId = (int) $journal['foreign_currency_id'];
+ $foreignId = (int) $journal['foreign_currency_id'];
if (0 !== $foreignId) {
- $array[$foreignId] ??= [
+ $array[$foreignId] ??= [
'sum' => '0',
'currency_id' => $foreignId,
'currency_name' => $journal['foreign_currency_name'],
@@ -257,36 +260,65 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $expense = null,
?TransactionCurrency $currency = null
- ): array {
- $journals = $this->getTransactionsForSum(TransactionType::WITHDRAWAL, $start, $end, $accounts, $expense, $currency);
+ ): array
+ {
+ $journals = $this->getTransactionsForSum(TransactionTypeEnum::WITHDRAWAL->value, $start, $end, $accounts, $expense, $currency);
return $this->groupByDirection($journals, 'destination', 'negative');
}
private function groupByDirection(array $journals, string $direction, string $method): array
{
- $array = [];
- $idKey = sprintf('%s_account_id', $direction);
- $nameKey = sprintf('%s_account_name', $direction);
-
+ $array = [];
+ $idKey = sprintf('%s_account_id', $direction);
+ $nameKey = sprintf('%s_account_name', $direction);
+ $convertToNative = Amount::convertToNative($this->user);
+ $default = Amount::getDefaultCurrencyByUserGroup($this->user->userGroup);
+ Log::debug(sprintf('groupByDirection(array, %s, %s).', $direction, $method));
foreach ($journals as $journal) {
- $key = sprintf('%s-%s', $journal[$idKey], $journal['currency_id']);
+ // currency
+ $currencyId = $journal['currency_id'];
+ $currencyName = $journal['currency_name'];
+ $currencySymbol = $journal['currency_symbol'];
+ $currencyCode = $journal['currency_code'];
+ $currencyDecimalPlaces = $journal['currency_decimal_places'];
+ $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
+
+ // perhaps use default currency instead?
+ if ($convertToNative && $journal['currency_id'] !== $default->id) {
+ $currencyId = $default->id;
+ $currencyName = $default->name;
+ $currencySymbol = $default->symbol;
+ $currencyCode = $default->code;
+ $currencyDecimalPlaces = $default->decimal_places;
+ }
+ // use foreign amount when the foreign currency IS the default currency.
+ if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
+ $field = 'foreign_amount';
+ }
+ $key = sprintf('%s-%s', $journal[$idKey], $currencyId);
+ // sum it all up or create a new array.
$array[$key] ??= [
'id' => $journal[$idKey],
'name' => $journal[$nameKey],
'sum' => '0',
- 'currency_id' => $journal['currency_id'],
- 'currency_name' => $journal['currency_name'],
- 'currency_symbol' => $journal['currency_symbol'],
- 'currency_code' => $journal['currency_code'],
- 'currency_decimal_places' => $journal['currency_decimal_places'],
+ 'currency_id' => $currencyId,
+ 'currency_name' => $currencyName,
+ 'currency_symbol' => $currencySymbol,
+ 'currency_code' => $currencyCode,
+ 'currency_decimal_places' => $currencyDecimalPlaces,
];
- $array[$key]['sum'] = bcadd($array[$key]['sum'], app('steam')->{$method}((string) $journal['amount'])); // @phpstan-ignore-line
- // also do foreign amount:
- if (0 !== (int) $journal['foreign_currency_id']) {
+ // add the data from the $field to the array.
+ $array[$key]['sum'] = bcadd($array[$key]['sum'], app('steam')->{$method}((string) ($journal[$field] ?? '0'))); // @phpstan-ignore-line
+ Log::debug(sprintf('Field for transaction #%d is "%s" (%s). Sum: %s', $journal['transaction_group_id'], $currencyCode, $field, $array[$key]['sum']));
+
+ // also do foreign amount, but only when convertToNative is false (otherwise we have it already)
+ // or when convertToNative is true and the foreign currency is ALSO not the default currency.
+ if ((!$convertToNative || $journal['foreign_currency_id'] !== $default->id) && 0 !== (int) $journal['foreign_currency_id']) {
+ Log::debug(sprintf('Use foreign amount from transaction #%d: %s %s. Sum: %s', $journal['transaction_group_id'], $currencyCode, $journal['foreign_amount'], $array[$key]['sum']));
$key = sprintf('%s-%s', $journal[$idKey], $journal['foreign_currency_id']);
- $array[$key] ??= [
+ $array[$key] ??= [
'id' => $journal[$idKey],
'name' => $journal[$nameKey],
'sum' => '0',
@@ -312,8 +344,9 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $expense = null,
?TransactionCurrency $currency = null
- ): array {
- $journals = $this->getTransactionsForSum(TransactionType::WITHDRAWAL, $start, $end, $accounts, $expense, $currency);
+ ): array
+ {
+ $journals = $this->getTransactionsForSum(TransactionTypeEnum::WITHDRAWAL->value, $start, $end, $accounts, $expense, $currency);
return $this->groupByDirection($journals, 'source', 'negative');
}
@@ -327,8 +360,9 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $revenue = null,
?TransactionCurrency $currency = null
- ): array {
- $journals = $this->getTransactionsForSum(TransactionType::DEPOSIT, $start, $end, $accounts, $revenue, $currency);
+ ): array
+ {
+ $journals = $this->getTransactionsForSum(TransactionTypeEnum::DEPOSIT->value, $start, $end, $accounts, $revenue, $currency);
return $this->groupByCurrency($journals, 'positive');
}
@@ -342,8 +376,9 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $revenue = null,
?TransactionCurrency $currency = null
- ): array {
- $journals = $this->getTransactionsForSum(TransactionType::DEPOSIT, $start, $end, $accounts, $revenue, $currency);
+ ): array
+ {
+ $journals = $this->getTransactionsForSum(TransactionTypeEnum::DEPOSIT->value, $start, $end, $accounts, $revenue, $currency);
return $this->groupByDirection($journals, 'destination', 'positive');
}
@@ -357,15 +392,16 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $revenue = null,
?TransactionCurrency $currency = null
- ): array {
- $journals = $this->getTransactionsForSum(TransactionType::DEPOSIT, $start, $end, $accounts, $revenue, $currency);
+ ): array
+ {
+ $journals = $this->getTransactionsForSum(TransactionTypeEnum::DEPOSIT->value, $start, $end, $accounts, $revenue, $currency);
return $this->groupByDirection($journals, 'source', 'positive');
}
public function sumTransfers(Carbon $start, Carbon $end, ?Collection $accounts = null, ?TransactionCurrency $currency = null): array
{
- $journals = $this->getTransactionsForSum(TransactionType::TRANSFER, $start, $end, $accounts, null, $currency);
+ $journals = $this->getTransactionsForSum(TransactionTypeEnum::TRANSFER->value, $start, $end, $accounts, null, $currency);
return $this->groupByEither($journals);
}
@@ -378,7 +414,7 @@ class OperationsRepository implements OperationsRepositoryInterface
foreach ($journals as $journal) {
$return = $this->groupByEitherJournal($return, $journal);
}
- $final = [];
+ $final = [];
foreach ($return as $array) {
$array['difference_float'] = (float) $array['difference'];
$array['in_float'] = (float) $array['in'];
@@ -391,12 +427,12 @@ class OperationsRepository implements OperationsRepositoryInterface
private function groupByEitherJournal(array $return, array $journal): array
{
- $sourceId = $journal['source_account_id'];
- $destinationId = $journal['destination_account_id'];
- $currencyId = $journal['currency_id'];
- $sourceKey = sprintf('%d-%d', $currencyId, $sourceId);
- $destKey = sprintf('%d-%d', $currencyId, $destinationId);
- $amount = app('steam')->positive($journal['amount']);
+ $sourceId = $journal['source_account_id'];
+ $destinationId = $journal['destination_account_id'];
+ $currencyId = $journal['currency_id'];
+ $sourceKey = sprintf('%d-%d', $currencyId, $sourceId);
+ $destKey = sprintf('%d-%d', $currencyId, $destinationId);
+ $amount = app('steam')->positive($journal['amount']);
// source first
$return[$sourceKey] ??= [
@@ -413,7 +449,7 @@ class OperationsRepository implements OperationsRepositoryInterface
];
// dest next:
- $return[$destKey] ??= [
+ $return[$destKey] ??= [
'id' => (string) $destinationId,
'name' => $journal['destination_account_name'],
'difference' => '0',
@@ -431,15 +467,15 @@ class OperationsRepository implements OperationsRepositoryInterface
$return[$sourceKey]['difference'] = bcadd($return[$sourceKey]['out'], $return[$sourceKey]['in']);
// destination account? money comes in:
- $return[$destKey]['in'] = bcadd($return[$destKey]['in'], $amount);
- $return[$destKey]['difference'] = bcadd($return[$destKey]['out'], $return[$destKey]['in']);
+ $return[$destKey]['in'] = bcadd($return[$destKey]['in'], $amount);
+ $return[$destKey]['difference'] = bcadd($return[$destKey]['out'], $return[$destKey]['in']);
// foreign currency
if (null !== $journal['foreign_currency_id'] && null !== $journal['foreign_amount']) {
- $currencyId = $journal['foreign_currency_id'];
- $sourceKey = sprintf('%d-%d', $currencyId, $sourceId);
- $destKey = sprintf('%d-%d', $currencyId, $destinationId);
- $amount = app('steam')->positive($journal['foreign_amount']);
+ $currencyId = $journal['foreign_currency_id'];
+ $sourceKey = sprintf('%d-%d', $currencyId, $sourceId);
+ $destKey = sprintf('%d-%d', $currencyId, $destinationId);
+ $amount = app('steam')->positive($journal['foreign_amount']);
// same as above:
// source first
@@ -457,7 +493,7 @@ class OperationsRepository implements OperationsRepositoryInterface
];
// dest next:
- $return[$destKey] ??= [
+ $return[$destKey] ??= [
'id' => (string) $destinationId,
'name' => $journal['destination_account_name'],
'difference' => '0',
@@ -474,8 +510,8 @@ class OperationsRepository implements OperationsRepositoryInterface
$return[$sourceKey]['difference'] = bcadd($return[$sourceKey]['out'], $return[$sourceKey]['in']);
// destination account? money comes in:
- $return[$destKey]['in'] = bcadd($return[$destKey]['in'], $amount);
- $return[$destKey]['difference'] = bcadd($return[$destKey]['out'], $return[$destKey]['in']);
+ $return[$destKey]['in'] = bcadd($return[$destKey]['in'], $amount);
+ $return[$destKey]['difference'] = bcadd($return[$destKey]['out'], $return[$destKey]['in']);
}
return $return;
diff --git a/composer.lock b/composer.lock
index ae1a0ee832..87535dbbba 100644
--- a/composer.lock
+++ b/composer.lock
@@ -9682,16 +9682,16 @@
},
{
"name": "twig/twig",
- "version": "v3.17.1",
+ "version": "v3.18.0",
"source": {
"type": "git",
"url": "https://github.com/twigphp/Twig.git",
- "reference": "677ef8da6497a03048192aeeb5aa3018e379ac71"
+ "reference": "acffa88cc2b40dbe42eaf3a5025d6c0d4600cc50"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/twigphp/Twig/zipball/677ef8da6497a03048192aeeb5aa3018e379ac71",
- "reference": "677ef8da6497a03048192aeeb5aa3018e379ac71",
+ "url": "https://api.github.com/repos/twigphp/Twig/zipball/acffa88cc2b40dbe42eaf3a5025d6c0d4600cc50",
+ "reference": "acffa88cc2b40dbe42eaf3a5025d6c0d4600cc50",
"shasum": ""
},
"require": {
@@ -9746,7 +9746,7 @@
],
"support": {
"issues": "https://github.com/twigphp/Twig/issues",
- "source": "https://github.com/twigphp/Twig/tree/v3.17.1"
+ "source": "https://github.com/twigphp/Twig/tree/v3.18.0"
},
"funding": [
{
@@ -9758,7 +9758,7 @@
"type": "tidelift"
}
],
- "time": "2024-12-12T09:58:10+00:00"
+ "time": "2024-12-29T10:51:50+00:00"
},
{
"name": "verifiedjoseph/ntfy-php-library",
diff --git a/public/v1/js/ff/currencies/index.js b/public/v1/js/ff/currencies/index.js
index d8b670c18b..3a7acbe465 100644
--- a/public/v1/js/ff/currencies/index.js
+++ b/public/v1/js/ff/currencies/index.js
@@ -26,7 +26,6 @@ $(function () {
$('.make_default').on('click', setDefaultCurrency);
$('.enable-currency').on('click', enableCurrency);
$('.disable-currency').on('click', disableCurrency);
- console.log('Loaded3');
});
function setDefaultCurrency(e) {
@@ -47,6 +46,7 @@ function setDefaultCurrency(e) {
}
$.ajax({
+ timeout: 30000, // sets timeout to 30 seconds
url: updateCurrencyUrl + '/' + currencyCode,
data: JSON.stringify(params),
type: 'PUT',
From 05f1819f7dcde926daa62921a5d2bdc05b2b498b Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 14:24:20 +0100
Subject: [PATCH 159/167] Fix API convert to native. Still needs refactoring.
---
.../Insight/Expense/PeriodController.php | 66 +++++++-----
.../Insight/Expense/TagController.php | 79 ++++++++------
.../Insight/Income/AccountController.php | 1 +
.../Insight/Income/PeriodController.php | 56 +++++-----
.../Insight/Income/TagController.php | 41 +++----
.../Insight/Transfer/PeriodController.php | 39 +++----
.../Insight/Transfer/TagController.php | 72 +++++++------
.../Account/OperationsRepository.php | 48 +++++----
.../Budget/NoBudgetRepository.php | 100 ++++++++----------
.../Budget/NoBudgetRepositoryInterface.php | 5 -
10 files changed, 262 insertions(+), 245 deletions(-)
diff --git a/app/Api/V1/Controllers/Insight/Expense/PeriodController.php b/app/Api/V1/Controllers/Insight/Expense/PeriodController.php
index 9f091b8501..28a4fd25e7 100644
--- a/app/Api/V1/Controllers/Insight/Expense/PeriodController.php
+++ b/app/Api/V1/Controllers/Insight/Expense/PeriodController.php
@@ -28,7 +28,9 @@ use FireflyIII\Api\V1\Controllers\Controller;
use FireflyIII\Api\V1\Requests\Insight\GenericRequest;
use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
+use FireflyIII\Support\Facades\Amount;
use Illuminate\Http\JsonResponse;
+use Illuminate\Support\Facades\Log;
/**
* Class PeriodController
@@ -41,39 +43,49 @@ class PeriodController extends Controller
*/
public function total(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $response = [];
+ $convertToNative = Amount::convertToNative();
+ $default = Amount::getDefaultCurrency();
// collect all expenses in this period (regardless of type)
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::WITHDRAWAL->value])->setRange($start, $end)->setSourceAccounts($accounts);
$genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $foreignCurrencyId = (int) $journal['foreign_currency_id'];
+ // same code as many other sumExpense methods. I think this needs some kind of generic method.
+ $amount = '0';
+ $currencyId = (int) $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ if ($convertToNative) {
+ $amount = Amount::getAmountFromJournal($journal);
+ if ($default->id !== (int) $journal['currency_id'] && $default->id !== (int) $journal['foreign_currency_id']) {
+ $currencyId = $default->id;
+ $currencyCode = $default->code;
+ }
+ if ($default->id !== (int) $journal['currency_id'] && $default->id === (int) $journal['foreign_currency_id']) {
+ $currencyId = $journal['foreign_currency_id'];
+ $currencyCode = $journal['foreign_currency_code'];
+ }
+ Log::debug(sprintf('[a] Add amount %s %s', $currencyCode, $amount));
+ }
+ if (!$convertToNative) {
+ // ignore the amount in foreign currency.
+ Log::debug(sprintf('[b] Add amount %s %s', $currencyCode, $journal['amount']));
+ $amount = $journal['amount'];
+ }
- if (0 !== $currencyId) {
- $response[$currencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $currencyId,
- 'currency_code' => $journal['currency_code'],
- ];
- $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], $journal['amount']);
- $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference']; // intentional float
- }
- if (0 !== $foreignCurrencyId) {
- $response[$foreignCurrencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $foreignCurrencyId,
- 'currency_code' => $journal['foreign_currency_code'],
- ];
- $response[$foreignCurrencyId]['difference'] = bcadd($response[$foreignCurrencyId]['difference'], $journal['foreign_amount']);
- $response[$foreignCurrencyId]['difference_float'] = (float) $response[$foreignCurrencyId]['difference']; // intentional float
- }
+
+ $response[$currencyId] ??= [
+ 'difference' => '0',
+ 'difference_float' => 0,
+ 'currency_id' => (string) $currencyId,
+ 'currency_code' => $currencyCode,
+ ];
+ $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], $amount);
+ $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference']; // intentional float
}
return response()->json(array_values($response));
diff --git a/app/Api/V1/Controllers/Insight/Expense/TagController.php b/app/Api/V1/Controllers/Insight/Expense/TagController.php
index b76dcc776a..b39105ada0 100644
--- a/app/Api/V1/Controllers/Insight/Expense/TagController.php
+++ b/app/Api/V1/Controllers/Insight/Expense/TagController.php
@@ -29,7 +29,9 @@ use FireflyIII\Api\V1\Requests\Insight\GenericRequest;
use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Repositories\Tag\TagRepositoryInterface;
+use FireflyIII\Support\Facades\Amount;
use Illuminate\Http\JsonResponse;
+use Illuminate\Support\Facades\Log;
/**
* Class TagController
@@ -62,42 +64,51 @@ class TagController extends Controller
*/
public function noTag(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $response = [];
+ $convertToNative = Amount::convertToNative();
+ $default = Amount::getDefaultCurrency();
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::WITHDRAWAL->value])->setRange($start, $end)->setSourceAccounts($accounts);
$collector->withoutTags();
$genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $foreignCurrencyId = (int) $journal['foreign_currency_id'];
+ // same code as many other sumExpense methods. I think this needs some kind of generic method.
+ $amount = '0';
+ $currencyId = (int) $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ if ($convertToNative) {
+ $amount = Amount::getAmountFromJournal($journal);
+ if ($default->id !== (int) $journal['currency_id'] && $default->id !== (int) $journal['foreign_currency_id']) {
+ $currencyId = $default->id;
+ $currencyCode = $default->code;
+ }
+ if ($default->id !== (int) $journal['currency_id'] && $default->id === (int) $journal['foreign_currency_id']) {
+ $currencyId = $journal['foreign_currency_id'];
+ $currencyCode = $journal['foreign_currency_code'];
+ }
+ Log::debug(sprintf('[a] Add amount %s %s', $currencyCode, $amount));
+ }
+ if (!$convertToNative) {
+ // ignore the amount in foreign currency.
+ Log::debug(sprintf('[b] Add amount %s %s', $currencyCode, $journal['amount']));
+ $amount = $journal['amount'];
+ }
- if (0 !== $currencyId) {
- $response[$currencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $currencyId,
- 'currency_code' => $journal['currency_code'],
- ];
- $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], $journal['amount']);
- $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference']; // float but on purpose.
- }
- if (0 !== $foreignCurrencyId) {
- $response[$foreignCurrencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $foreignCurrencyId,
- 'currency_code' => $journal['foreign_currency_code'],
- ];
- $response[$foreignCurrencyId]['difference'] = bcadd($response[$foreignCurrencyId]['difference'], $journal['foreign_amount']);
- $response[$foreignCurrencyId]['difference_float'] = (float) $response[$foreignCurrencyId]['difference']; // float but on purpose.
- }
+ $response[$currencyId] ??= [
+ 'difference' => '0',
+ 'difference_float' => 0,
+ 'currency_id' => (string) $currencyId,
+ 'currency_code' => $currencyCode,
+ ];
+ $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], $amount);
+ $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference']; // float but on purpose.
}
return response()->json(array_values($response));
@@ -111,11 +122,11 @@ class TagController extends Controller
*/
public function tag(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $tags = $request->getTags();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $tags = $request->getTags();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $response = [];
// get all tags:
if (0 === $tags->count()) {
@@ -123,7 +134,7 @@ class TagController extends Controller
}
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::WITHDRAWAL->value])->setRange($start, $end)->setSourceAccounts($accounts);
$collector->setTags($tags);
$genericSet = $collector->getExtractedJournals();
@@ -141,7 +152,7 @@ class TagController extends Controller
// on currency ID
if (0 !== $currencyId) {
- $response[$key] ??= [
+ $response[$key] ??= [
'id' => (string) $tagId,
'name' => $tag['name'],
'difference' => '0',
diff --git a/app/Api/V1/Controllers/Insight/Income/AccountController.php b/app/Api/V1/Controllers/Insight/Income/AccountController.php
index 5c7b28231e..87cff7be5c 100644
--- a/app/Api/V1/Controllers/Insight/Income/AccountController.php
+++ b/app/Api/V1/Controllers/Insight/Income/AccountController.php
@@ -73,6 +73,7 @@ class AccountController extends Controller
$start = $request->getStart();
$end = $request->getEnd();
$assetAccounts = $request->getAssetAccounts();
+
$income = $this->opsRepository->sumIncomeByDestination($start, $end, $assetAccounts);
$result = [];
diff --git a/app/Api/V1/Controllers/Insight/Income/PeriodController.php b/app/Api/V1/Controllers/Insight/Income/PeriodController.php
index 970ffa2e52..360abf4664 100644
--- a/app/Api/V1/Controllers/Insight/Income/PeriodController.php
+++ b/app/Api/V1/Controllers/Insight/Income/PeriodController.php
@@ -28,6 +28,7 @@ use FireflyIII\Api\V1\Controllers\Controller;
use FireflyIII\Api\V1\Requests\Insight\GenericRequest;
use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
+use FireflyIII\Support\Facades\Amount;
use Illuminate\Http\JsonResponse;
/**
@@ -41,42 +42,41 @@ class PeriodController extends Controller
*/
public function total(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $response = [];
+ $convertToNative = Amount::convertToNative();
+ $default = Amount::getDefaultCurrency();
// collect all expenses in this period (regardless of type)
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::DEPOSIT->value])->setRange($start, $end)->setDestinationAccounts($accounts);
$genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $foreignCurrencyId = (int) $journal['foreign_currency_id'];
+ // currency
+ $currencyId = $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
- if (0 !== $currencyId) {
- $response[$currencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $currencyId,
- 'currency_code' => $journal['currency_code'],
- ];
- $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal['amount']));
- $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference']; // float but on purpose.
+ // perhaps use default currency instead?
+ if ($convertToNative && $journal['currency_id'] !== $default->id) {
+ $currencyId = $default->id;
+ $currencyCode = $default->code;
}
- if (0 !== $foreignCurrencyId) {
- $response[$foreignCurrencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $foreignCurrencyId,
- 'currency_code' => $journal['foreign_currency_code'],
- ];
- $response[$foreignCurrencyId]['difference'] = bcadd(
- $response[$foreignCurrencyId]['difference'],
- app('steam')->positive($journal['foreign_amount'])
- );
- $response[$foreignCurrencyId]['difference_float'] = (float) $response[$foreignCurrencyId]['difference']; // float but on purpose.
+ // use foreign amount when the foreign currency IS the default currency.
+ if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
+ $field = 'foreign_amount';
}
+
+ $response[$currencyId] ??= [
+ 'difference' => '0',
+ 'difference_float' => 0,
+ 'currency_id' => (string) $currencyId,
+ 'currency_code' => $currencyCode,
+ ];
+ $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal[$field]));
+ $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference']; // float but on purpose.
}
return response()->json(array_values($response));
diff --git a/app/Api/V1/Controllers/Insight/Income/TagController.php b/app/Api/V1/Controllers/Insight/Income/TagController.php
index e0eece3e90..3a3a5f67b6 100644
--- a/app/Api/V1/Controllers/Insight/Income/TagController.php
+++ b/app/Api/V1/Controllers/Insight/Income/TagController.php
@@ -29,6 +29,7 @@ use FireflyIII\Api\V1\Requests\Insight\GenericRequest;
use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Repositories\Tag\TagRepositoryInterface;
+use FireflyIII\Support\Facades\Amount;
use Illuminate\Http\JsonResponse;
/**
@@ -67,6 +68,8 @@ class TagController extends Controller
$start = $request->getStart();
$end = $request->getEnd();
$response = [];
+ $convertToNative = Amount::convertToNative();
+ $default = Amount::getDefaultCurrency();
// collect all expenses in this period (regardless of type) by the given bills and accounts.
$collector = app(GroupCollectorInterface::class);
@@ -76,32 +79,30 @@ class TagController extends Controller
$genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $foreignCurrencyId = (int) $journal['foreign_currency_id'];
+ // currency
+ $currencyId = $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
- if (0 !== $currencyId) {
- $response[$currencyId] ??= [
+ // perhaps use default currency instead?
+ if ($convertToNative && $journal['currency_id'] !== $default->id) {
+ $currencyId = $default->id;
+ $currencyCode = $default->code;
+ }
+ // use foreign amount when the foreign currency IS the default currency.
+ if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
+ $field = 'foreign_amount';
+ }
+
+ $response[$currencyId] ??= [
'difference' => '0',
'difference_float' => 0,
'currency_id' => (string) $currencyId,
- 'currency_code' => $journal['currency_code'],
+ 'currency_code' => $currencyCode,
];
- $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal['amount']));
+ $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal[$field]));
$response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference'];
- }
- if (0 !== $foreignCurrencyId) {
- $response[$foreignCurrencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $foreignCurrencyId,
- 'currency_code' => $journal['foreign_currency_code'],
- ];
- $response[$foreignCurrencyId]['difference'] = bcadd(
- $response[$foreignCurrencyId]['difference'],
- app('steam')->positive($journal['foreign_amount'])
- );
- $response[$foreignCurrencyId]['difference_float'] = (float) $response[$foreignCurrencyId]['difference'];
- }
+
}
return response()->json(array_values($response));
diff --git a/app/Api/V1/Controllers/Insight/Transfer/PeriodController.php b/app/Api/V1/Controllers/Insight/Transfer/PeriodController.php
index f66f9776ee..5d0b5a22d5 100644
--- a/app/Api/V1/Controllers/Insight/Transfer/PeriodController.php
+++ b/app/Api/V1/Controllers/Insight/Transfer/PeriodController.php
@@ -28,6 +28,7 @@ use FireflyIII\Api\V1\Controllers\Controller;
use FireflyIII\Api\V1\Requests\Insight\GenericRequest;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Models\TransactionType;
+use FireflyIII\Support\Facades\Amount;
use Illuminate\Http\JsonResponse;
/**
@@ -45,38 +46,38 @@ class PeriodController extends Controller
$start = $request->getStart();
$end = $request->getEnd();
$response = [];
+ $convertToNative = Amount::convertToNative();
+ $default = Amount::getDefaultCurrency();
// collect all expenses in this period (regardless of type)
$collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionType::TRANSFER])->setRange($start, $end)->setDestinationAccounts($accounts);
$genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $foreignCurrencyId = (int) $journal['foreign_currency_id'];
+ // currency
+ $currencyId = $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
+
+ // perhaps use default currency instead?
+ if ($convertToNative && $journal['currency_id'] !== $default->id) {
+ $currencyId = $default->id;
+ $currencyCode = $default->code;
+ }
+ // use foreign amount when the foreign currency IS the default currency.
+ if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
+ $field = 'foreign_amount';
+ }
- if (0 !== $currencyId) {
$response[$currencyId] ??= [
'difference' => '0',
'difference_float' => 0,
'currency_id' => (string) $currencyId,
- 'currency_code' => $journal['currency_code'],
+ 'currency_code' => $currencyCode,
];
- $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal['amount']));
+ $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal[$field]));
$response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference'];
- }
- if (0 !== $foreignCurrencyId) {
- $response[$foreignCurrencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $foreignCurrencyId,
- 'currency_code' => $journal['foreign_currency_code'],
- ];
- $response[$foreignCurrencyId]['difference'] = bcadd(
- $response[$foreignCurrencyId]['difference'],
- app('steam')->positive($journal['foreign_amount'])
- );
- $response[$foreignCurrencyId]['difference_float'] = (float) $response[$foreignCurrencyId]['difference'];
- }
+
}
return response()->json(array_values($response));
diff --git a/app/Api/V1/Controllers/Insight/Transfer/TagController.php b/app/Api/V1/Controllers/Insight/Transfer/TagController.php
index 6fa1fbdedd..001a4ca5f1 100644
--- a/app/Api/V1/Controllers/Insight/Transfer/TagController.php
+++ b/app/Api/V1/Controllers/Insight/Transfer/TagController.php
@@ -29,6 +29,7 @@ use FireflyIII\Api\V1\Requests\Insight\GenericRequest;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Models\TransactionType;
use FireflyIII\Repositories\Tag\TagRepositoryInterface;
+use FireflyIII\Support\Facades\Amount;
use Illuminate\Http\JsonResponse;
/**
@@ -61,45 +62,46 @@ class TagController extends Controller
*/
public function noTag(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $response = [];
+ $convertToNative = Amount::convertToNative();
+ $default = Amount::getDefaultCurrency();
+
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionType::TRANSFER])->setRange($start, $end)->setDestinationAccounts($accounts);
$collector->withoutTags();
$genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $foreignCurrencyId = (int) $journal['foreign_currency_id'];
+ // currency
+ $currencyId = $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
- if (0 !== $currencyId) {
- $response[$currencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $currencyId,
- 'currency_code' => $journal['currency_code'],
- ];
- $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal['amount']));
- $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference'];
+ // perhaps use default currency instead?
+ if ($convertToNative && $journal['currency_id'] !== $default->id) {
+ $currencyId = $default->id;
+ $currencyCode = $default->code;
}
- if (0 !== $foreignCurrencyId) {
- $response[$foreignCurrencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $foreignCurrencyId,
- 'currency_code' => $journal['foreign_currency_code'],
- ];
- $response[$foreignCurrencyId]['difference'] = bcadd(
- $response[$foreignCurrencyId]['difference'],
- app('steam')->positive($journal['foreign_amount'])
- );
- $response[$foreignCurrencyId]['difference_float'] = (float) $response[$foreignCurrencyId]['difference'];
+ // use foreign amount when the foreign currency IS the default currency.
+ if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
+ $field = 'foreign_amount';
}
+
+ $response[$currencyId] ??= [
+ 'difference' => '0',
+ 'difference_float' => 0,
+ 'currency_id' => (string) $currencyId,
+ 'currency_code' => $currencyCode,
+ ];
+ $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal[$field]));
+ $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference'];
+
}
return response()->json(array_values($response));
@@ -113,11 +115,11 @@ class TagController extends Controller
*/
public function tag(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $tags = $request->getTags();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $tags = $request->getTags();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $response = [];
// get all tags:
if (0 === $tags->count()) {
@@ -125,7 +127,7 @@ class TagController extends Controller
}
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionType::TRANSFER])->setRange($start, $end)->setDestinationAccounts($accounts);
$collector->setTags($tags);
$genericSet = $collector->getExtractedJournals();
@@ -143,7 +145,7 @@ class TagController extends Controller
// on currency ID
if (0 !== $currencyId) {
- $response[$key] ??= [
+ $response[$key] ??= [
'id' => (string) $tagId,
'name' => $tag['name'],
'difference' => '0',
diff --git a/app/Repositories/Account/OperationsRepository.php b/app/Repositories/Account/OperationsRepository.php
index 3656222061..b214e45d76 100644
--- a/app/Repositories/Account/OperationsRepository.php
+++ b/app/Repositories/Account/OperationsRepository.php
@@ -220,32 +220,40 @@ class OperationsRepository implements OperationsRepositoryInterface
private function groupByCurrency(array $journals, string $direction): array
{
$array = [];
+ $convertToNative = Amount::convertToNative($this->user);
+ $default = Amount::getDefaultCurrencyByUserGroup($this->user->userGroup);
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
+ // currency
+ $currencyId = $journal['currency_id'];
+ $currencyName = $journal['currency_name'];
+ $currencySymbol = $journal['currency_symbol'];
+ $currencyCode = $journal['currency_code'];
+ $currencyDecimalPlaces = $journal['currency_decimal_places'];
+ $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
+
+ // perhaps use default currency instead?
+ if ($convertToNative && $journal['currency_id'] !== $default->id) {
+ $currencyId = $default->id;
+ $currencyName = $default->name;
+ $currencySymbol = $default->symbol;
+ $currencyCode = $default->code;
+ $currencyDecimalPlaces = $default->decimal_places;
+ }
+ // use foreign amount when the foreign currency IS the default currency.
+ if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
+ $field = 'foreign_amount';
+ }
+
$array[$currencyId] ??= [
'sum' => '0',
'currency_id' => $currencyId,
- 'currency_name' => $journal['currency_name'],
- 'currency_symbol' => $journal['currency_symbol'],
- 'currency_code' => $journal['currency_code'],
- 'currency_decimal_places' => $journal['currency_decimal_places'],
+ 'currency_name' => $currencyName,
+ 'currency_symbol' => $currencySymbol,
+ 'currency_code' => $currencyCode,
+ 'currency_decimal_places' => $currencyDecimalPlaces,
];
- $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->{$direction}($journal['amount'])); // @phpstan-ignore-line
-
- // also do foreign amount:
- $foreignId = (int) $journal['foreign_currency_id'];
- if (0 !== $foreignId) {
- $array[$foreignId] ??= [
- 'sum' => '0',
- 'currency_id' => $foreignId,
- 'currency_name' => $journal['foreign_currency_name'],
- 'currency_symbol' => $journal['foreign_currency_symbol'],
- 'currency_code' => $journal['foreign_currency_code'],
- 'currency_decimal_places' => $journal['foreign_currency_decimal_places'],
- ];
- $array[$foreignId]['sum'] = bcadd($array[$foreignId]['sum'], app('steam')->{$direction}($journal['foreign_amount'])); // @phpstan-ignore-line
- }
+ $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->{$direction}($journal[$field])); // @phpstan-ignore-line
}
return $array;
diff --git a/app/Repositories/Budget/NoBudgetRepository.php b/app/Repositories/Budget/NoBudgetRepository.php
index ebe62ac894..7630d50881 100644
--- a/app/Repositories/Budget/NoBudgetRepository.php
+++ b/app/Repositories/Budget/NoBudgetRepository.php
@@ -28,9 +28,11 @@ use Carbon\Carbon;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Models\TransactionType;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Support\Collection;
+use Illuminate\Support\Facades\Log;
/**
* Class NoBudgetRepository
@@ -79,54 +81,6 @@ class NoBudgetRepository implements NoBudgetRepositoryInterface
return $data;
}
- /**
- * @deprecated
- */
- public function spentInPeriodWoBudgetMc(Collection $accounts, Carbon $start, Carbon $end): array
- {
- /** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
-
- $collector->setUser($this->user);
- $collector->setRange($start, $end)->setTypes([TransactionType::WITHDRAWAL])->withoutBudget();
-
- if ($accounts->count() > 0) {
- $collector->setAccounts($accounts);
- }
- $journals = $collector->getExtractedJournals();
- $return = [];
- $total = [];
- $currencies = [];
-
- /** @var array $journal */
- foreach ($journals as $journal) {
- $code = $journal['currency_code'];
- if (!array_key_exists($code, $currencies)) {
- $currencies[$code] = [
- 'id' => $journal['currency_id'],
- 'name' => $journal['currency_name'],
- 'symbol' => $journal['currency_symbol'],
- 'decimal_places' => $journal['currency_decimal_places'],
- ];
- }
- $total[$code] = array_key_exists($code, $total) ? bcadd($total[$code], $journal['amount']) : $journal['amount'];
- }
- foreach ($total as $code => $spent) {
- /** @var TransactionCurrency $currency */
- $currency = $currencies[$code];
- $return[] = [
- 'currency_id' => (string) $currency['id'],
- 'currency_code' => $code,
- 'currency_name' => $currency['name'],
- 'currency_symbol' => $currency['symbol'],
- 'currency_decimal_places' => $currency['decimal_places'],
- 'amount' => app('steam')->bcround($spent, $currency['decimal_places']),
- ];
- }
-
- return $return;
- }
-
public function setUser(null|Authenticatable|User $user): void
{
if ($user instanceof User) {
@@ -134,10 +88,6 @@ class NoBudgetRepository implements NoBudgetRepositoryInterface
}
}
- /**
- * TODO this method does not include multi currency. It just counts.
- * TODO this probably also applies to the other "sumExpenses" methods.
- */
public function sumExpenses(Carbon $start, Carbon $end, ?Collection $accounts = null, ?TransactionCurrency $currency = null): array
{
/** @var GroupCollectorInterface $collector */
@@ -154,18 +104,54 @@ class NoBudgetRepository implements NoBudgetRepositoryInterface
$collector->withBudgetInformation();
$journals = $collector->getExtractedJournals();
$array = [];
+ $convertToNative = Amount::convertToNative($this->user);
+ $default = Amount::getDefaultCurrency();
foreach ($journals as $journal) {
+ // same as in the other methods.
+ $amount = '0';
$currencyId = (int) $journal['currency_id'];
+ $currencyName = $journal['currency_name'];
+ $currencySymbol = $journal['currency_symbol'];
+ $currencyCode = $journal['currency_code'];
+ $currencyDecimalPlaces = $journal['currency_decimal_places'];
+
+ if ($convertToNative) {
+ $useNative = $default->id !== (int) $journal['currency_id'];
+ $amount = Amount::getAmountFromJournal($journal);
+ if ($useNative) {
+ Log::debug(sprintf('Journal #%d switches to native amount (original is %s)', $journal['transaction_journal_id'], $journal['currency_code']));
+ $currencyId = $default->id;
+ $currencyName = $default->name;
+ $currencySymbol = $default->symbol;
+ $currencyCode = $default->code;
+ $currencyDecimalPlaces = $default->decimal_places;
+ }
+ }
+ if (!$convertToNative) {
+ $amount = $journal['amount'];
+ // if the amount is not in $currency (but should be), use the foreign_amount if that one is correct.
+ // otherwise, ignore the transaction all together.
+ if (null !== $currency && $currencyId !== $currency->id && $currency->id === (int) $journal['foreign_currency_id']) {
+ Log::debug(sprintf('Journal #%d switches to foreign amount because it matches native.', $journal['transaction_journal_id']));
+ $amount = $journal['foreign_amount'];
+ $currencyId = (int) $journal['foreign_currency_id'];
+ $currencyName = $journal['foreign_currency_name'];
+ $currencySymbol = $journal['foreign_currency_symbol'];
+ $currencyCode = $journal['foreign_currency_code'];
+ $currencyDecimalPlaces = $journal['foreign_currency_decimal_places'];
+ }
+ }
+
$array[$currencyId] ??= [
'sum' => '0',
'currency_id' => $currencyId,
- 'currency_name' => $journal['currency_name'],
- 'currency_symbol' => $journal['currency_symbol'],
- 'currency_code' => $journal['currency_code'],
- 'currency_decimal_places' => $journal['currency_decimal_places'],
+ 'currency_name' => $currencyName,
+ 'currency_symbol' => $currencySymbol,
+ 'currency_code' => $currencyCode,
+ 'currency_decimal_places' => $currencyDecimalPlaces,
];
- $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->negative($journal['amount']));
+ $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->negative($amount));
}
return $array;
diff --git a/app/Repositories/Budget/NoBudgetRepositoryInterface.php b/app/Repositories/Budget/NoBudgetRepositoryInterface.php
index e430d6e8cd..01b4d6d1f1 100644
--- a/app/Repositories/Budget/NoBudgetRepositoryInterface.php
+++ b/app/Repositories/Budget/NoBudgetRepositoryInterface.php
@@ -42,10 +42,5 @@ interface NoBudgetRepositoryInterface
public function setUser(null|Authenticatable|User $user): void;
- /**
- * @deprecated
- */
- public function spentInPeriodWoBudgetMc(Collection $accounts, Carbon $start, Carbon $end): array;
-
public function sumExpenses(Carbon $start, Carbon $end, ?Collection $accounts = null, ?TransactionCurrency $currency = null): array;
}
From 9f25880a59744c3211e623018c5bd9898ad3aaf1 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Sun, 29 Dec 2024 18:32:02 +0100
Subject: [PATCH 160/167] Clean up several endpoints with complex code.
---
.../Account/OperationsRepository.php | 107 +----------
.../Budget/NoBudgetRepository.php | 58 +-----
.../Budget/OperationsRepository.php | 57 +-----
.../Category/NoCategoryRepository.php | 47 +----
.../Category/OperationsRepository.php | 54 +-----
.../Summarizer/TransactionSummarizer.php | 178 ++++++++++++++++++
app/Transformers/AccountTransformer.php | 2 +-
7 files changed, 198 insertions(+), 305 deletions(-)
create mode 100644 app/Support/Report/Summarizer/TransactionSummarizer.php
diff --git a/app/Repositories/Account/OperationsRepository.php b/app/Repositories/Account/OperationsRepository.php
index b214e45d76..5f0bdca8bf 100644
--- a/app/Repositories/Account/OperationsRepository.php
+++ b/app/Repositories/Account/OperationsRepository.php
@@ -29,6 +29,7 @@ use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Support\Facades\Amount;
+use FireflyIII\Support\Report\Summarizer\TransactionSummarizer;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Support\Collection;
@@ -219,44 +220,8 @@ class OperationsRepository implements OperationsRepositoryInterface
private function groupByCurrency(array $journals, string $direction): array
{
- $array = [];
- $convertToNative = Amount::convertToNative($this->user);
- $default = Amount::getDefaultCurrencyByUserGroup($this->user->userGroup);
-
- foreach ($journals as $journal) {
- // currency
- $currencyId = $journal['currency_id'];
- $currencyName = $journal['currency_name'];
- $currencySymbol = $journal['currency_symbol'];
- $currencyCode = $journal['currency_code'];
- $currencyDecimalPlaces = $journal['currency_decimal_places'];
- $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
-
- // perhaps use default currency instead?
- if ($convertToNative && $journal['currency_id'] !== $default->id) {
- $currencyId = $default->id;
- $currencyName = $default->name;
- $currencySymbol = $default->symbol;
- $currencyCode = $default->code;
- $currencyDecimalPlaces = $default->decimal_places;
- }
- // use foreign amount when the foreign currency IS the default currency.
- if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
- $field = 'foreign_amount';
- }
-
- $array[$currencyId] ??= [
- 'sum' => '0',
- 'currency_id' => $currencyId,
- 'currency_name' => $currencyName,
- 'currency_symbol' => $currencySymbol,
- 'currency_code' => $currencyCode,
- 'currency_decimal_places' => $currencyDecimalPlaces,
- ];
- $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->{$direction}($journal[$field])); // @phpstan-ignore-line
- }
-
- return $array;
+ $summarizer = new TransactionSummarizer($this->user);
+ return $summarizer->groupByCurrencyId($journals, $direction);
}
/**
@@ -277,70 +242,8 @@ class OperationsRepository implements OperationsRepositoryInterface
private function groupByDirection(array $journals, string $direction, string $method): array
{
- $array = [];
- $idKey = sprintf('%s_account_id', $direction);
- $nameKey = sprintf('%s_account_name', $direction);
- $convertToNative = Amount::convertToNative($this->user);
- $default = Amount::getDefaultCurrencyByUserGroup($this->user->userGroup);
- Log::debug(sprintf('groupByDirection(array, %s, %s).', $direction, $method));
- foreach ($journals as $journal) {
- // currency
- $currencyId = $journal['currency_id'];
- $currencyName = $journal['currency_name'];
- $currencySymbol = $journal['currency_symbol'];
- $currencyCode = $journal['currency_code'];
- $currencyDecimalPlaces = $journal['currency_decimal_places'];
- $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
-
- // perhaps use default currency instead?
- if ($convertToNative && $journal['currency_id'] !== $default->id) {
- $currencyId = $default->id;
- $currencyName = $default->name;
- $currencySymbol = $default->symbol;
- $currencyCode = $default->code;
- $currencyDecimalPlaces = $default->decimal_places;
- }
- // use foreign amount when the foreign currency IS the default currency.
- if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
- $field = 'foreign_amount';
- }
- $key = sprintf('%s-%s', $journal[$idKey], $currencyId);
- // sum it all up or create a new array.
- $array[$key] ??= [
- 'id' => $journal[$idKey],
- 'name' => $journal[$nameKey],
- 'sum' => '0',
- 'currency_id' => $currencyId,
- 'currency_name' => $currencyName,
- 'currency_symbol' => $currencySymbol,
- 'currency_code' => $currencyCode,
- 'currency_decimal_places' => $currencyDecimalPlaces,
- ];
-
- // add the data from the $field to the array.
- $array[$key]['sum'] = bcadd($array[$key]['sum'], app('steam')->{$method}((string) ($journal[$field] ?? '0'))); // @phpstan-ignore-line
- Log::debug(sprintf('Field for transaction #%d is "%s" (%s). Sum: %s', $journal['transaction_group_id'], $currencyCode, $field, $array[$key]['sum']));
-
- // also do foreign amount, but only when convertToNative is false (otherwise we have it already)
- // or when convertToNative is true and the foreign currency is ALSO not the default currency.
- if ((!$convertToNative || $journal['foreign_currency_id'] !== $default->id) && 0 !== (int) $journal['foreign_currency_id']) {
- Log::debug(sprintf('Use foreign amount from transaction #%d: %s %s. Sum: %s', $journal['transaction_group_id'], $currencyCode, $journal['foreign_amount'], $array[$key]['sum']));
- $key = sprintf('%s-%s', $journal[$idKey], $journal['foreign_currency_id']);
- $array[$key] ??= [
- 'id' => $journal[$idKey],
- 'name' => $journal[$nameKey],
- 'sum' => '0',
- 'currency_id' => $journal['foreign_currency_id'],
- 'currency_name' => $journal['foreign_currency_name'],
- 'currency_symbol' => $journal['foreign_currency_symbol'],
- 'currency_code' => $journal['foreign_currency_code'],
- 'currency_decimal_places' => $journal['foreign_currency_decimal_places'],
- ];
- $array[$key]['sum'] = bcadd($array[$key]['sum'], app('steam')->{$method}((string) $journal['foreign_amount'])); // @phpstan-ignore-line
- }
- }
-
- return $array;
+ $summarizer = new TransactionSummarizer($this->user);
+ return $summarizer->groupByDirection($journals, $method, $direction);
}
/**
diff --git a/app/Repositories/Budget/NoBudgetRepository.php b/app/Repositories/Budget/NoBudgetRepository.php
index 7630d50881..21dcae270f 100644
--- a/app/Repositories/Budget/NoBudgetRepository.php
+++ b/app/Repositories/Budget/NoBudgetRepository.php
@@ -25,10 +25,12 @@ declare(strict_types=1);
namespace FireflyIII\Repositories\Budget;
use Carbon\Carbon;
+use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Models\TransactionType;
use FireflyIII\Support\Facades\Amount;
+use FireflyIII\Support\Report\Summarizer\TransactionSummarizer;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Support\Collection;
@@ -50,7 +52,7 @@ class NoBudgetRepository implements NoBudgetRepositoryInterface
$collector = app(GroupCollectorInterface::class);
$collector->setAccounts($accounts)->setRange($start, $end);
- $collector->setTypes([TransactionType::WITHDRAWAL]);
+ $collector->setTypes([TransactionTypeEnum::WITHDRAWAL->value]);
$collector->withoutBudget();
$journals = $collector->getExtractedJournals();
$data = [];
@@ -103,57 +105,7 @@ class NoBudgetRepository implements NoBudgetRepositoryInterface
$collector->withoutBudget();
$collector->withBudgetInformation();
$journals = $collector->getExtractedJournals();
- $array = [];
- $convertToNative = Amount::convertToNative($this->user);
- $default = Amount::getDefaultCurrency();
-
- foreach ($journals as $journal) {
- // same as in the other methods.
- $amount = '0';
- $currencyId = (int) $journal['currency_id'];
- $currencyName = $journal['currency_name'];
- $currencySymbol = $journal['currency_symbol'];
- $currencyCode = $journal['currency_code'];
- $currencyDecimalPlaces = $journal['currency_decimal_places'];
-
- if ($convertToNative) {
- $useNative = $default->id !== (int) $journal['currency_id'];
- $amount = Amount::getAmountFromJournal($journal);
- if ($useNative) {
- Log::debug(sprintf('Journal #%d switches to native amount (original is %s)', $journal['transaction_journal_id'], $journal['currency_code']));
- $currencyId = $default->id;
- $currencyName = $default->name;
- $currencySymbol = $default->symbol;
- $currencyCode = $default->code;
- $currencyDecimalPlaces = $default->decimal_places;
- }
- }
- if (!$convertToNative) {
- $amount = $journal['amount'];
- // if the amount is not in $currency (but should be), use the foreign_amount if that one is correct.
- // otherwise, ignore the transaction all together.
- if (null !== $currency && $currencyId !== $currency->id && $currency->id === (int) $journal['foreign_currency_id']) {
- Log::debug(sprintf('Journal #%d switches to foreign amount because it matches native.', $journal['transaction_journal_id']));
- $amount = $journal['foreign_amount'];
- $currencyId = (int) $journal['foreign_currency_id'];
- $currencyName = $journal['foreign_currency_name'];
- $currencySymbol = $journal['foreign_currency_symbol'];
- $currencyCode = $journal['foreign_currency_code'];
- $currencyDecimalPlaces = $journal['foreign_currency_decimal_places'];
- }
- }
-
- $array[$currencyId] ??= [
- 'sum' => '0',
- 'currency_id' => $currencyId,
- 'currency_name' => $currencyName,
- 'currency_symbol' => $currencySymbol,
- 'currency_code' => $currencyCode,
- 'currency_decimal_places' => $currencyDecimalPlaces,
- ];
- $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->negative($amount));
- }
-
- return $array;
+ $summarizer = new TransactionSummarizer($this->user);
+ return $summarizer->groupByCurrencyId($journals);
}
}
diff --git a/app/Repositories/Budget/OperationsRepository.php b/app/Repositories/Budget/OperationsRepository.php
index 75404c40c8..eb3e82688c 100644
--- a/app/Repositories/Budget/OperationsRepository.php
+++ b/app/Repositories/Budget/OperationsRepository.php
@@ -33,6 +33,7 @@ use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Models\TransactionType;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
use FireflyIII\Support\Facades\Amount;
+use FireflyIII\Support\Report\Summarizer\TransactionSummarizer;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Support\Collection;
@@ -222,10 +223,6 @@ class OperationsRepository implements OperationsRepositoryInterface
$subset = $repository->getAccountsByType(config('firefly.valid_liabilities'));
$selection = new Collection();
- // default currency information for native stuff.
- $convertToNative = Amount::convertToNative($this->user);
- $default = Amount::getDefaultCurrency();
-
/** @var Account $account */
foreach ($subset as $account) {
if ('credit' === $repository->getMetaValue($account, 'liability_direction')) {
@@ -258,55 +255,7 @@ class OperationsRepository implements OperationsRepositoryInterface
if (null !== $currency) {
Log::debug('STOP looking for transactions in the foreign currency.');
}
- $array = [];
-
- foreach ($journals as $journal) {
- // TODO same as in category::sumexpenses
- $amount = '0';
- $currencyId = (int) $journal['currency_id'];
- $currencyName = $journal['currency_name'];
- $currencySymbol = $journal['currency_symbol'];
- $currencyCode = $journal['currency_code'];
- $currencyDecimalPlaces = $journal['currency_decimal_places'];
- if ($convertToNative) {
- $useNative = $default->id !== (int) $journal['currency_id'];
- $amount = Amount::getAmountFromJournal($journal);
- if ($useNative) {
- Log::debug(sprintf('Journal #%d switches to native amount (original is %s)', $journal['transaction_journal_id'], $journal['currency_code']));
- $currencyId = $default->id;
- $currencyName = $default->name;
- $currencySymbol = $default->symbol;
- $currencyCode = $default->code;
- $currencyDecimalPlaces = $default->decimal_places;
- }
- }
- if (!$convertToNative) {
- $amount = $journal['amount'];
- // if the amount is not in $currency (but should be), use the foreign_amount if that one is correct.
- // otherwise, ignore the transaction all together.
- if (null !== $currency && $currencyId !== $currency->id && $currency->id === (int) $journal['foreign_currency_id']) {
- Log::debug(sprintf('Journal #%d switches to foreign amount because it matches native.', $journal['transaction_journal_id']));
- $amount = $journal['foreign_amount'];
- $currencyId = (int) $journal['foreign_currency_id'];
- $currencyName = $journal['foreign_currency_name'];
- $currencySymbol = $journal['foreign_currency_symbol'];
- $currencyCode = $journal['foreign_currency_code'];
- $currencyDecimalPlaces = $journal['foreign_currency_decimal_places'];
- }
- }
- $array[$currencyId] ??= [
- 'sum' => '0',
- 'currency_id' => $currencyId,
- 'currency_name' => $currencyName,
- 'currency_symbol' => $currencySymbol,
- 'currency_code' => $currencyCode,
- 'currency_decimal_places' => $currencyDecimalPlaces,
- ];
- $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->negative($amount));
- Log::debug(sprintf('Journal #%d adds amount %s %s', $journal['transaction_journal_id'], $currencyCode, $amount));
- }
- Log::debug('End of sumExpenses.', $array);
-
- return $array;
+ $summarizer = new TransactionSummarizer($this->user);
+ return $summarizer->groupByCurrencyId($journals);
}
}
diff --git a/app/Repositories/Category/NoCategoryRepository.php b/app/Repositories/Category/NoCategoryRepository.php
index 810fc178b3..0d62a6b979 100644
--- a/app/Repositories/Category/NoCategoryRepository.php
+++ b/app/Repositories/Category/NoCategoryRepository.php
@@ -28,6 +28,7 @@ use Carbon\Carbon;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Models\TransactionType;
use FireflyIII\Support\Facades\Amount;
+use FireflyIII\Support\Report\Summarizer\TransactionSummarizer;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Support\Collection;
@@ -152,50 +153,8 @@ class NoCategoryRepository implements NoCategoryRepositoryInterface
$collector->setAccounts($accounts);
}
$journals = $collector->getExtractedJournals();
- $array = [];
- // default currency information for native stuff.
- $convertToNative = Amount::convertToNative($this->user);
- $default = Amount::getDefaultCurrency();
-
- foreach ($journals as $journal) {
- // Almost the same as in \FireflyIII\Repositories\Budget\OperationsRepository::sumExpenses
- $amount = '0';
- $currencyId = (int) $journal['currency_id'];
- $currencyName = $journal['currency_name'];
- $currencySymbol = $journal['currency_symbol'];
- $currencyCode = $journal['currency_code'];
- $currencyDecimalPlaces = $journal['currency_decimal_places'];
- if ($convertToNative) {
- $useNative = $default->id !== (int) $journal['currency_id'];
- $amount = Amount::getAmountFromJournal($journal);
- if ($useNative) {
- $currencyId = $default->id;
- $currencyName = $default->name;
- $currencySymbol = $default->symbol;
- $currencyCode = $default->code;
- $currencyDecimalPlaces = $default->decimal_places;
- }
- Log::debug(sprintf('[a] Add amount %s %s', $currencyCode, $amount));
- }
- if (!$convertToNative) {
- // ignore the amount in foreign currency.
- Log::debug(sprintf('[b] Add amount %s %s', $currencyCode, $journal['amount']));
- $amount = $journal['amount'];
- }
-
-
- $array[$currencyId] ??= [
- 'sum' => '0',
- 'currency_id' => (string) $currencyId,
- 'currency_name' => $currencyName,
- 'currency_symbol' => $currencySymbol,
- 'currency_code' => $currencyCode,
- 'currency_decimal_places' => $currencyDecimalPlaces,
- ];
- $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->negative($amount));
- }
-
- return $array;
+ $summarizer = new TransactionSummarizer($this->user);
+ return $summarizer->groupByCurrencyId($journals);
}
/**
diff --git a/app/Repositories/Category/OperationsRepository.php b/app/Repositories/Category/OperationsRepository.php
index 6d4615b3f4..dbe1ff6660 100644
--- a/app/Repositories/Category/OperationsRepository.php
+++ b/app/Repositories/Category/OperationsRepository.php
@@ -29,6 +29,7 @@ use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Models\TransactionType;
use FireflyIII\Support\Facades\Amount;
+use FireflyIII\Support\Report\Summarizer\TransactionSummarizer;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Support\Collection;
@@ -330,9 +331,6 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionTypeEnum::WITHDRAWAL->value]);
- // default currency information for native stuff.
- $convertToNative = Amount::convertToNative($this->user);
- $default = Amount::getDefaultCurrency();
if (null !== $accounts && $accounts->count() > 0) {
$collector->setAccounts($accounts);
}
@@ -342,54 +340,8 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setCategories($categories);
$collector->withCategoryInformation();
$journals = $collector->getExtractedJournals();
- $array = [];
-
- Log::debug(sprintf('Collected %d journals', count($journals)));
-
- foreach ($journals as $journal) {
- // Almost the same as in \FireflyIII\Repositories\Budget\OperationsRepository::sumExpenses
- $amount = '0';
- $currencyId = (int) $journal['currency_id'];
- $currencyName = $journal['currency_name'];
- $currencySymbol = $journal['currency_symbol'];
- $currencyCode = $journal['currency_code'];
- $currencyDecimalPlaces = $journal['currency_decimal_places'];
- if ($convertToNative) {
- $amount = Amount::getAmountFromJournal($journal);
- if ($default->id !== (int) $journal['currency_id'] && $default->id !== (int) $journal['foreign_currency_id']) {
- $currencyId = $default->id;
- $currencyName = $default->name;
- $currencySymbol = $default->symbol;
- $currencyCode = $default->code;
- $currencyDecimalPlaces = $default->decimal_places;
- }
- if ($default->id !== (int) $journal['currency_id'] && $default->id === (int) $journal['foreign_currency_id']) {
- $currencyId = $journal['foreign_currency_id'];
- $currencyName = $journal['foreign_currency_name'];
- $currencySymbol = $journal['foreign_currency_symbol'];
- $currencyCode = $journal['foreign_currency_code'];
- $currencyDecimalPlaces = $journal['foreign_currency_decimal_places'];
- }
- Log::debug(sprintf('[a] Add amount %s %s', $currencyCode, $amount));
- }
- if (!$convertToNative) {
- // ignore the amount in foreign currency.
- Log::debug(sprintf('[b] Add amount %s %s', $currencyCode, $journal['amount']));
- $amount = $journal['amount'];
- }
-
- $array[$currencyId] ??= [
- 'sum' => '0',
- 'currency_id' => (string) $currencyId,
- 'currency_name' => $currencyName,
- 'currency_symbol' => $currencySymbol,
- 'currency_code' => $currencyCode,
- 'currency_decimal_places' => $currencyDecimalPlaces,
- ];
- $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->negative($amount));
- }
-
- return $array;
+ $summarizer = new TransactionSummarizer($this->user);
+ return $summarizer->groupByCurrencyId($journals);
}
/**
diff --git a/app/Support/Report/Summarizer/TransactionSummarizer.php b/app/Support/Report/Summarizer/TransactionSummarizer.php
new file mode 100644
index 0000000000..d6cbbf04f6
--- /dev/null
+++ b/app/Support/Report/Summarizer/TransactionSummarizer.php
@@ -0,0 +1,178 @@
+setUser($user);
+ }
+ }
+
+ public function setUser(User $user): void
+ {
+ $this->user = $user;
+ $this->default = Amount::getDefaultCurrencyByUserGroup($user->userGroup);
+ $this->convertToNative = Amount::convertToNative($user);
+ }
+
+ public function groupByCurrencyId(array $journals, string $method = 'negative'): array
+ {
+ $array = [];
+ foreach ($journals as $journal) {
+ $field = 'amount';
+
+ // grab default currency information.
+ $currencyId = (int) $journal['currency_id'];
+ $currencyName = $journal['currency_name'];
+ $currencySymbol = $journal['currency_symbol'];
+ $currencyCode = $journal['currency_code'];
+ $currencyDecimalPlaces = $journal['currency_decimal_places'];
+ if ($this->convertToNative) {
+ // if convert to native, use the native amount yes or no?
+ $useNative = $this->default->id !== (int) $journal['currency_id'];
+ $useForeign = $this->default->id === (int) $journal['foreign_currency_id'];
+ if ($useNative) {
+ Log::debug(sprintf('Journal #%d switches to native amount (original is %s)', $journal['transaction_journal_id'], $journal['currency_code']));
+ $field = 'native_amount';
+ $currencyId = $this->default->id;
+ $currencyName = $this->default->name;
+ $currencySymbol = $this->default->symbol;
+ $currencyCode = $this->default->code;
+ $currencyDecimalPlaces = $this->default->decimal_places;
+ }
+ if ($useForeign) {
+ Log::debug(sprintf('Journal #%d switches to foreign amount (foreign is %s)', $journal['transaction_journal_id'], $journal['foreign_currency_code']));
+ $field = 'foreign_amount';
+ $currencyId = (int) $journal['foreign_currency_id'];
+ $currencyName = $journal['foreign_currency_name'];
+ $currencySymbol = $journal['foreign_currency_symbol'];
+ $currencyCode = $journal['foreign_currency_code'];
+ $currencyDecimalPlaces = $journal['foreign_currency_decimal_places'];
+ }
+ }
+ if(!$this->convertToNative) {
+ // default to the normal amount, but also
+ }
+ $amount = (string) ($journal[$field] ?? '0');
+ $array[$currencyId] ??= [
+ 'sum' => '0',
+ 'currency_id' => $currencyId,
+ 'currency_name' => $currencyName,
+ 'currency_symbol' => $currencySymbol,
+ 'currency_code' => $currencyCode,
+ 'currency_decimal_places' => $currencyDecimalPlaces,
+ ];
+ $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->$method($amount));
+ Log::debug(sprintf('Journal #%d adds amount %s %s', $journal['transaction_journal_id'], $currencyCode, $amount));
+ }
+ Log::debug('End of sumExpenses.', $array);
+ return $array;
+ }
+
+ public function groupByDirection(array $journals, string $method, string $direction): array {
+
+ $array = [];
+ $idKey = sprintf('%s_account_id', $direction);
+ $nameKey = sprintf('%s_account_name', $direction);
+ $convertToNative = Amount::convertToNative($this->user);
+ $default = Amount::getDefaultCurrencyByUserGroup($this->user->userGroup);
+
+
+
+
+
+ Log::debug(sprintf('groupByDirection(array, %s, %s).', $direction, $method));
+ foreach ($journals as $journal) {
+ // currency
+ $currencyId = $journal['currency_id'];
+ $currencyName = $journal['currency_name'];
+ $currencySymbol = $journal['currency_symbol'];
+ $currencyCode = $journal['currency_code'];
+ $currencyDecimalPlaces = $journal['currency_decimal_places'];
+ $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
+
+ // perhaps use default currency instead?
+ if ($convertToNative && $journal['currency_id'] !== $default->id) {
+ $currencyId = $default->id;
+ $currencyName = $default->name;
+ $currencySymbol = $default->symbol;
+ $currencyCode = $default->code;
+ $currencyDecimalPlaces = $default->decimal_places;
+ }
+ // use foreign amount when the foreign currency IS the default currency.
+ if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
+ $field = 'foreign_amount';
+ }
+ $key = sprintf('%s-%s', $journal[$idKey], $currencyId);
+ // sum it all up or create a new array.
+ $array[$key] ??= [
+ 'id' => $journal[$idKey],
+ 'name' => $journal[$nameKey],
+ 'sum' => '0',
+ 'currency_id' => $currencyId,
+ 'currency_name' => $currencyName,
+ 'currency_symbol' => $currencySymbol,
+ 'currency_code' => $currencyCode,
+ 'currency_decimal_places' => $currencyDecimalPlaces,
+ ];
+
+ // add the data from the $field to the array.
+ $array[$key]['sum'] = bcadd($array[$key]['sum'], app('steam')->{$method}((string) ($journal[$field] ?? '0'))); // @phpstan-ignore-line
+ Log::debug(sprintf('Field for transaction #%d is "%s" (%s). Sum: %s', $journal['transaction_group_id'], $currencyCode, $field, $array[$key]['sum']));
+
+ // also do foreign amount, but only when convertToNative is false (otherwise we have it already)
+ // or when convertToNative is true and the foreign currency is ALSO not the default currency.
+ if ((!$convertToNative || $journal['foreign_currency_id'] !== $default->id) && 0 !== (int) $journal['foreign_currency_id']) {
+ Log::debug(sprintf('Use foreign amount from transaction #%d: %s %s. Sum: %s', $journal['transaction_group_id'], $currencyCode, $journal['foreign_amount'], $array[$key]['sum']));
+ $key = sprintf('%s-%s', $journal[$idKey], $journal['foreign_currency_id']);
+ $array[$key] ??= [
+ 'id' => $journal[$idKey],
+ 'name' => $journal[$nameKey],
+ 'sum' => '0',
+ 'currency_id' => $journal['foreign_currency_id'],
+ 'currency_name' => $journal['foreign_currency_name'],
+ 'currency_symbol' => $journal['foreign_currency_symbol'],
+ 'currency_code' => $journal['foreign_currency_code'],
+ 'currency_decimal_places' => $journal['foreign_currency_decimal_places'],
+ ];
+ $array[$key]['sum'] = bcadd($array[$key]['sum'], app('steam')->{$method}((string) $journal['foreign_amount'])); // @phpstan-ignore-line
+ }
+ }
+
+ return $array;
+ }
+
+}
diff --git a/app/Transformers/AccountTransformer.php b/app/Transformers/AccountTransformer.php
index 70212444b4..a322dd9cbd 100644
--- a/app/Transformers/AccountTransformer.php
+++ b/app/Transformers/AccountTransformer.php
@@ -58,7 +58,7 @@ class AccountTransformer extends AbstractTransformer
// get account type:
$fullType = $account->accountType->type;
- $accountType = (string) config(sprintf('firefly.shortNamesByFullName.%s', $fullType));
+ $accountType = (string) config(sprintf( 'firefly.shortNamesByFullName.%s', $fullType));
$liabilityType = (string) config(sprintf('firefly.shortLiabilityNameByFullName.%s', $fullType));
$liabilityType = '' === $liabilityType ? null : strtolower($liabilityType);
$liabilityDirection = $this->repository->getMetaValue($account, 'liability_direction');
From 0579c8565d9b0c191c6414df82182bf53b2b979d Mon Sep 17 00:00:00 2001
From: github-actions <41898282+github-actions[bot]@users.noreply.github.com>
Date: Mon, 30 Dec 2024 04:12:18 +0100
Subject: [PATCH 161/167] Auto commit for release 'develop' on 2024-12-30
---
.ci/php-cs-fixer/composer.lock | 26 +++----
.../Autocomplete/AccountController.php | 2 +-
.../Controllers/Chart/AccountController.php | 28 +++----
app/Api/V1/Controllers/Controller.php | 4 +-
.../V1/Controllers/Data/DestroyController.php | 8 +-
.../Insight/Expense/BillController.php | 14 ++--
.../Insight/Expense/PeriodController.php | 12 +--
.../Insight/Expense/TagController.php | 26 +++----
.../Insight/Income/PeriodController.php | 12 +--
.../Insight/Income/TagController.php | 32 ++++----
.../Insight/Transfer/PeriodController.php | 34 ++++-----
.../Insight/Transfer/TagController.php | 26 +++----
.../TransactionCurrency/ShowController.php | 8 +-
app/Api/V2/Controllers/Controller.php | 4 +-
app/Factory/PiggyBankFactory.php | 48 ++++++------
.../Events/PreferencesEventHandler.php | 18 +++--
.../Observer/AvailableBudgetObserver.php | 2 +-
.../Controllers/Chart/BudgetController.php | 6 +-
app/Models/Account.php | 14 ++--
app/Models/AutoBudget.php | 4 +-
app/Models/AvailableBudget.php | 2 +-
app/Models/BudgetLimit.php | 12 +--
app/Models/PiggyBank.php | 20 ++---
app/Models/PiggyBankEvent.php | 2 +-
.../Account/OperationsRepository.php | 74 +++++++++----------
app/Repositories/Bill/BillRepository.php | 2 +-
.../Budget/NoBudgetRepository.php | 7 +-
.../Budget/OperationsRepository.php | 11 +--
.../Category/NoCategoryRepository.php | 7 +-
.../Category/OperationsRepository.php | 5 +-
app/Support/Amount.php | 51 ++++++-------
app/Support/Navigation.php | 4 +-
.../Summarizer/TransactionSummarizer.php | 30 ++++----
app/Transformers/AccountTransformer.php | 2 +-
changelog.md | 6 +-
composer.lock | 26 +++----
config/firefly.php | 2 +-
resources/assets/v1/src/locales/de.json | 2 +-
resources/assets/v1/src/locales/nl.json | 6 +-
tests/integration/TestCase.php | 5 +-
40 files changed, 301 insertions(+), 303 deletions(-)
diff --git a/.ci/php-cs-fixer/composer.lock b/.ci/php-cs-fixer/composer.lock
index c358fdbe1c..d63d6ea412 100644
--- a/.ci/php-cs-fixer/composer.lock
+++ b/.ci/php-cs-fixer/composer.lock
@@ -406,16 +406,16 @@
},
{
"name": "friendsofphp/php-cs-fixer",
- "version": "v3.65.0",
+ "version": "v3.66.0",
"source": {
"type": "git",
"url": "https://github.com/PHP-CS-Fixer/PHP-CS-Fixer.git",
- "reference": "79d4f3e77b250a7d8043d76c6af8f0695e8a469f"
+ "reference": "5f5f2a142ff36b93c41885bca29cc5f861c013e6"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/PHP-CS-Fixer/PHP-CS-Fixer/zipball/79d4f3e77b250a7d8043d76c6af8f0695e8a469f",
- "reference": "79d4f3e77b250a7d8043d76c6af8f0695e8a469f",
+ "url": "https://api.github.com/repos/PHP-CS-Fixer/PHP-CS-Fixer/zipball/5f5f2a142ff36b93c41885bca29cc5f861c013e6",
+ "reference": "5f5f2a142ff36b93c41885bca29cc5f861c013e6",
"shasum": ""
},
"require": {
@@ -441,7 +441,7 @@
"symfony/polyfill-mbstring": "^1.28",
"symfony/polyfill-php80": "^1.28",
"symfony/polyfill-php81": "^1.28",
- "symfony/process": "^5.4 || ^6.0 || ^7.0",
+ "symfony/process": "^5.4 || ^6.0 || ^7.0 <7.2",
"symfony/stopwatch": "^5.4 || ^6.0 || ^7.0"
},
"require-dev": {
@@ -497,7 +497,7 @@
],
"support": {
"issues": "https://github.com/PHP-CS-Fixer/PHP-CS-Fixer/issues",
- "source": "https://github.com/PHP-CS-Fixer/PHP-CS-Fixer/tree/v3.65.0"
+ "source": "https://github.com/PHP-CS-Fixer/PHP-CS-Fixer/tree/v3.66.0"
},
"funding": [
{
@@ -505,7 +505,7 @@
"type": "github"
}
],
- "time": "2024-11-25T00:39:24+00:00"
+ "time": "2024-12-29T13:46:23+00:00"
},
{
"name": "psr/container",
@@ -2246,16 +2246,16 @@
},
{
"name": "symfony/process",
- "version": "v7.2.0",
+ "version": "v7.1.8",
"source": {
"type": "git",
"url": "https://github.com/symfony/process.git",
- "reference": "d34b22ba9390ec19d2dd966c40aa9e8462f27a7e"
+ "reference": "42783370fda6e538771f7c7a36e9fa2ee3a84892"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/symfony/process/zipball/d34b22ba9390ec19d2dd966c40aa9e8462f27a7e",
- "reference": "d34b22ba9390ec19d2dd966c40aa9e8462f27a7e",
+ "url": "https://api.github.com/repos/symfony/process/zipball/42783370fda6e538771f7c7a36e9fa2ee3a84892",
+ "reference": "42783370fda6e538771f7c7a36e9fa2ee3a84892",
"shasum": ""
},
"require": {
@@ -2287,7 +2287,7 @@
"description": "Executes commands in sub-processes",
"homepage": "https://symfony.com",
"support": {
- "source": "https://github.com/symfony/process/tree/v7.2.0"
+ "source": "https://github.com/symfony/process/tree/v7.1.8"
},
"funding": [
{
@@ -2303,7 +2303,7 @@
"type": "tidelift"
}
],
- "time": "2024-11-06T14:24:19+00:00"
+ "time": "2024-11-06T14:23:19+00:00"
},
{
"name": "symfony/service-contracts",
diff --git a/app/Api/V1/Controllers/Autocomplete/AccountController.php b/app/Api/V1/Controllers/Autocomplete/AccountController.php
index fdbf680486..7651886b7c 100644
--- a/app/Api/V1/Controllers/Autocomplete/AccountController.php
+++ b/app/Api/V1/Controllers/Autocomplete/AccountController.php
@@ -99,7 +99,7 @@ class AccountController extends Controller
);
}
- $return[] = [
+ $return[] = [
'id' => (string) $account->id,
'name' => $account->name,
'name_with_balance' => $nameWithBalance,
diff --git a/app/Api/V1/Controllers/Chart/AccountController.php b/app/Api/V1/Controllers/Chart/AccountController.php
index 3f86521a4f..e47ae5d23e 100644
--- a/app/Api/V1/Controllers/Chart/AccountController.php
+++ b/app/Api/V1/Controllers/Chart/AccountController.php
@@ -72,19 +72,19 @@ class AccountController extends Controller
public function overview(DateRequest $request): JsonResponse
{
// parameters for chart:
- $dates = $request->getAll();
+ $dates = $request->getAll();
/** @var Carbon $start */
- $start = $dates['start'];
+ $start = $dates['start'];
/** @var Carbon $end */
- $end = $dates['end'];
+ $end = $dates['end'];
// user's preferences
$defaultSet = $this->repository->getAccountsByType([AccountTypeEnum::ASSET->value])->pluck('id')->toArray();
/** @var Preference $frontpage */
- $frontpage = app('preferences')->get('frontpageAccounts', $defaultSet);
+ $frontpage = app('preferences')->get('frontpageAccounts', $defaultSet);
if (!(is_array($frontpage->data) && count($frontpage->data) > 0)) {
$frontpage->data = $defaultSet;
@@ -92,14 +92,14 @@ class AccountController extends Controller
}
// get accounts:
- $accounts = $this->repository->getAccountsById($frontpage->data);
- $chartData = [];
+ $accounts = $this->repository->getAccountsById($frontpage->data);
+ $chartData = [];
/** @var Account $account */
foreach ($accounts as $account) {
- $currency = $this->repository->getAccountCurrency($account) ?? $this->defaultCurrency;
- $field = $this->convertToNative && $currency->id !== $this->defaultCurrency->id ? 'native_balance' : 'balance';
- $currentSet = [
+ $currency = $this->repository->getAccountCurrency($account) ?? $this->defaultCurrency;
+ $field = $this->convertToNative && $currency->id !== $this->defaultCurrency->id ? 'native_balance' : 'balance';
+ $currentSet = [
'label' => $account->name,
'currency_id' => (string) $currency->id,
'currency_code' => $currency->code,
@@ -116,14 +116,14 @@ class AccountController extends Controller
$range = app('steam')->finalAccountBalanceInRange($account, $start, clone $end, $this->convertToNative);
$previous = array_values($range)[0][$field];
while ($currentStart <= $end) {
- $format = $currentStart->format('Y-m-d');
- $label = $currentStart->toAtomString();
- $balance = array_key_exists($format, $range) ? $range[$format][$field] : $previous;
- $previous = $balance;
+ $format = $currentStart->format('Y-m-d');
+ $label = $currentStart->toAtomString();
+ $balance = array_key_exists($format, $range) ? $range[$format][$field] : $previous;
+ $previous = $balance;
$currentStart->addDay();
$currentSet['entries'][$label] = $balance;
}
- $chartData[] = $currentSet;
+ $chartData[] = $currentSet;
}
return response()->json($chartData);
diff --git a/app/Api/V1/Controllers/Controller.php b/app/Api/V1/Controllers/Controller.php
index 5f710f1220..fcf5b21ef2 100644
--- a/app/Api/V1/Controllers/Controller.php
+++ b/app/Api/V1/Controllers/Controller.php
@@ -94,8 +94,8 @@ abstract class Controller extends BaseController
if ($page < 1) {
$page = 1;
}
- if ($page > pow(2,16)) {
- $page = pow(2, 16);
+ if ($page > 2 ** 16) {
+ $page = 2 ** 16;
}
$bag->set('page', $page);
diff --git a/app/Api/V1/Controllers/Data/DestroyController.php b/app/Api/V1/Controllers/Data/DestroyController.php
index 3a73ec08d5..c83e18d079 100644
--- a/app/Api/V1/Controllers/Data/DestroyController.php
+++ b/app/Api/V1/Controllers/Data/DestroyController.php
@@ -63,8 +63,8 @@ class DestroyController extends Controller
*/
public function destroy(DestroyRequest $request): JsonResponse
{
- $objects = $request->getObjects();
- $this->unused = $request->boolean('unused', false);
+ $objects = $request->getObjects();
+ $this->unused = $request->boolean('unused', false);
$allExceptAssets = [AccountTypeEnum::BENEFICIARY->value, AccountTypeEnum::CASH->value, AccountTypeEnum::CREDITCARD->value, AccountTypeEnum::DEFAULT->value, AccountTypeEnum::EXPENSE->value, AccountTypeEnum::IMPORT->value, AccountTypeEnum::INITIAL_BALANCE->value, AccountTypeEnum::LIABILITY_CREDIT->value, AccountTypeEnum::RECONCILIATION->value, AccountTypeEnum::REVENUE->value];
$all = [AccountTypeEnum::ASSET->value, AccountTypeEnum::BENEFICIARY->value, AccountTypeEnum::CASH->value, AccountTypeEnum::CREDITCARD->value, AccountTypeEnum::DEBT->value, AccountTypeEnum::DEFAULT->value, AccountTypeEnum::EXPENSE->value, AccountTypeEnum::IMPORT->value, AccountTypeEnum::INITIAL_BALANCE->value, AccountTypeEnum::LIABILITY_CREDIT->value, AccountTypeEnum::LOAN->value, AccountTypeEnum::MORTGAGE->value, AccountTypeEnum::RECONCILIATION->value];
@@ -101,11 +101,11 @@ class DestroyController extends Controller
private function destroyBudgets(): void
{
/** @var AvailableBudgetRepositoryInterface $abRepository */
- $abRepository = app(AvailableBudgetRepositoryInterface::class);
+ $abRepository = app(AvailableBudgetRepositoryInterface::class);
$abRepository->destroyAll();
/** @var BudgetLimitRepositoryInterface $blRepository */
- $blRepository = app(BudgetLimitRepositoryInterface::class);
+ $blRepository = app(BudgetLimitRepositoryInterface::class);
$blRepository->destroyAll();
/** @var BudgetRepositoryInterface $budgetRepository */
diff --git a/app/Api/V1/Controllers/Insight/Expense/BillController.php b/app/Api/V1/Controllers/Insight/Expense/BillController.php
index bd6bff441e..10a89eff60 100644
--- a/app/Api/V1/Controllers/Insight/Expense/BillController.php
+++ b/app/Api/V1/Controllers/Insight/Expense/BillController.php
@@ -79,11 +79,11 @@ class BillController extends Controller
}
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::WITHDRAWAL->value])->setRange($start, $end)->setSourceAccounts($accounts);
$collector->setBills($bills);
- $genericSet = $collector->getExtractedJournals();
+ $genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
$billId = (int) $journal['bill_id'];
$currencyId = (int) $journal['currency_id'];
@@ -102,10 +102,10 @@ class BillController extends Controller
}
Log::debug(sprintf('Journal #%d in bill #%d will use %s (%s %s)', $journal['transaction_group_id'], $billId, $field, $currencyCode, $journal[$field] ?? '0'));
- $key = sprintf('%d-%d', $billId, $currencyId);
+ $key = sprintf('%d-%d', $billId, $currencyId);
if (0 !== $currencyId) {
- $response[$key] ??= [
+ $response[$key] ??= [
'id' => (string) $billId,
'name' => $journal['bill_name'],
'difference' => '0',
@@ -137,11 +137,11 @@ class BillController extends Controller
$response = [];
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::WITHDRAWAL->value])->setRange($start, $end)->setSourceAccounts($accounts);
$collector->withoutBill();
- $genericSet = $collector->getExtractedJournals();
+ $genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
$currencyId = (int) $journal['currency_id'];
@@ -161,7 +161,7 @@ class BillController extends Controller
Log::debug(sprintf('Journal #%d will use %s (%s %s)', $journal['transaction_group_id'], $field, $currencyCode, $journal[$field] ?? '0'));
if (0 !== $currencyId) {
- $response[$currencyId] ??= [
+ $response[$currencyId] ??= [
'difference' => '0',
'difference_float' => 0,
'currency_id' => (string) $currencyId,
diff --git a/app/Api/V1/Controllers/Insight/Expense/PeriodController.php b/app/Api/V1/Controllers/Insight/Expense/PeriodController.php
index 28a4fd25e7..b4d2c42450 100644
--- a/app/Api/V1/Controllers/Insight/Expense/PeriodController.php
+++ b/app/Api/V1/Controllers/Insight/Expense/PeriodController.php
@@ -51,14 +51,14 @@ class PeriodController extends Controller
$default = Amount::getDefaultCurrency();
// collect all expenses in this period (regardless of type)
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::WITHDRAWAL->value])->setRange($start, $end)->setSourceAccounts($accounts);
- $genericSet = $collector->getExtractedJournals();
+ $genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
// same code as many other sumExpense methods. I think this needs some kind of generic method.
- $amount = '0';
- $currencyId = (int) $journal['currency_id'];
- $currencyCode = $journal['currency_code'];
+ $amount = '0';
+ $currencyId = (int) $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
if ($convertToNative) {
$amount = Amount::getAmountFromJournal($journal);
if ($default->id !== (int) $journal['currency_id'] && $default->id !== (int) $journal['foreign_currency_id']) {
@@ -78,7 +78,7 @@ class PeriodController extends Controller
}
- $response[$currencyId] ??= [
+ $response[$currencyId] ??= [
'difference' => '0',
'difference_float' => 0,
'currency_id' => (string) $currencyId,
diff --git a/app/Api/V1/Controllers/Insight/Expense/TagController.php b/app/Api/V1/Controllers/Insight/Expense/TagController.php
index b39105ada0..83f43eee37 100644
--- a/app/Api/V1/Controllers/Insight/Expense/TagController.php
+++ b/app/Api/V1/Controllers/Insight/Expense/TagController.php
@@ -72,17 +72,17 @@ class TagController extends Controller
$default = Amount::getDefaultCurrency();
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::WITHDRAWAL->value])->setRange($start, $end)->setSourceAccounts($accounts);
$collector->withoutTags();
- $genericSet = $collector->getExtractedJournals();
+ $genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
// same code as many other sumExpense methods. I think this needs some kind of generic method.
- $amount = '0';
- $currencyId = (int) $journal['currency_id'];
- $currencyCode = $journal['currency_code'];
+ $amount = '0';
+ $currencyId = (int) $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
if ($convertToNative) {
$amount = Amount::getAmountFromJournal($journal);
if ($default->id !== (int) $journal['currency_id'] && $default->id !== (int) $journal['foreign_currency_id']) {
@@ -101,7 +101,7 @@ class TagController extends Controller
$amount = $journal['amount'];
}
- $response[$currencyId] ??= [
+ $response[$currencyId] ??= [
'difference' => '0',
'difference_float' => 0,
'currency_id' => (string) $currencyId,
@@ -122,11 +122,11 @@ class TagController extends Controller
*/
public function tag(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $tags = $request->getTags();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $tags = $request->getTags();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $response = [];
// get all tags:
if (0 === $tags->count()) {
@@ -134,7 +134,7 @@ class TagController extends Controller
}
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::WITHDRAWAL->value])->setRange($start, $end)->setSourceAccounts($accounts);
$collector->setTags($tags);
$genericSet = $collector->getExtractedJournals();
@@ -152,7 +152,7 @@ class TagController extends Controller
// on currency ID
if (0 !== $currencyId) {
- $response[$key] ??= [
+ $response[$key] ??= [
'id' => (string) $tagId,
'name' => $tag['name'],
'difference' => '0',
diff --git a/app/Api/V1/Controllers/Insight/Income/PeriodController.php b/app/Api/V1/Controllers/Insight/Income/PeriodController.php
index 360abf4664..89d4c251c5 100644
--- a/app/Api/V1/Controllers/Insight/Income/PeriodController.php
+++ b/app/Api/V1/Controllers/Insight/Income/PeriodController.php
@@ -50,14 +50,14 @@ class PeriodController extends Controller
$default = Amount::getDefaultCurrency();
// collect all expenses in this period (regardless of type)
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::DEPOSIT->value])->setRange($start, $end)->setDestinationAccounts($accounts);
- $genericSet = $collector->getExtractedJournals();
+ $genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
// currency
- $currencyId = $journal['currency_id'];
- $currencyCode = $journal['currency_code'];
- $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
+ $currencyId = $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
// perhaps use default currency instead?
if ($convertToNative && $journal['currency_id'] !== $default->id) {
@@ -69,7 +69,7 @@ class PeriodController extends Controller
$field = 'foreign_amount';
}
- $response[$currencyId] ??= [
+ $response[$currencyId] ??= [
'difference' => '0',
'difference_float' => 0,
'currency_id' => (string) $currencyId,
diff --git a/app/Api/V1/Controllers/Insight/Income/TagController.php b/app/Api/V1/Controllers/Insight/Income/TagController.php
index 3a3a5f67b6..e81186582e 100644
--- a/app/Api/V1/Controllers/Insight/Income/TagController.php
+++ b/app/Api/V1/Controllers/Insight/Income/TagController.php
@@ -64,25 +64,25 @@ class TagController extends Controller
*/
public function noTag(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $response = [];
$convertToNative = Amount::convertToNative();
$default = Amount::getDefaultCurrency();
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionTypeEnum::DEPOSIT->value])->setRange($start, $end)->setDestinationAccounts($accounts);
$collector->withoutTags();
- $genericSet = $collector->getExtractedJournals();
+ $genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
// currency
- $currencyId = $journal['currency_id'];
- $currencyCode = $journal['currency_code'];
- $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
+ $currencyId = $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
// perhaps use default currency instead?
if ($convertToNative && $journal['currency_id'] !== $default->id) {
@@ -95,13 +95,13 @@ class TagController extends Controller
}
$response[$currencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $currencyId,
- 'currency_code' => $currencyCode,
- ];
- $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal[$field]));
- $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference'];
+ 'difference' => '0',
+ 'difference_float' => 0,
+ 'currency_id' => (string) $currencyId,
+ 'currency_code' => $currencyCode,
+ ];
+ $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal[$field]));
+ $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference'];
}
diff --git a/app/Api/V1/Controllers/Insight/Transfer/PeriodController.php b/app/Api/V1/Controllers/Insight/Transfer/PeriodController.php
index 5d0b5a22d5..e86a98a748 100644
--- a/app/Api/V1/Controllers/Insight/Transfer/PeriodController.php
+++ b/app/Api/V1/Controllers/Insight/Transfer/PeriodController.php
@@ -42,22 +42,22 @@ class PeriodController extends Controller
*/
public function total(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $response = [];
$convertToNative = Amount::convertToNative();
$default = Amount::getDefaultCurrency();
// collect all expenses in this period (regardless of type)
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionType::TRANSFER])->setRange($start, $end)->setDestinationAccounts($accounts);
- $genericSet = $collector->getExtractedJournals();
+ $genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
// currency
- $currencyId = $journal['currency_id'];
- $currencyCode = $journal['currency_code'];
- $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
+ $currencyId = $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
// perhaps use default currency instead?
if ($convertToNative && $journal['currency_id'] !== $default->id) {
@@ -69,14 +69,14 @@ class PeriodController extends Controller
$field = 'foreign_amount';
}
- $response[$currencyId] ??= [
- 'difference' => '0',
- 'difference_float' => 0,
- 'currency_id' => (string) $currencyId,
- 'currency_code' => $currencyCode,
- ];
- $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal[$field]));
- $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference'];
+ $response[$currencyId] ??= [
+ 'difference' => '0',
+ 'difference_float' => 0,
+ 'currency_id' => (string) $currencyId,
+ 'currency_code' => $currencyCode,
+ ];
+ $response[$currencyId]['difference'] = bcadd($response[$currencyId]['difference'], app('steam')->positive($journal[$field]));
+ $response[$currencyId]['difference_float'] = (float) $response[$currencyId]['difference'];
}
diff --git a/app/Api/V1/Controllers/Insight/Transfer/TagController.php b/app/Api/V1/Controllers/Insight/Transfer/TagController.php
index 001a4ca5f1..4d3f8f56db 100644
--- a/app/Api/V1/Controllers/Insight/Transfer/TagController.php
+++ b/app/Api/V1/Controllers/Insight/Transfer/TagController.php
@@ -71,17 +71,17 @@ class TagController extends Controller
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionType::TRANSFER])->setRange($start, $end)->setDestinationAccounts($accounts);
$collector->withoutTags();
- $genericSet = $collector->getExtractedJournals();
+ $genericSet = $collector->getExtractedJournals();
foreach ($genericSet as $journal) {
// currency
- $currencyId = $journal['currency_id'];
- $currencyCode = $journal['currency_code'];
- $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
+ $currencyId = $journal['currency_id'];
+ $currencyCode = $journal['currency_code'];
+ $field = $convertToNative && $currencyId !== $default->id ? 'native_amount' : 'amount';
// perhaps use default currency instead?
if ($convertToNative && $journal['currency_id'] !== $default->id) {
@@ -93,7 +93,7 @@ class TagController extends Controller
$field = 'foreign_amount';
}
- $response[$currencyId] ??= [
+ $response[$currencyId] ??= [
'difference' => '0',
'difference_float' => 0,
'currency_id' => (string) $currencyId,
@@ -115,11 +115,11 @@ class TagController extends Controller
*/
public function tag(GenericRequest $request): JsonResponse
{
- $accounts = $request->getAssetAccounts();
- $tags = $request->getTags();
- $start = $request->getStart();
- $end = $request->getEnd();
- $response = [];
+ $accounts = $request->getAssetAccounts();
+ $tags = $request->getTags();
+ $start = $request->getStart();
+ $end = $request->getEnd();
+ $response = [];
// get all tags:
if (0 === $tags->count()) {
@@ -127,7 +127,7 @@ class TagController extends Controller
}
// collect all expenses in this period (regardless of type) by the given bills and accounts.
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setTypes([TransactionType::TRANSFER])->setRange($start, $end)->setDestinationAccounts($accounts);
$collector->setTags($tags);
$genericSet = $collector->getExtractedJournals();
@@ -145,7 +145,7 @@ class TagController extends Controller
// on currency ID
if (0 !== $currencyId) {
- $response[$key] ??= [
+ $response[$key] ??= [
'id' => (string) $tagId,
'name' => $tag['name'],
'difference' => '0',
diff --git a/app/Api/V1/Controllers/Models/TransactionCurrency/ShowController.php b/app/Api/V1/Controllers/Models/TransactionCurrency/ShowController.php
index 8d9cec0f1f..48ff9bb724 100644
--- a/app/Api/V1/Controllers/Models/TransactionCurrency/ShowController.php
+++ b/app/Api/V1/Controllers/Models/TransactionCurrency/ShowController.php
@@ -105,18 +105,18 @@ class ShowController extends Controller
public function show(TransactionCurrency $currency): JsonResponse
{
/** @var User $user */
- $user = auth()->user();
- $manager = $this->getManager();
+ $user = auth()->user();
+ $manager = $this->getManager();
$this->parameters->set('defaultCurrency', $this->defaultCurrency);
// update fields with user info.
$currency->refreshForUser($user);
/** @var CurrencyTransformer $transformer */
- $transformer = app(CurrencyTransformer::class);
+ $transformer = app(CurrencyTransformer::class);
$transformer->setParameters($this->parameters);
- $resource = new Item($currency, $transformer, 'currencies');
+ $resource = new Item($currency, $transformer, 'currencies');
return response()->json($manager->createData($resource)->toArray())->header('Content-Type', self::CONTENT_TYPE);
}
diff --git a/app/Api/V2/Controllers/Controller.php b/app/Api/V2/Controllers/Controller.php
index 24499ef3b5..ee8d782e48 100644
--- a/app/Api/V2/Controllers/Controller.php
+++ b/app/Api/V2/Controllers/Controller.php
@@ -93,8 +93,8 @@ class Controller extends BaseController
if ($page < 1) {
$page = 1;
}
- if ($page > pow(2,16)) {
- $page = pow(2, 16);
+ if ($page > 2 ** 16) {
+ $page = 2 ** 16;
}
$bag->set('page', $page);
diff --git a/app/Factory/PiggyBankFactory.php b/app/Factory/PiggyBankFactory.php
index fead291f9b..831f24b8b8 100644
--- a/app/Factory/PiggyBankFactory.php
+++ b/app/Factory/PiggyBankFactory.php
@@ -43,11 +43,11 @@ class PiggyBankFactory
public User $user {
set(User $value) {
- $this->user = $value;
- $this->currencyRepository->setUser($value);
- $this->accountRepository->setUser($value);
- $this->piggyBankRepository->setUser($value);
- }
+ $this->user = $value;
+ $this->currencyRepository->setUser($value);
+ $this->accountRepository->setUser($value);
+ $this->piggyBankRepository->setUser($value);
+ }
}
private AccountRepositoryInterface $accountRepository;
private CurrencyRepositoryInterface $currencyRepository;
@@ -62,15 +62,11 @@ class PiggyBankFactory
/**
* Store a piggy bank or come back with an exception.
- *
- * @param array $data
- *
- * @return PiggyBank
*/
public function store(array $data): PiggyBank
{
- $piggyBankData = $data;
+ $piggyBankData = $data;
// unset some fields
unset($piggyBankData['object_group_title'], $piggyBankData['transaction_currency_code'], $piggyBankData['transaction_currency_id'], $piggyBankData['accounts'], $piggyBankData['object_group_id'], $piggyBankData['notes']);
@@ -94,11 +90,11 @@ class PiggyBankFactory
throw new FireflyException('400005: Could not store new piggy bank.', 0, $e);
}
- $piggyBank = $this->setOrder($piggyBank, $data);
+ $piggyBank = $this->setOrder($piggyBank, $data);
$this->linkToAccountIds($piggyBank, $data['accounts']);
$this->piggyBankRepository->updateNote($piggyBank, $data['notes']);
- $objectGroupTitle = $data['object_group_title'] ?? '';
+ $objectGroupTitle = $data['object_group_title'] ?? '';
if ('' !== $objectGroupTitle) {
$objectGroup = $this->findOrCreateObjectGroup($objectGroupTitle);
if (null !== $objectGroup) {
@@ -106,7 +102,7 @@ class PiggyBankFactory
}
}
// try also with ID
- $objectGroupId = (int) ($data['object_group_id'] ?? 0);
+ $objectGroupId = (int) ($data['object_group_id'] ?? 0);
if (0 !== $objectGroupId) {
$objectGroup = $this->findObjectGroupById($objectGroupId);
if (null !== $objectGroup) {
@@ -114,9 +110,10 @@ class PiggyBankFactory
}
}
Log::debug('Touch piggy bank');
- $piggyBank->encrypted = false;
+ $piggyBank->encrypted = false;
$piggyBank->save();
$piggyBank->touch();
+
return $piggyBank;
}
@@ -132,6 +129,7 @@ class PiggyBankFactory
$currency = $this->currencyRepository->find((int) ($data['transaction_currency_id'] ?? 0));
}
$currency ??= $defaultCurrency;
+
return $currency;
}
@@ -144,12 +142,12 @@ class PiggyBankFactory
}
// first find by ID:
if ($piggyBankId > 0) {
- $piggyBank = PiggyBank
- ::leftJoin('account_piggy_bank', 'account_piggy_bank.piggy_bank_id', '=', 'piggy_banks.id')
+ $piggyBank = PiggyBank::leftJoin('account_piggy_bank', 'account_piggy_bank.piggy_bank_id', '=', 'piggy_banks.id')
->leftJoin('accounts', 'accounts.id', '=', 'account_piggy_bank.account_id')
->where('accounts.user_id', $this->user->id)
->where('piggy_banks.id', $piggyBankId)
- ->first(['piggy_banks.*']);
+ ->first(['piggy_banks.*'])
+ ;
if (null !== $piggyBank) {
return $piggyBank;
}
@@ -169,23 +167,24 @@ class PiggyBankFactory
public function findByName(string $name): ?PiggyBank
{
- return PiggyBank
- ::leftJoin('account_piggy_bank', 'account_piggy_bank.piggy_bank_id', '=', 'piggy_banks.id')
+ return PiggyBank::leftJoin('account_piggy_bank', 'account_piggy_bank.piggy_bank_id', '=', 'piggy_banks.id')
->leftJoin('accounts', 'accounts.id', '=', 'account_piggy_bank.account_id')
->where('accounts.user_id', $this->user->id)
->where('piggy_banks.name', $name)
- ->first(['piggy_banks.*']);
+ ->first(['piggy_banks.*'])
+ ;
}
private function setOrder(PiggyBank $piggyBank, array $data): PiggyBank
{
$this->resetOrder();
- $order = $this->getMaxOrder() + 1;
+ $order = $this->getMaxOrder() + 1;
if (array_key_exists('order', $data)) {
$order = $data['order'];
}
$piggyBank->order = $order;
$piggyBank->saveQuietly();
+
return $piggyBank;
}
@@ -193,8 +192,7 @@ class PiggyBankFactory
public function resetOrder(): void
{
// TODO duplicate code
- $set = PiggyBank
- ::leftJoin('account_piggy_bank', 'account_piggy_bank.piggy_bank_id', '=', 'piggy_banks.id')
+ $set = PiggyBank::leftJoin('account_piggy_bank', 'account_piggy_bank.piggy_bank_id', '=', 'piggy_banks.id')
->leftJoin('accounts', 'accounts.id', '=', 'account_piggy_bank.account_id')
->where('accounts.user_id', $this->user->id)
->with(
@@ -202,7 +200,8 @@ class PiggyBankFactory
'objectGroups',
]
)
- ->orderBy('piggy_banks.order', 'ASC')->get(['piggy_banks.*']);
+ ->orderBy('piggy_banks.order', 'ASC')->get(['piggy_banks.*'])
+ ;
$current = 1;
foreach ($set as $piggyBank) {
if ($piggyBank->order !== $current) {
@@ -214,7 +213,6 @@ class PiggyBankFactory
}
}
-
private function getMaxOrder(): int
{
return (int) $this->piggyBankRepository->getPiggyBanks()->max('order');
diff --git a/app/Handlers/Events/PreferencesEventHandler.php b/app/Handlers/Events/PreferencesEventHandler.php
index 28d4e5c5e8..a18dcc75f7 100644
--- a/app/Handlers/Events/PreferencesEventHandler.php
+++ b/app/Handlers/Events/PreferencesEventHandler.php
@@ -99,7 +99,7 @@ class PreferencesEventHandler
{
$repository = app(BudgetRepositoryInterface::class);
$repository->setUserGroup($userGroup);
- $set = $repository->getBudgets();
+ $set = $repository->getBudgets();
/** @var Budget $budget */
foreach ($set as $budget) {
@@ -127,13 +127,15 @@ class PreferencesEventHandler
{
// custom query because of the potential size of this update.
$success = DB::table('transactions')
- ->join('transaction_journals', 'transaction_journals.id', '=', 'transactions.transaction_journal_id')
- ->where('transaction_journals.user_group_id', $userGroup->id)
- ->where(static function (Builder $q): void {
- $q->whereNotNull('native_amount')
- ->orWhereNotNull('native_foreign_amount');
- })
- ->update(['native_amount' => null, 'native_foreign_amount' => null]);
+ ->join('transaction_journals', 'transaction_journals.id', '=', 'transactions.transaction_journal_id')
+ ->where('transaction_journals.user_group_id', $userGroup->id)
+ ->where(static function (Builder $q): void {
+ $q->whereNotNull('native_amount')
+ ->orWhereNotNull('native_foreign_amount')
+ ;
+ })
+ ->update(['native_amount' => null, 'native_foreign_amount' => null])
+ ;
Log::debug(sprintf('Reset %d transactions.', $success));
}
}
diff --git a/app/Handlers/Observer/AvailableBudgetObserver.php b/app/Handlers/Observer/AvailableBudgetObserver.php
index 6bf610c0a8..8644bac575 100644
--- a/app/Handlers/Observer/AvailableBudgetObserver.php
+++ b/app/Handlers/Observer/AvailableBudgetObserver.php
@@ -39,7 +39,7 @@ class AvailableBudgetObserver
public function updated(AvailableBudget $availableBudget): void
{
- //Log::debug('Observe "updated" of an available budget.');
+ // Log::debug('Observe "updated" of an available budget.');
$this->updateNativeAmount($availableBudget);
}
diff --git a/app/Http/Controllers/Chart/BudgetController.php b/app/Http/Controllers/Chart/BudgetController.php
index 961c8daac5..df07bf8d10 100644
--- a/app/Http/Controllers/Chart/BudgetController.php
+++ b/app/Http/Controllers/Chart/BudgetController.php
@@ -234,9 +234,9 @@ class BudgetController extends Controller
$key = sprintf('%d-%d', $journal['source_account_id'], $journal['currency_id']);
$amount = $journal['amount'];
- $symbol = $journal['currency_symbol'];
- $code = $journal['currency_code'];
- $name = $journal['currency_name'];
+ $symbol = $journal['currency_symbol'];
+ $code = $journal['currency_code'];
+ $name = $journal['currency_name'];
// if convert to native, use the native things, unless it's the foreign amount which is in the native currency.
if ($this->convertToNative && $journal['currency_id'] !== $this->defaultCurrency->id) {
diff --git a/app/Models/Account.php b/app/Models/Account.php
index 03d87fc708..eede2e7f38 100644
--- a/app/Models/Account.php
+++ b/app/Models/Account.php
@@ -50,13 +50,13 @@ class Account extends Model
protected $casts
= [
- 'created_at' => 'datetime',
- 'updated_at' => 'datetime',
- 'user_id' => 'integer',
- 'deleted_at' => 'datetime',
- 'active' => 'boolean',
- 'encrypted' => 'boolean',
- 'virtual_balance' => 'string',
+ 'created_at' => 'datetime',
+ 'updated_at' => 'datetime',
+ 'user_id' => 'integer',
+ 'deleted_at' => 'datetime',
+ 'active' => 'boolean',
+ 'encrypted' => 'boolean',
+ 'virtual_balance' => 'string',
'native_virtual_balance' => 'string',
];
diff --git a/app/Models/AutoBudget.php b/app/Models/AutoBudget.php
index a2d475c176..7eea5746e1 100644
--- a/app/Models/AutoBudget.php
+++ b/app/Models/AutoBudget.php
@@ -48,10 +48,10 @@ class AutoBudget extends Model
public const int AUTO_BUDGET_ROLLOVER = 2;
protected $casts
= [
- 'amount' => 'string',
+ 'amount' => 'string',
'native_amount' => 'string',
];
- protected $fillable = ['budget_id', 'amount', 'period','native_amount'];
+ protected $fillable = ['budget_id', 'amount', 'period', 'native_amount'];
public function budget(): BelongsTo
{
diff --git a/app/Models/AvailableBudget.php b/app/Models/AvailableBudget.php
index eef99656af..c88b5d7a3c 100644
--- a/app/Models/AvailableBudget.php
+++ b/app/Models/AvailableBudget.php
@@ -53,7 +53,7 @@ class AvailableBudget extends Model
'native_amount' => 'string',
];
- protected $fillable = ['user_id', 'user_group_id', 'transaction_currency_id', 'amount', 'start_date', 'end_date', 'start_date_tz', 'end_date_tz','native_amount'];
+ protected $fillable = ['user_id', 'user_group_id', 'transaction_currency_id', 'amount', 'start_date', 'end_date', 'start_date_tz', 'end_date_tz', 'native_amount'];
/**
* Route binder. Converts the key in the URL to the specified object (or throw 404).
diff --git a/app/Models/BudgetLimit.php b/app/Models/BudgetLimit.php
index b2a652db14..375b9e6b6c 100644
--- a/app/Models/BudgetLimit.php
+++ b/app/Models/BudgetLimit.php
@@ -43,12 +43,12 @@ class BudgetLimit extends Model
protected $casts
= [
- 'created_at' => 'datetime',
- 'updated_at' => 'datetime',
- 'start_date' => SeparateTimezoneCaster::class,
- 'end_date' => SeparateTimezoneCaster::class,
- 'auto_budget' => 'boolean',
- 'amount' => 'string',
+ 'created_at' => 'datetime',
+ 'updated_at' => 'datetime',
+ 'start_date' => SeparateTimezoneCaster::class,
+ 'end_date' => SeparateTimezoneCaster::class,
+ 'auto_budget' => 'boolean',
+ 'amount' => 'string',
'native_amount' => 'string',
];
protected $dispatchesEvents
diff --git a/app/Models/PiggyBank.php b/app/Models/PiggyBank.php
index 58c9a25697..3af9eabe22 100644
--- a/app/Models/PiggyBank.php
+++ b/app/Models/PiggyBank.php
@@ -44,19 +44,19 @@ class PiggyBank extends Model
protected $casts
= [
- 'created_at' => 'datetime',
- 'updated_at' => 'datetime',
- 'deleted_at' => 'datetime',
- 'start_date' => 'date',
- 'target_date' => 'date',
- 'order' => 'int',
- 'active' => 'boolean',
- 'encrypted' => 'boolean',
- 'target_amount' => 'string',
+ 'created_at' => 'datetime',
+ 'updated_at' => 'datetime',
+ 'deleted_at' => 'datetime',
+ 'start_date' => 'date',
+ 'target_date' => 'date',
+ 'order' => 'int',
+ 'active' => 'boolean',
+ 'encrypted' => 'boolean',
+ 'target_amount' => 'string',
'native_target_amount' => 'string',
];
- protected $fillable = ['name', 'order', 'target_amount', 'start_date', 'start_date_tz', 'target_date', 'target_date_tz', 'active', 'transaction_currency_id','native_target_amount'];
+ protected $fillable = ['name', 'order', 'target_amount', 'start_date', 'start_date_tz', 'target_date', 'target_date_tz', 'active', 'transaction_currency_id', 'native_target_amount'];
/**
* Route binder. Converts the key in the URL to the specified object (or throw 404).
diff --git a/app/Models/PiggyBankEvent.php b/app/Models/PiggyBankEvent.php
index 059768e70b..b1c6fc3e28 100644
--- a/app/Models/PiggyBankEvent.php
+++ b/app/Models/PiggyBankEvent.php
@@ -45,7 +45,7 @@ class PiggyBankEvent extends Model
'amount' => 'native_string',
];
- protected $fillable = ['piggy_bank_id', 'transaction_journal_id', 'date', 'date_tz', 'amount','native_amount'];
+ protected $fillable = ['piggy_bank_id', 'transaction_journal_id', 'date', 'date_tz', 'amount', 'native_amount'];
protected $hidden = ['amount_encrypted'];
diff --git a/app/Repositories/Account/OperationsRepository.php b/app/Repositories/Account/OperationsRepository.php
index 5f0bdca8bf..d7959127d8 100644
--- a/app/Repositories/Account/OperationsRepository.php
+++ b/app/Repositories/Account/OperationsRepository.php
@@ -28,12 +28,10 @@ use Carbon\Carbon;
use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Models\TransactionCurrency;
-use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Report\Summarizer\TransactionSummarizer;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Support\Collection;
-use Illuminate\Support\Facades\Log;
/**
* Class OperationsRepository
@@ -68,7 +66,7 @@ class OperationsRepository implements OperationsRepositoryInterface
return $collector->getExtractedJournals();
}
- public function setUser(null | Authenticatable | User $user): void
+ public function setUser(null|Authenticatable|User $user): void
{
if ($user instanceof User) {
$this->user = $user;
@@ -79,8 +77,8 @@ class OperationsRepository implements OperationsRepositoryInterface
{
$array = [];
foreach ($journals as $journal) {
- $currencyId = (int) $journal['currency_id'];
- $journalId = (int) $journal['transaction_journal_id'];
+ $currencyId = (int) $journal['currency_id'];
+ $journalId = (int) $journal['transaction_journal_id'];
$array[$currencyId] ??= [
'currency_id' => $journal['currency_id'],
'currency_name' => $journal['currency_name'],
@@ -132,8 +130,7 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $expense = null,
?TransactionCurrency $currency = null
- ): array
- {
+ ): array {
$journals = $this->getTransactionsForSum(TransactionTypeEnum::WITHDRAWAL->value, $start, $end, $accounts, $expense, $currency);
return $this->groupByCurrency($journals, 'negative');
@@ -150,8 +147,7 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $opposing = null,
?TransactionCurrency $currency = null
- ): array
- {
+ ): array {
$start->startOfDay();
$end->endOfDay();
@@ -184,14 +180,15 @@ class OperationsRepository implements OperationsRepositoryInterface
if (null !== $currency) {
$collector->setCurrency($currency);
}
- $journals = $collector->getExtractedJournals();
+ $journals = $collector->getExtractedJournals();
// same but for foreign currencies:
if (null !== $currency) {
/** @var GroupCollectorInterface $collector */
$collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([$type])->withAccountInformation()
- ->setForeignCurrency($currency);
+ ->setForeignCurrency($currency)
+ ;
if (TransactionTypeEnum::WITHDRAWAL->value === $type) {
if (null !== $accounts) {
$collector->setSourceAccounts($accounts);
@@ -209,10 +206,10 @@ class OperationsRepository implements OperationsRepositoryInterface
}
}
- $result = $collector->getExtractedJournals();
+ $result = $collector->getExtractedJournals();
// do not use array_merge because you want keys to overwrite (otherwise you get double results):
- $journals = $result + $journals;
+ $journals = $result + $journals;
}
return $journals;
@@ -221,6 +218,7 @@ class OperationsRepository implements OperationsRepositoryInterface
private function groupByCurrency(array $journals, string $direction): array
{
$summarizer = new TransactionSummarizer($this->user);
+
return $summarizer->groupByCurrencyId($journals, $direction);
}
@@ -233,8 +231,7 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $expense = null,
?TransactionCurrency $currency = null
- ): array
- {
+ ): array {
$journals = $this->getTransactionsForSum(TransactionTypeEnum::WITHDRAWAL->value, $start, $end, $accounts, $expense, $currency);
return $this->groupByDirection($journals, 'destination', 'negative');
@@ -243,6 +240,7 @@ class OperationsRepository implements OperationsRepositoryInterface
private function groupByDirection(array $journals, string $direction, string $method): array
{
$summarizer = new TransactionSummarizer($this->user);
+
return $summarizer->groupByDirection($journals, $method, $direction);
}
@@ -255,8 +253,7 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $expense = null,
?TransactionCurrency $currency = null
- ): array
- {
+ ): array {
$journals = $this->getTransactionsForSum(TransactionTypeEnum::WITHDRAWAL->value, $start, $end, $accounts, $expense, $currency);
return $this->groupByDirection($journals, 'source', 'negative');
@@ -271,8 +268,7 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $revenue = null,
?TransactionCurrency $currency = null
- ): array
- {
+ ): array {
$journals = $this->getTransactionsForSum(TransactionTypeEnum::DEPOSIT->value, $start, $end, $accounts, $revenue, $currency);
return $this->groupByCurrency($journals, 'positive');
@@ -287,8 +283,7 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $revenue = null,
?TransactionCurrency $currency = null
- ): array
- {
+ ): array {
$journals = $this->getTransactionsForSum(TransactionTypeEnum::DEPOSIT->value, $start, $end, $accounts, $revenue, $currency);
return $this->groupByDirection($journals, 'destination', 'positive');
@@ -303,8 +298,7 @@ class OperationsRepository implements OperationsRepositoryInterface
?Collection $accounts = null,
?Collection $revenue = null,
?TransactionCurrency $currency = null
- ): array
- {
+ ): array {
$journals = $this->getTransactionsForSum(TransactionTypeEnum::DEPOSIT->value, $start, $end, $accounts, $revenue, $currency);
return $this->groupByDirection($journals, 'source', 'positive');
@@ -325,7 +319,7 @@ class OperationsRepository implements OperationsRepositoryInterface
foreach ($journals as $journal) {
$return = $this->groupByEitherJournal($return, $journal);
}
- $final = [];
+ $final = [];
foreach ($return as $array) {
$array['difference_float'] = (float) $array['difference'];
$array['in_float'] = (float) $array['in'];
@@ -338,12 +332,12 @@ class OperationsRepository implements OperationsRepositoryInterface
private function groupByEitherJournal(array $return, array $journal): array
{
- $sourceId = $journal['source_account_id'];
- $destinationId = $journal['destination_account_id'];
- $currencyId = $journal['currency_id'];
- $sourceKey = sprintf('%d-%d', $currencyId, $sourceId);
- $destKey = sprintf('%d-%d', $currencyId, $destinationId);
- $amount = app('steam')->positive($journal['amount']);
+ $sourceId = $journal['source_account_id'];
+ $destinationId = $journal['destination_account_id'];
+ $currencyId = $journal['currency_id'];
+ $sourceKey = sprintf('%d-%d', $currencyId, $sourceId);
+ $destKey = sprintf('%d-%d', $currencyId, $destinationId);
+ $amount = app('steam')->positive($journal['amount']);
// source first
$return[$sourceKey] ??= [
@@ -360,7 +354,7 @@ class OperationsRepository implements OperationsRepositoryInterface
];
// dest next:
- $return[$destKey] ??= [
+ $return[$destKey] ??= [
'id' => (string) $destinationId,
'name' => $journal['destination_account_name'],
'difference' => '0',
@@ -378,15 +372,15 @@ class OperationsRepository implements OperationsRepositoryInterface
$return[$sourceKey]['difference'] = bcadd($return[$sourceKey]['out'], $return[$sourceKey]['in']);
// destination account? money comes in:
- $return[$destKey]['in'] = bcadd($return[$destKey]['in'], $amount);
- $return[$destKey]['difference'] = bcadd($return[$destKey]['out'], $return[$destKey]['in']);
+ $return[$destKey]['in'] = bcadd($return[$destKey]['in'], $amount);
+ $return[$destKey]['difference'] = bcadd($return[$destKey]['out'], $return[$destKey]['in']);
// foreign currency
if (null !== $journal['foreign_currency_id'] && null !== $journal['foreign_amount']) {
- $currencyId = $journal['foreign_currency_id'];
- $sourceKey = sprintf('%d-%d', $currencyId, $sourceId);
- $destKey = sprintf('%d-%d', $currencyId, $destinationId);
- $amount = app('steam')->positive($journal['foreign_amount']);
+ $currencyId = $journal['foreign_currency_id'];
+ $sourceKey = sprintf('%d-%d', $currencyId, $sourceId);
+ $destKey = sprintf('%d-%d', $currencyId, $destinationId);
+ $amount = app('steam')->positive($journal['foreign_amount']);
// same as above:
// source first
@@ -404,7 +398,7 @@ class OperationsRepository implements OperationsRepositoryInterface
];
// dest next:
- $return[$destKey] ??= [
+ $return[$destKey] ??= [
'id' => (string) $destinationId,
'name' => $journal['destination_account_name'],
'difference' => '0',
@@ -421,8 +415,8 @@ class OperationsRepository implements OperationsRepositoryInterface
$return[$sourceKey]['difference'] = bcadd($return[$sourceKey]['out'], $return[$sourceKey]['in']);
// destination account? money comes in:
- $return[$destKey]['in'] = bcadd($return[$destKey]['in'], $amount);
- $return[$destKey]['difference'] = bcadd($return[$destKey]['out'], $return[$destKey]['in']);
+ $return[$destKey]['in'] = bcadd($return[$destKey]['in'], $amount);
+ $return[$destKey]['difference'] = bcadd($return[$destKey]['out'], $return[$destKey]['in']);
}
return $return;
diff --git a/app/Repositories/Bill/BillRepository.php b/app/Repositories/Bill/BillRepository.php
index 185fc700be..a92ff5af30 100644
--- a/app/Repositories/Bill/BillRepository.php
+++ b/app/Repositories/Bill/BillRepository.php
@@ -586,7 +586,7 @@ class BillRepository implements BillRepositoryInterface
$minField = $convertToNative && $bill->transactionCurrency->id !== $default->id ? 'native_amount_min' : 'amount_min';
$maxField = $convertToNative && $bill->transactionCurrency->id !== $default->id ? 'native_amount_max' : 'amount_max';
- Log::debug(sprintf('min field is %s, max field is %s', $minField, $maxField));
+ Log::debug(sprintf('min field is %s, max field is %s', $minField, $maxField));
if ($total > 0) {
$currency = $convertToNative && $bill->transactionCurrency->id !== $default->id ? $default : $bill->transactionCurrency;
diff --git a/app/Repositories/Budget/NoBudgetRepository.php b/app/Repositories/Budget/NoBudgetRepository.php
index 21dcae270f..7e50046aca 100644
--- a/app/Repositories/Budget/NoBudgetRepository.php
+++ b/app/Repositories/Budget/NoBudgetRepository.php
@@ -29,12 +29,10 @@ use FireflyIII\Enums\TransactionTypeEnum;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Models\TransactionType;
-use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Report\Summarizer\TransactionSummarizer;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Support\Collection;
-use Illuminate\Support\Facades\Log;
/**
* Class NoBudgetRepository
@@ -93,7 +91,7 @@ class NoBudgetRepository implements NoBudgetRepositoryInterface
public function sumExpenses(Carbon $start, Carbon $end, ?Collection $accounts = null, ?TransactionCurrency $currency = null): array
{
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionType::WITHDRAWAL]);
if (null !== $accounts && $accounts->count() > 0) {
@@ -104,8 +102,9 @@ class NoBudgetRepository implements NoBudgetRepositoryInterface
}
$collector->withoutBudget();
$collector->withBudgetInformation();
- $journals = $collector->getExtractedJournals();
+ $journals = $collector->getExtractedJournals();
$summarizer = new TransactionSummarizer($this->user);
+
return $summarizer->groupByCurrencyId($journals);
}
}
diff --git a/app/Repositories/Budget/OperationsRepository.php b/app/Repositories/Budget/OperationsRepository.php
index eb3e82688c..bc0e78304c 100644
--- a/app/Repositories/Budget/OperationsRepository.php
+++ b/app/Repositories/Budget/OperationsRepository.php
@@ -218,10 +218,10 @@ class OperationsRepository implements OperationsRepositoryInterface
// 2024-12-24 disable the exclusion for now.
- $repository = app(AccountRepositoryInterface::class);
+ $repository = app(AccountRepositoryInterface::class);
$repository->setUser($this->user);
- $subset = $repository->getAccountsByType(config('firefly.valid_liabilities'));
- $selection = new Collection();
+ $subset = $repository->getAccountsByType(config('firefly.valid_liabilities'));
+ $selection = new Collection();
/** @var Account $account */
foreach ($subset as $account) {
@@ -231,7 +231,7 @@ class OperationsRepository implements OperationsRepositoryInterface
}
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)
->setRange($start, $end)
// ->excludeDestinationAccounts($selection)
@@ -249,13 +249,14 @@ class OperationsRepository implements OperationsRepositoryInterface
$collector->setNormalCurrency($currency);
}
$collector->setBudgets($budgets);
- $journals = $collector->getExtractedJournals();
+ $journals = $collector->getExtractedJournals();
// same but for transactions in the foreign currency:
if (null !== $currency) {
Log::debug('STOP looking for transactions in the foreign currency.');
}
$summarizer = new TransactionSummarizer($this->user);
+
return $summarizer->groupByCurrencyId($journals);
}
}
diff --git a/app/Repositories/Category/NoCategoryRepository.php b/app/Repositories/Category/NoCategoryRepository.php
index 0d62a6b979..6cc823a29d 100644
--- a/app/Repositories/Category/NoCategoryRepository.php
+++ b/app/Repositories/Category/NoCategoryRepository.php
@@ -27,12 +27,10 @@ namespace FireflyIII\Repositories\Category;
use Carbon\Carbon;
use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Models\TransactionType;
-use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Report\Summarizer\TransactionSummarizer;
use FireflyIII\User;
use Illuminate\Contracts\Auth\Authenticatable;
use Illuminate\Support\Collection;
-use Illuminate\Support\Facades\Log;
/**
* Class NoCategoryRepository
@@ -146,14 +144,15 @@ class NoCategoryRepository implements NoCategoryRepositoryInterface
public function sumExpenses(Carbon $start, Carbon $end, ?Collection $accounts = null): array
{
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionType::WITHDRAWAL])->withoutCategory();
if (null !== $accounts && $accounts->count() > 0) {
$collector->setAccounts($accounts);
}
- $journals = $collector->getExtractedJournals();
+ $journals = $collector->getExtractedJournals();
$summarizer = new TransactionSummarizer($this->user);
+
return $summarizer->groupByCurrencyId($journals);
}
diff --git a/app/Repositories/Category/OperationsRepository.php b/app/Repositories/Category/OperationsRepository.php
index dbe1ff6660..26db0fba10 100644
--- a/app/Repositories/Category/OperationsRepository.php
+++ b/app/Repositories/Category/OperationsRepository.php
@@ -328,7 +328,7 @@ class OperationsRepository implements OperationsRepositoryInterface
public function sumExpenses(Carbon $start, Carbon $end, ?Collection $accounts = null, ?Collection $categories = null): array
{
/** @var GroupCollectorInterface $collector */
- $collector = app(GroupCollectorInterface::class);
+ $collector = app(GroupCollectorInterface::class);
$collector->setUser($this->user)->setRange($start, $end)->setTypes([TransactionTypeEnum::WITHDRAWAL->value]);
if (null !== $accounts && $accounts->count() > 0) {
@@ -339,8 +339,9 @@ class OperationsRepository implements OperationsRepositoryInterface
}
$collector->setCategories($categories);
$collector->withCategoryInformation();
- $journals = $collector->getExtractedJournals();
+ $journals = $collector->getExtractedJournals();
$summarizer = new TransactionSummarizer($this->user);
+
return $summarizer->groupByCurrencyId($journals);
}
diff --git a/app/Support/Amount.php b/app/Support/Amount.php
index 9d21ef4e67..ac4dc9cbe0 100644
--- a/app/Support/Amount.php
+++ b/app/Support/Amount.php
@@ -85,16 +85,16 @@ class Amount
*/
public function getAmountFromJournalObject(TransactionJournal $journal): string
{
- $convertToNative = $this->convertToNative();
- $currency = $this->getDefaultCurrency();
- $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
+ $convertToNative = $this->convertToNative();
+ $currency = $this->getDefaultCurrency();
+ $field = $convertToNative && $currency->id !== $journal->transaction_currency_id ? 'native_amount' : 'amount';
/** @var null|Transaction $sourceTransaction */
$sourceTransaction = $journal->transactions()->where('amount', '<', 0)->first();
if (null === $sourceTransaction) {
return '0';
}
- $amount = $sourceTransaction->{$field} ?? '0';
+ $amount = $sourceTransaction->{$field} ?? '0';
if ((int) $sourceTransaction->foreign_currency_id === $currency->id) {
// use foreign amount instead!
$amount = (string) $sourceTransaction->foreign_amount; // hard coded to be foreign amount.
@@ -113,15 +113,15 @@ class Amount
*/
public function formatFlat(string $symbol, int $decimalPlaces, string $amount, ?bool $coloured = null): string
{
- $locale = app('steam')->getLocale();
- $rounded = app('steam')->bcround($amount, $decimalPlaces);
+ $locale = app('steam')->getLocale();
+ $rounded = app('steam')->bcround($amount, $decimalPlaces);
$coloured ??= true;
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$fmt->setSymbol(\NumberFormatter::CURRENCY_SYMBOL, $symbol);
$fmt->setAttribute(\NumberFormatter::MIN_FRACTION_DIGITS, $decimalPlaces);
$fmt->setAttribute(\NumberFormatter::MAX_FRACTION_DIGITS, $decimalPlaces);
- $result = (string) $fmt->format((float) $rounded); // intentional float
+ $result = (string) $fmt->format((float) $rounded); // intentional float
if (true === $coloured) {
if (1 === bccomp($rounded, '0')) {
@@ -166,12 +166,13 @@ class Amount
return $this->getDefaultCurrencyByUserGroup($user->userGroup);
}
}
+
return $this->getSystemCurrency();
}
public function getDefaultCurrencyByUserGroup(UserGroup $userGroup): TransactionCurrency
{
- $cache = new CacheProperties();
+ $cache = new CacheProperties();
$cache->addProperty('getDefaultCurrencyByGroup');
$cache->addProperty($userGroup->id);
if ($cache->has()) {
@@ -234,20 +235,20 @@ class Amount
private function getLocaleInfo(): array
{
// get config from preference, not from translation:
- $locale = app('steam')->getLocale();
- $array = app('steam')->getLocaleArray($locale);
+ $locale = app('steam')->getLocale();
+ $array = app('steam')->getLocaleArray($locale);
setlocale(LC_MONETARY, $array);
- $info = localeconv();
+ $info = localeconv();
// correct variables
- $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
- $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
+ $info['n_cs_precedes'] = $this->getLocaleField($info, 'n_cs_precedes');
+ $info['p_cs_precedes'] = $this->getLocaleField($info, 'p_cs_precedes');
- $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
- $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
+ $info['n_sep_by_space'] = $this->getLocaleField($info, 'n_sep_by_space');
+ $info['p_sep_by_space'] = $this->getLocaleField($info, 'p_sep_by_space');
- $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
+ $fmt = new \NumberFormatter($locale, \NumberFormatter::CURRENCY);
$info['mon_decimal_point'] = $fmt->getSymbol(\NumberFormatter::MONETARY_SEPARATOR_SYMBOL);
$info['mon_thousands_sep'] = $fmt->getSymbol(\NumberFormatter::MONETARY_GROUPING_SEPARATOR_SYMBOL);
@@ -270,7 +271,7 @@ class Amount
public static function getAmountJsConfig(bool $sepBySpace, int $signPosn, string $sign, bool $csPrecedes): string
{
// negative first:
- $space = ' ';
+ $space = ' ';
// require space between symbol and amount?
if (false === $sepBySpace) {
@@ -279,11 +280,11 @@ class Amount
// there are five possible positions for the "+" or "-" sign (if it is even used)
// pos_a and pos_e could be the ( and ) symbol.
- $posA = ''; // before everything
- $posB = ''; // before currency symbol
- $posC = ''; // after currency symbol
- $posD = ''; // before amount
- $posE = ''; // after everything
+ $posA = ''; // before everything
+ $posB = ''; // before currency symbol
+ $posC = ''; // after currency symbol
+ $posD = ''; // before amount
+ $posE = ''; // after everything
// format would be (currency before amount)
// AB%sC_D%vE
@@ -325,11 +326,11 @@ class Amount
}
// default is amount before currency
- $format = $posA . $posD . '%v' . $space . $posB . '%s' . $posC . $posE;
+ $format = $posA.$posD.'%v'.$space.$posB.'%s'.$posC.$posE;
if ($csPrecedes) {
// alternative is currency before amount
- $format = $posA . $posB . '%s' . $posC . $space . $posD . '%v' . $posE;
+ $format = $posA.$posB.'%s'.$posC.$space.$posD.'%v'.$posE;
}
return $format;
diff --git a/app/Support/Navigation.php b/app/Support/Navigation.php
index a0e3b458b6..9aa6f13b0f 100644
--- a/app/Support/Navigation.php
+++ b/app/Support/Navigation.php
@@ -507,12 +507,12 @@ class Navigation
$diff = $start->diffInMonths($end, true);
Log::debug(sprintf('preferredCarbonFormat(%s, %s) = %f', $start->format('Y-m-d'), $end->format('Y-m-d'), $diff));
if ($diff >= 1.001) {
-// Log::debug(sprintf('Return Y-m because %s', $diff));
+ // Log::debug(sprintf('Return Y-m because %s', $diff));
$format = 'Y-m';
}
if ($diff >= 12.001) {
-// Log::debug(sprintf('Return Y because %s', $diff));
+ // Log::debug(sprintf('Return Y because %s', $diff));
$format = 'Y';
}
diff --git a/app/Support/Report/Summarizer/TransactionSummarizer.php b/app/Support/Report/Summarizer/TransactionSummarizer.php
index d6cbbf04f6..17368c53b8 100644
--- a/app/Support/Report/Summarizer/TransactionSummarizer.php
+++ b/app/Support/Report/Summarizer/TransactionSummarizer.php
@@ -1,4 +1,5 @@
convertToNative) {
// if convert to native, use the native amount yes or no?
$useNative = $this->default->id !== (int) $journal['currency_id'];
@@ -83,11 +84,11 @@ class TransactionSummarizer
$currencyDecimalPlaces = $journal['foreign_currency_decimal_places'];
}
}
- if(!$this->convertToNative) {
+ if (!$this->convertToNative) {
// default to the normal amount, but also
}
$amount = (string) ($journal[$field] ?? '0');
- $array[$currencyId] ??= [
+ $array[$currencyId] ??= [
'sum' => '0',
'currency_id' => $currencyId,
'currency_name' => $currencyName,
@@ -95,14 +96,16 @@ class TransactionSummarizer
'currency_code' => $currencyCode,
'currency_decimal_places' => $currencyDecimalPlaces,
];
- $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->$method($amount));
+ $array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->{$method}($amount));
Log::debug(sprintf('Journal #%d adds amount %s %s', $journal['transaction_journal_id'], $currencyCode, $amount));
}
Log::debug('End of sumExpenses.', $array);
+
return $array;
}
- public function groupByDirection(array $journals, string $method, string $direction): array {
+ public function groupByDirection(array $journals, string $method, string $direction): array
+ {
$array = [];
$idKey = sprintf('%s_account_id', $direction);
@@ -136,7 +139,7 @@ class TransactionSummarizer
if ($convertToNative && $journal['currency_id'] !== $default->id && $default->id === $journal['foreign_currency_id']) {
$field = 'foreign_amount';
}
- $key = sprintf('%s-%s', $journal[$idKey], $currencyId);
+ $key = sprintf('%s-%s', $journal[$idKey], $currencyId);
// sum it all up or create a new array.
$array[$key] ??= [
'id' => $journal[$idKey],
@@ -150,7 +153,7 @@ class TransactionSummarizer
];
// add the data from the $field to the array.
- $array[$key]['sum'] = bcadd($array[$key]['sum'], app('steam')->{$method}((string) ($journal[$field] ?? '0'))); // @phpstan-ignore-line
+ $array[$key]['sum'] = bcadd($array[$key]['sum'], app('steam')->{$method}((string) ($journal[$field] ?? '0'))); // @phpstan-ignore-line
Log::debug(sprintf('Field for transaction #%d is "%s" (%s). Sum: %s', $journal['transaction_group_id'], $currencyCode, $field, $array[$key]['sum']));
// also do foreign amount, but only when convertToNative is false (otherwise we have it already)
@@ -158,7 +161,7 @@ class TransactionSummarizer
if ((!$convertToNative || $journal['foreign_currency_id'] !== $default->id) && 0 !== (int) $journal['foreign_currency_id']) {
Log::debug(sprintf('Use foreign amount from transaction #%d: %s %s. Sum: %s', $journal['transaction_group_id'], $currencyCode, $journal['foreign_amount'], $array[$key]['sum']));
$key = sprintf('%s-%s', $journal[$idKey], $journal['foreign_currency_id']);
- $array[$key] ??= [
+ $array[$key] ??= [
'id' => $journal[$idKey],
'name' => $journal[$nameKey],
'sum' => '0',
@@ -174,5 +177,4 @@ class TransactionSummarizer
return $array;
}
-
}
diff --git a/app/Transformers/AccountTransformer.php b/app/Transformers/AccountTransformer.php
index a322dd9cbd..70212444b4 100644
--- a/app/Transformers/AccountTransformer.php
+++ b/app/Transformers/AccountTransformer.php
@@ -58,7 +58,7 @@ class AccountTransformer extends AbstractTransformer
// get account type:
$fullType = $account->accountType->type;
- $accountType = (string) config(sprintf( 'firefly.shortNamesByFullName.%s', $fullType));
+ $accountType = (string) config(sprintf('firefly.shortNamesByFullName.%s', $fullType));
$liabilityType = (string) config(sprintf('firefly.shortLiabilityNameByFullName.%s', $fullType));
$liabilityType = '' === $liabilityType ? null : strtolower($liabilityType);
$liabilityDirection = $this->repository->getMetaValue($account, 'liability_direction');
diff --git a/changelog.md b/changelog.md
index a19fb17aa2..5d416e3168 100644
--- a/changelog.md
+++ b/changelog.md
@@ -16,9 +16,9 @@ This project adheres to [Semantic Versioning](http://semver.org/).
- [Issue 7945](https://github.com/firefly-iii/firefly-iii/issues/7945) ("Rules" that only trigger manually) reported by @SekoiaTree
- [Issue 6760](https://github.com/firefly-iii/firefly-iii/issues/6760) (Add a new trigger for automated rules) reported by @Gsyltc
- [Issue 6557](https://github.com/firefly-iii/firefly-iii/issues/6557) (Piggy Banks - Draw Funds from Multiple Accounts) reported by @BugPhobic
-- #5532
-- #6314
-- #9586
+- [Issue 5532](https://github.com/firefly-iii/firefly-iii/issues/5532) (Asset prices and exchange rates) reported by @svozniuk
+- [Issue 6314](https://github.com/firefly-iii/firefly-iii/issues/6314) (Currencies and exchange rates) reported by @JC5
+- [Issue 9586](https://github.com/firefly-iii/firefly-iii/issues/9586) (Non en_US translated string in sign-up mail) reported by @benni347
### Changed
diff --git a/composer.lock b/composer.lock
index 87535dbbba..c28f738963 100644
--- a/composer.lock
+++ b/composer.lock
@@ -2614,16 +2614,16 @@
},
{
"name": "league/commonmark",
- "version": "2.6.0",
+ "version": "2.6.1",
"source": {
"type": "git",
"url": "https://github.com/thephpleague/commonmark.git",
- "reference": "d150f911e0079e90ae3c106734c93137c184f932"
+ "reference": "d990688c91cedfb69753ffc2512727ec646df2ad"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/thephpleague/commonmark/zipball/d150f911e0079e90ae3c106734c93137c184f932",
- "reference": "d150f911e0079e90ae3c106734c93137c184f932",
+ "url": "https://api.github.com/repos/thephpleague/commonmark/zipball/d990688c91cedfb69753ffc2512727ec646df2ad",
+ "reference": "d990688c91cedfb69753ffc2512727ec646df2ad",
"shasum": ""
},
"require": {
@@ -2717,7 +2717,7 @@
"type": "tidelift"
}
],
- "time": "2024-12-07T15:34:16+00:00"
+ "time": "2024-12-29T14:10:59+00:00"
},
{
"name": "league/config",
@@ -10193,20 +10193,20 @@
},
{
"name": "barryvdh/laravel-ide-helper",
- "version": "v3.3.0",
+ "version": "v3.4.0",
"source": {
"type": "git",
"url": "https://github.com/barryvdh/laravel-ide-helper.git",
- "reference": "b7675670f75914bf34afdea52a6c2fe3781f7c44"
+ "reference": "2a41415f01bf3c409d200f6cdd940c1e7d86cfd3"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/barryvdh/laravel-ide-helper/zipball/b7675670f75914bf34afdea52a6c2fe3781f7c44",
- "reference": "b7675670f75914bf34afdea52a6c2fe3781f7c44",
+ "url": "https://api.github.com/repos/barryvdh/laravel-ide-helper/zipball/2a41415f01bf3c409d200f6cdd940c1e7d86cfd3",
+ "reference": "2a41415f01bf3c409d200f6cdd940c1e7d86cfd3",
"shasum": ""
},
"require": {
- "barryvdh/reflection-docblock": "^2.1.2",
+ "barryvdh/reflection-docblock": "^2.2",
"composer/class-map-generator": "^1.0",
"ext-json": "*",
"illuminate/console": "^11.15",
@@ -10239,7 +10239,7 @@
]
},
"branch-alias": {
- "dev-master": "3.2-dev"
+ "dev-master": "3.4-dev"
}
},
"autoload": {
@@ -10271,7 +10271,7 @@
],
"support": {
"issues": "https://github.com/barryvdh/laravel-ide-helper/issues",
- "source": "https://github.com/barryvdh/laravel-ide-helper/tree/v3.3.0"
+ "source": "https://github.com/barryvdh/laravel-ide-helper/tree/v3.4.0"
},
"funding": [
{
@@ -10283,7 +10283,7 @@
"type": "github"
}
],
- "time": "2024-12-18T08:24:19+00:00"
+ "time": "2024-12-29T12:10:58+00:00"
},
{
"name": "barryvdh/reflection-docblock",
diff --git a/config/firefly.php b/config/firefly.php
index 4f59a04af3..0f7ff0fc66 100644
--- a/config/firefly.php
+++ b/config/firefly.php
@@ -81,7 +81,7 @@ return [
'running_balance_column' => env('USE_RUNNING_BALANCE', false),
// see cer.php for exchange rates feature flag.
],
- 'version' => 'develop/2024-12-28',
+ 'version' => 'develop/2024-12-30',
'api_version' => '2.1.0', // field is no longer used.
'db_version' => 25,
diff --git a/resources/assets/v1/src/locales/de.json b/resources/assets/v1/src/locales/de.json
index 46ba8f5c04..46b17f4116 100644
--- a/resources/assets/v1/src/locales/de.json
+++ b/resources/assets/v1/src/locales/de.json
@@ -133,7 +133,7 @@
"header_exchange_rates": "Wechselkurse",
"exchange_rates_intro": "Firefly III unterst\u00fctzt das Herunterladen und Verwenden von Wechselkursen. Lesen Sie mehr dar\u00fcber in der Dokumentation<\/a>.",
"exchange_rates_from_to": "Zwischen {from} und {to} (und umgekehrt)",
- "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
+ "exchange_rates_intro_rates": "Firefly III verwendet die folgenden Wechselkurse. Der Kehrwert wird automatisch berechnet, wenn er nicht angegeben wurde. Wenn f\u00fcr das Datum der Transaktion kein Wechselkurs vorhanden ist, sucht Firefly III in der Vergangenheit nach einem Kurs. Wenn keine vorhanden sind, wird der Kurs \u201e1\u201c verwendet.",
"header_exchange_rates_rates": "Wechselkurse",
"header_exchange_rates_table": "Tabelle mit Wechselkursen",
"help_rate_form": "An diesem Tag, wie viele {to} werden Sie f\u00fcr {from} bekommen?",
diff --git a/resources/assets/v1/src/locales/nl.json b/resources/assets/v1/src/locales/nl.json
index 2c3f7a6ae4..ae4088faf6 100644
--- a/resources/assets/v1/src/locales/nl.json
+++ b/resources/assets/v1/src/locales/nl.json
@@ -36,7 +36,7 @@
"is_reconciled_fields_dropped": "Omdat deze transactie al is afgestemd, kan je het bedrag noch de rekeningen wijzigen.",
"tags": "Tags",
"no_budget": "(geen budget)",
- "no_bill": "(no subscription)",
+ "no_bill": "(geen abonnement)",
"category": "Categorie",
"attachments": "Bijlagen",
"notes": "Notities",
@@ -52,7 +52,7 @@
"destination_account_reconciliation": "Je kan de doelrekening van een afstemming niet wijzigen.",
"source_account_reconciliation": "Je kan de bronrekening van een afstemming niet wijzigen.",
"budget": "Budget",
- "bill": "Subscription",
+ "bill": "Abonnement",
"you_create_withdrawal": "Je maakt een uitgave.",
"you_create_transfer": "Je maakt een overschrijving.",
"you_create_deposit": "Je maakt inkomsten.",
@@ -133,7 +133,7 @@
"header_exchange_rates": "Wisselkoersen",
"exchange_rates_intro": "Firefly III kan wisselkoersen downloaden en gebruiken. Lees hier meer over in de documentatie<\/a>.",
"exchange_rates_from_to": "Tussen {from} en {to} (en andersom)",
- "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
+ "exchange_rates_intro_rates": "Firefly III gebruikt de volgende wisselkoersen. De inverse berekent zichzelf als deze niet is opgegeven. Als er geen wisselkoers bestaat voor de datum van de transactie, gaat Firefly III terug in de tijd om er een te vinden. Als er geen aanwezig is, zal de koers \"1\" gebruikt worden.",
"header_exchange_rates_rates": "Wisselkoersen",
"header_exchange_rates_table": "Tabel met wisselkoersen",
"help_rate_form": "Hoeveel {to} krijg je op deze dag voor \u00e9\u00e9n {from}?",
diff --git a/tests/integration/TestCase.php b/tests/integration/TestCase.php
index bb85425ea0..6be5deece5 100644
--- a/tests/integration/TestCase.php
+++ b/tests/integration/TestCase.php
@@ -54,9 +54,10 @@ abstract class TestCase extends BaseTestCase
protected function createAuthenticatedUser(): User
{
$group = UserGroup::create(['title' => 'test@email.com']);
+
return User::create([
- 'email' => 'test@email.com',
- 'password' => 'password',
+ 'email' => 'test@email.com',
+ 'password' => 'password',
'user_group_id' => $group->id,
]);
}
From 46a200aa1fa592bd35685b01a38119d391d637df Mon Sep 17 00:00:00 2001
From: James Cole
Date: Mon, 30 Dec 2024 07:30:23 +0100
Subject: [PATCH 162/167] Fix broken variable.
---
app/Api/V1/Controllers/Autocomplete/AccountController.php | 5 ++---
1 file changed, 2 insertions(+), 3 deletions(-)
diff --git a/app/Api/V1/Controllers/Autocomplete/AccountController.php b/app/Api/V1/Controllers/Autocomplete/AccountController.php
index fdbf680486..cfd335e135 100644
--- a/app/Api/V1/Controllers/Autocomplete/AccountController.php
+++ b/app/Api/V1/Controllers/Autocomplete/AccountController.php
@@ -29,7 +29,6 @@ use FireflyIII\Api\V1\Requests\Autocomplete\AutocompleteRequest;
use FireflyIII\Enums\AccountTypeEnum;
use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Models\Account;
-use FireflyIII\Models\AccountType;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
use FireflyIII\Support\Facades\Steam;
use FireflyIII\Support\Http\Api\AccountFilter;
@@ -86,7 +85,7 @@ class AccountController extends Controller
foreach ($result as $account) {
$nameWithBalance = $account->name;
$currency = $this->repository->getAccountCurrency($account) ?? $this->defaultCurrency;
-
+ $useCurrency = $currency;
if (in_array($account->accountType->type, $this->balanceTypes, true)) {
$balance = Steam::finalAccountBalance($account, $date);
$key = $this->convertToNative && $currency->id !== $this->defaultCurrency->id ? 'native_balance' : 'balance';
@@ -116,7 +115,7 @@ class AccountController extends Controller
usort(
$return,
static function (array $left, array $right) {
- $order = [AccountType::ASSET, AccountType::REVENUE, AccountType::EXPENSE];
+ $order = [AccountTypeEnum::ASSET->value, AccountTypeEnum::REVENUE->value, AccountTypeEnum::EXPENSE->value];
$posA = (int) array_search($left['type'], $order, true);
$posB = (int) array_search($right['type'], $order, true);
From 760da08ab75244ae04bdb16e1085e617bb6de54d Mon Sep 17 00:00:00 2001
From: James Cole
Date: Mon, 30 Dec 2024 07:36:22 +0100
Subject: [PATCH 163/167] Update exchange rates.
---
config/cer.php | 53 +++++++++++++++++++++++++-------------------------
1 file changed, 27 insertions(+), 26 deletions(-)
diff --git a/config/cer.php b/config/cer.php
index ddfde2d15b..6ef20aebfb 100644
--- a/config/cer.php
+++ b/config/cer.php
@@ -28,47 +28,48 @@ return [
'download_enabled' => env('ENABLE_EXTERNAL_RATES', false),
// if currencies are added, default rates must be added as well!
- // last exchange rate update: 6-6-2022
+ // last exchange rate update: 2024-12-30
// source: https://www.xe.com/currencyconverter/
- 'date' => '2022-06-06',
+ 'date' => '2024-12-30',
// all rates are from EUR to $currency:
'rates' => [
// europa
'EUR' => 1,
- 'HUF' => 387.9629,
- 'GBP' => 0.85420754,
- 'UAH' => 31.659752,
- 'PLN' => 4.581788,
- 'TRY' => 17.801397,
- 'DKK' => 7.4389753,
+ 'HUF' => 410.79798,
+ 'GBP' => 0.82858703,
+ 'UAH' => 43.485934,
+ 'PLN' => 4.2708542,
+ 'TRY' => 36.804124,
+ 'DKK' => 7.4591,
+ 'RON' => 4.9768699,
// Americas
- 'USD' => 1.0722281,
- 'BRL' => 5.0973173,
- 'CAD' => 1.3459969,
- 'MXN' => 20.899824,
+ 'USD' => 1.0430046,
+ 'BRL' => 6.4639113,
+ 'CAD' => 1.5006908,
+ 'MXN' => 21.249542,
// Oceania currencies
- 'IDR' => 15466.299,
- 'AUD' => 1.4838549,
- 'NZD' => 1.6425829,
+ 'IDR' => 16860.057,
+ 'AUD' => 1.6705648,
+ 'NZD' => 1.8436945,
// africa
- 'EGP' => 19.99735,
- 'MAD' => 10.573307,
- 'ZAR' => 16.413167,
+ 'EGP' => 53.038174,
+ 'MAD' => 10.521629,
+ 'ZAR' => 19.460263,
// asia
- 'JPY' => 140.15257,
- 'RMB' => 7.1194265,
- 'CNY' => 1,
- 'RUB' => 66.000895,
- 'INR' => 83.220481,
+ 'JPY' => 164.74767,
+ 'RMB' => 7.6138994,
+ 'CNY' => 7.6138994,
+ 'RUB' => 108.56771,
+ 'INR' => 89.157391,
// int
- 'ILS' => 3.5712508,
- 'CHF' => 1.0323891,
- 'HRK' => 7.5220845,
+ 'ILS' => 3.8428028,
+ 'CHF' => 0.94044969,
+ 'HRK' => 7.5345, // replaced by EUR
],
];
From 62f4da6063e8bb7e5c650036a1a0b9cb72189eaa Mon Sep 17 00:00:00 2001
From: James Cole
Date: Mon, 30 Dec 2024 10:51:34 +0100
Subject: [PATCH 164/167] Update available budgets code.
---
app/Handlers/Events/Model/BudgetLimitHandler.php | 1 +
.../Observer/AvailableBudgetObserver.php | 2 +-
.../Controllers/Account/CreateController.php | 3 +--
app/Http/Controllers/Account/EditController.php | 2 +-
.../Controllers/Account/ReconcileController.php | 4 ++--
app/Http/Controllers/Account/ShowController.php | 4 ++--
app/Http/Controllers/Bill/CreateController.php | 2 +-
app/Http/Controllers/Bill/EditController.php | 7 +++----
app/Http/Controllers/Budget/CreateController.php | 3 +--
app/Http/Controllers/Budget/EditController.php | 3 +--
app/Http/Controllers/Budget/IndexController.php | 12 +++++++-----
app/Http/Controllers/Chart/AccountController.php | 6 ++----
app/Http/Controllers/Chart/BudgetController.php | 2 +-
app/Http/Controllers/Controller.php | 2 +-
app/Http/Controllers/Json/BoxController.php | 16 +++++++---------
.../Controllers/Json/ReconcileController.php | 4 ++--
app/Http/Controllers/PreferencesController.php | 7 +++++++
.../Controllers/Recurring/CreateController.php | 4 ++--
.../Transaction/ConvertController.php | 6 ++----
.../Controllers/Transaction/CreateController.php | 2 +-
.../Controllers/Transaction/EditController.php | 2 +-
app/Http/Middleware/Range.php | 5 +++--
app/Http/Requests/PiggyBankStoreRequest.php | 3 ++-
app/Http/Requests/PiggyBankUpdateRequest.php | 3 ++-
app/Models/RecurrenceRepetition.php | 8 ++++----
app/Repositories/Bill/BillRepository.php | 2 +-
.../Budget/AvailableBudgetRepository.php | 9 +++++----
.../Report/Summarizer/TransactionSummarizer.php | 2 +-
28 files changed, 65 insertions(+), 61 deletions(-)
diff --git a/app/Handlers/Events/Model/BudgetLimitHandler.php b/app/Handlers/Events/Model/BudgetLimitHandler.php
index 6164460cdd..a0a60b60e1 100644
--- a/app/Handlers/Events/Model/BudgetLimitHandler.php
+++ b/app/Handlers/Events/Model/BudgetLimitHandler.php
@@ -143,6 +143,7 @@ class BudgetLimitHandler
);
$availableBudget->save();
Log::debug(sprintf('ID of new AB is #%d', $availableBudget->id));
+ $this->calculateAmount($availableBudget);
}
}
diff --git a/app/Handlers/Observer/AvailableBudgetObserver.php b/app/Handlers/Observer/AvailableBudgetObserver.php
index 8644bac575..ec23dd7df6 100644
--- a/app/Handlers/Observer/AvailableBudgetObserver.php
+++ b/app/Handlers/Observer/AvailableBudgetObserver.php
@@ -33,7 +33,7 @@ class AvailableBudgetObserver
{
public function created(AvailableBudget $availableBudget): void
{
- Log::debug('Observe "created" of an available budget.');
+ // Log::debug('Observe "created" of an available budget.');
$this->updateNativeAmount($availableBudget);
}
diff --git a/app/Http/Controllers/Account/CreateController.php b/app/Http/Controllers/Account/CreateController.php
index be9260c369..20dec447c6 100644
--- a/app/Http/Controllers/Account/CreateController.php
+++ b/app/Http/Controllers/Account/CreateController.php
@@ -76,7 +76,6 @@ class CreateController extends Controller
*/
public function create(Request $request, string $objectType)
{
- $defaultCurrency = app('amount')->getDefaultCurrency();
$subTitleIcon = config(sprintf('firefly.subIconsByIdentifier.%s', $objectType));
$subTitle = (string) trans(sprintf('firefly.make_new_%s_account', $objectType));
$roles = $this->getRoles();
@@ -106,7 +105,7 @@ class CreateController extends Controller
$request->session()->flash(
'preFilled',
[
- 'currency_id' => $defaultCurrency->id,
+ 'currency_id' => $this->defaultCurrency->id,
'include_net_worth' => $hasOldInput ? (bool) $request->old('include_net_worth') : true,
]
);
diff --git a/app/Http/Controllers/Account/EditController.php b/app/Http/Controllers/Account/EditController.php
index ca674eb407..a72c579179 100644
--- a/app/Http/Controllers/Account/EditController.php
+++ b/app/Http/Controllers/Account/EditController.php
@@ -124,7 +124,7 @@ class EditController extends Controller
$openingBalanceAmount = '';
}
$openingBalanceDate = $repository->getOpeningBalanceDate($account);
- $currency = $this->repository->getAccountCurrency($account) ?? app('amount')->getDefaultCurrency();
+ $currency = $this->repository->getAccountCurrency($account) ?? $this->defaultCurrency;
// include this account in net-worth charts?
$includeNetWorth = $repository->getMetaValue($account, 'include_net_worth');
diff --git a/app/Http/Controllers/Account/ReconcileController.php b/app/Http/Controllers/Account/ReconcileController.php
index 6a76227a83..ec3673c014 100644
--- a/app/Http/Controllers/Account/ReconcileController.php
+++ b/app/Http/Controllers/Account/ReconcileController.php
@@ -86,7 +86,7 @@ class ReconcileController extends Controller
return redirect(route('accounts.index', [config(sprintf('firefly.shortNamesByFullName.%s', $account->accountType->type))]));
}
- $currency = $this->accountRepos->getAccountCurrency($account) ?? app('amount')->getDefaultCurrency();
+ $currency = $this->accountRepos->getAccountCurrency($account) ?? $this->defaultCurrency;
// no start or end:
$range = app('navigation')->getViewRange(false);
@@ -197,7 +197,7 @@ class ReconcileController extends Controller
}
$reconciliation = $this->accountRepos->getReconciliation($account);
- $currency = $this->accountRepos->getAccountCurrency($account) ?? app('amount')->getDefaultCurrency();
+ $currency = $this->accountRepos->getAccountCurrency($account) ?? $this->defaultCurrency;
$source = $reconciliation;
$destination = $account;
if (1 === bccomp($difference, '0')) {
diff --git a/app/Http/Controllers/Account/ShowController.php b/app/Http/Controllers/Account/ShowController.php
index 6b6caffb64..2840229849 100644
--- a/app/Http/Controllers/Account/ShowController.php
+++ b/app/Http/Controllers/Account/ShowController.php
@@ -101,7 +101,7 @@ class ShowController extends Controller
$page = (int) $request->get('page');
$pageSize = (int) app('preferences')->get('listPageSize', 50)->data;
$accountCurrency = $this->repository->getAccountCurrency($account);
- $currency = $accountCurrency ?? Amount::getDefaultCurrency();
+ $currency = $accountCurrency ?? $this->defaultCurrency;
$fStart = $start->isoFormat($this->monthAndDayFormat);
$fEnd = $end->isoFormat($this->monthAndDayFormat);
$subTitle = (string) trans('firefly.journals_in_period_for_account', ['name' => $account->name, 'start' => $fStart, 'end' => $fEnd]);
@@ -178,7 +178,7 @@ class ShowController extends Controller
$subTitleIcon = config('firefly.subIconsByIdentifier.'.$account->accountType->type);
$page = (int) $request->get('page');
$pageSize = (int) app('preferences')->get('listPageSize', 50)->data;
- $currency = $this->repository->getAccountCurrency($account) ?? Amount::getDefaultCurrency();
+ $currency = $this->repository->getAccountCurrency($account) ?? $this->defaultCurrency;
$subTitle = (string) trans('firefly.all_journals_for_account', ['name' => $account->name]);
$periods = new Collection();
diff --git a/app/Http/Controllers/Bill/CreateController.php b/app/Http/Controllers/Bill/CreateController.php
index b126273230..664f7d8689 100644
--- a/app/Http/Controllers/Bill/CreateController.php
+++ b/app/Http/Controllers/Bill/CreateController.php
@@ -77,7 +77,7 @@ class CreateController extends Controller
$periods[$current] = (string) trans('firefly.repeat_freq_'.$current);
}
$subTitle = (string) trans('firefly.create_new_bill');
- $defaultCurrency = app('amount')->getDefaultCurrency();
+ $defaultCurrency = $this->defaultCurrency;
// put previous url in session if not redirect from store (not "create another").
if (true !== session('bills.create.fromStore')) {
diff --git a/app/Http/Controllers/Bill/EditController.php b/app/Http/Controllers/Bill/EditController.php
index abb062e606..c3f7b24969 100644
--- a/app/Http/Controllers/Bill/EditController.php
+++ b/app/Http/Controllers/Bill/EditController.php
@@ -85,11 +85,10 @@ class EditController extends Controller
$this->rememberPreviousUrl('bills.edit.url');
}
- $currency = app('amount')->getDefaultCurrency();
- $bill->amount_min = app('steam')->bcround($bill->amount_min, $currency->decimal_places);
- $bill->amount_max = app('steam')->bcround($bill->amount_max, $currency->decimal_places);
+ $bill->amount_min = app('steam')->bcround($bill->amount_min, $bill->transactionCurrency->decimal_places);
+ $bill->amount_max = app('steam')->bcround($bill->amount_max, $bill->transactionCurrency->decimal_places);
$rules = $this->repository->getRulesForBill($bill);
- $defaultCurrency = app('amount')->getDefaultCurrency();
+ $defaultCurrency = $this->defaultCurrency;
// code to handle active-checkboxes
$hasOldInput = null !== $request->old('_token');
diff --git a/app/Http/Controllers/Budget/CreateController.php b/app/Http/Controllers/Budget/CreateController.php
index 9bdc298e8f..026b3629e4 100644
--- a/app/Http/Controllers/Budget/CreateController.php
+++ b/app/Http/Controllers/Budget/CreateController.php
@@ -86,11 +86,10 @@ class CreateController extends Controller
'half_year' => (string) trans('firefly.auto_budget_period_half_year'),
'yearly' => (string) trans('firefly.auto_budget_period_yearly'),
];
- $currency = app('amount')->getDefaultCurrency();
$preFilled = [
'auto_budget_period' => $hasOldInput ? (bool) $request->old('auto_budget_period') : 'monthly',
- 'auto_budget_currency_id' => $hasOldInput ? (int) $request->old('auto_budget_currency_id') : $currency->id,
+ 'auto_budget_currency_id' => $hasOldInput ? (int) $request->old('auto_budget_currency_id') : $this->defaultCurrency->id,
];
$request->session()->flash('preFilled', $preFilled);
diff --git a/app/Http/Controllers/Budget/EditController.php b/app/Http/Controllers/Budget/EditController.php
index 8729985fac..382dc3a756 100644
--- a/app/Http/Controllers/Budget/EditController.php
+++ b/app/Http/Controllers/Budget/EditController.php
@@ -91,10 +91,9 @@ class EditController extends Controller
// code to handle active-checkboxes
$hasOldInput = null !== $request->old('_token');
- $currency = app('amount')->getDefaultCurrency();
$preFilled = [
'active' => $hasOldInput ? (bool) $request->old('active') : $budget->active,
- 'auto_budget_currency_id' => $hasOldInput ? (int) $request->old('auto_budget_currency_id') : $currency->id,
+ 'auto_budget_currency_id' => $hasOldInput ? (int) $request->old('auto_budget_currency_id') : $this->defaultCurrency->id,
];
if (null !== $autoBudget) {
$amount = $hasOldInput ? $request->old('auto_budget_amount') : $autoBudget->amount;
diff --git a/app/Http/Controllers/Budget/IndexController.php b/app/Http/Controllers/Budget/IndexController.php
index c49cee169c..8c67680cba 100644
--- a/app/Http/Controllers/Budget/IndexController.php
+++ b/app/Http/Controllers/Budget/IndexController.php
@@ -42,6 +42,7 @@ use Illuminate\Contracts\View\Factory;
use Illuminate\Http\JsonResponse;
use Illuminate\Http\Request;
use Illuminate\Support\Collection;
+use Illuminate\Support\Facades\Log;
use Illuminate\View\View;
/**
@@ -106,7 +107,6 @@ class IndexController extends Controller
$end ??= session('end', today(config('app.timezone'))->endOfMonth());
}
- $defaultCurrency = app('amount')->getDefaultCurrency();
$currencies = $this->currencyRepository->get();
$budgeted = '0';
$spent = '0';
@@ -119,14 +119,14 @@ class IndexController extends Controller
// get all available budgets:
$availableBudgets = $this->getAllAvailableBudgets($start, $end);
// get all active budgets:
- $budgets = $this->getAllBudgets($start, $end, $currencies, $defaultCurrency);
+ $budgets = $this->getAllBudgets($start, $end, $currencies, $this->defaultCurrency);
$sums = $this->getSums($budgets);
// get budgeted for default currency:
if (0 === count($availableBudgets)) {
- $budgeted = $this->blRepository->budgeted($start, $end, $defaultCurrency);
- $spentArr = $this->opsRepository->sumExpenses($start, $end, null, null, $defaultCurrency);
- $spent = $spentArr[$defaultCurrency->id]['sum'] ?? '0';
+ $budgeted = $this->blRepository->budgeted($start, $end, $this->defaultCurrency);
+ $spentArr = $this->opsRepository->sumExpenses($start, $end, null, null, $this->defaultCurrency);
+ $spent = $spentArr[$this->defaultCurrency->id]['sum'] ?? '0';
unset($spentArr);
}
@@ -136,6 +136,7 @@ class IndexController extends Controller
// get all inactive budgets, and simply list them:
$inactive = $this->repository->getInactiveBudgets();
+ $defaultCurrency = $this->defaultCurrency;
return view(
'budgets.index',
@@ -162,6 +163,7 @@ class IndexController extends Controller
private function getAllAvailableBudgets(Carbon $start, Carbon $end): array
{
+ Log::debug(sprintf('Start of getAllAvailableBudgets("%s", "%s")', $start->format('Y-m-d H:i:s'), $end->format('Y-m-d H:i:s')));
$converter = new ExchangeRateConverter();
// get all available budgets.
$ab = $this->abRepository->get($start, $end);
diff --git a/app/Http/Controllers/Chart/AccountController.php b/app/Http/Controllers/Chart/AccountController.php
index 09d5bb6ccd..bfd43804e0 100644
--- a/app/Http/Controllers/Chart/AccountController.php
+++ b/app/Http/Controllers/Chart/AccountController.php
@@ -103,7 +103,6 @@ class AccountController extends Controller
$currencies = [];
$chartData = [];
$tempData = [];
- $default = Amount::getDefaultCurrency();
// grab all accounts and names
$accounts = $this->accountRepository->getAccountsByType([AccountTypeEnum::EXPENSE->value]);
@@ -139,7 +138,7 @@ class AccountController extends Controller
continue;
}
Log::debug(sprintf('Will process expense array "%s" with amount %s', $key, $endBalance));
- $searchCode = $this->convertToNative ? $default->code : $key;
+ $searchCode = $this->convertToNative ? $this->defaultCurrency->code : $key;
Log::debug(sprintf('Search code is %s', $searchCode));
// see if there is an accompanying start amount.
// grab the difference and find the currency.
@@ -562,7 +561,6 @@ class AccountController extends Controller
$currencies = [];
$chartData = [];
$tempData = [];
- $default = Amount::getDefaultCurrency();
// grab all accounts and names
$accounts = $this->accountRepository->getAccountsByType([AccountTypeEnum::REVENUE->value]);
@@ -599,7 +597,7 @@ class AccountController extends Controller
continue;
}
Log::debug(sprintf('Will process expense array "%s" with amount %s', $key, $endBalance));
- $searchCode = $this->convertToNative ? $default->code : $key;
+ $searchCode = $this->convertToNative ? $this->defaultCurrency->code : $key;
Log::debug(sprintf('Search code is %s', $searchCode));
// see if there is an accompanying start amount.
// grab the difference and find the currency.
diff --git a/app/Http/Controllers/Chart/BudgetController.php b/app/Http/Controllers/Chart/BudgetController.php
index df07bf8d10..2ae6db7a63 100644
--- a/app/Http/Controllers/Chart/BudgetController.php
+++ b/app/Http/Controllers/Chart/BudgetController.php
@@ -465,7 +465,7 @@ class BudgetController extends Controller
$chartGenerator->setStart($start);
$chartGenerator->setEnd($end);
$chartGenerator->convertToNative = $this->convertToNative;
- $chartGenerator->default = Amount::getDefaultCurrency();
+ $chartGenerator->default = $this->defaultCurrency;
$chartData = $chartGenerator->generate();
$data = $this->generator->multiSet($chartData);
diff --git a/app/Http/Controllers/Controller.php b/app/Http/Controllers/Controller.php
index 1dcdbe3be8..237b02d55a 100644
--- a/app/Http/Controllers/Controller.php
+++ b/app/Http/Controllers/Controller.php
@@ -118,7 +118,7 @@ abstract class Controller extends BaseController
$this->defaultCurrency =null;
// get shown-intro-preference:
if (auth()->check()) {
- $this->defaultCurrency = app('amount')->getDefaultCurrency();
+ $this->defaultCurrency = Amount::getDefaultCurrency();
$language = Steam::getLanguage();
$locale = Steam::getLocale();
$darkMode = app('preferences')->get('darkMode', 'browser')->data;
diff --git a/app/Http/Controllers/Json/BoxController.php b/app/Http/Controllers/Json/BoxController.php
index d7781be69a..a20d2d8306 100644
--- a/app/Http/Controllers/Json/BoxController.php
+++ b/app/Http/Controllers/Json/BoxController.php
@@ -78,9 +78,7 @@ class BoxController extends Controller
$incomes = [];
$expenses = [];
$sums = [];
- $currency = app('amount')->getDefaultCurrency();
-
-
+ $currency = $this->defaultCurrency;
// collect income of user:
/** @var GroupCollectorInterface $collector */
$collector = app(GroupCollectorInterface::class);
@@ -91,7 +89,7 @@ class BoxController extends Controller
/** @var array $journal */
foreach ($set as $journal) {
- $currencyId = $this->convertToNative ? $currency->id : (int) $journal['currency_id'];
+ $currencyId = $this->convertToNative && $this->defaultCurrency->id !== (int) $journal['currency_id'] ? $this->defaultCurrency->id : (int) $journal['currency_id'];
$amount = Amount::getAmountFromJournal($journal);
$incomes[$currencyId] ??= '0';
$incomes[$currencyId] = bcadd($incomes[$currencyId], app('steam')->positive($amount));
@@ -109,7 +107,7 @@ class BoxController extends Controller
/** @var array $journal */
foreach ($set as $journal) {
- $currencyId = $this->convertToNative ? $currency->id : (int) $journal['currency_id'];
+ $currencyId = $this->convertToNative ? $this->defaultCurrency->id : (int) $journal['currency_id'];
$amount = Amount::getAmountFromJournal($journal);
$expenses[$currencyId] ??= '0';
$expenses[$currencyId] = bcadd($expenses[$currencyId], $amount);
@@ -126,10 +124,10 @@ class BoxController extends Controller
$expenses[$currencyId] = app('amount')->formatAnything($currency, $expenses[$currencyId] ?? '0', false);
}
if (0 === count($sums)) {
- $currency = app('amount')->getDefaultCurrency();
- $sums[$currency->id] = app('amount')->formatAnything($currency, '0', false);
- $incomes[$currency->id] = app('amount')->formatAnything($currency, '0', false);
- $expenses[$currency->id] = app('amount')->formatAnything($currency, '0', false);
+ $currency = $this->defaultCurrency;
+ $sums[$this->defaultCurrency->id] = app('amount')->formatAnything($this->defaultCurrency, '0', false);
+ $incomes[$this->defaultCurrency->id] = app('amount')->formatAnything($this->defaultCurrency, '0', false);
+ $expenses[$this->defaultCurrency->id] = app('amount')->formatAnything($this->defaultCurrency, '0', false);
}
$response = [
diff --git a/app/Http/Controllers/Json/ReconcileController.php b/app/Http/Controllers/Json/ReconcileController.php
index e27bda139a..38c29896f3 100644
--- a/app/Http/Controllers/Json/ReconcileController.php
+++ b/app/Http/Controllers/Json/ReconcileController.php
@@ -73,7 +73,7 @@ class ReconcileController extends Controller
{
$startBalance = $request->get('startBalance');
$endBalance = $request->get('endBalance');
- $accountCurrency = $this->accountRepos->getAccountCurrency($account) ?? app('amount')->getDefaultCurrency();
+ $accountCurrency = $this->accountRepos->getAccountCurrency($account) ?? $this->defaultCurrency;
$amount = '0';
$clearedAmount = '0';
@@ -193,7 +193,7 @@ class ReconcileController extends Controller
$startDate->subDay();
$end->endOfDay();
- $currency = $this->accountRepos->getAccountCurrency($account) ?? app('amount')->getDefaultCurrency();
+ $currency = $this->accountRepos->getAccountCurrency($account) ?? $this->defaultCurrency;
$startBalance = Steam::finalAccountBalance($account, $startDate)['balance'];
$endBalance = Steam::finalAccountBalance($account, $end)['balance'];
diff --git a/app/Http/Controllers/PreferencesController.php b/app/Http/Controllers/PreferencesController.php
index 290e60ea86..811da4c325 100644
--- a/app/Http/Controllers/PreferencesController.php
+++ b/app/Http/Controllers/PreferencesController.php
@@ -23,6 +23,7 @@ declare(strict_types=1);
namespace FireflyIII\Http\Controllers;
+use FireflyIII\Events\Preferences\UserGroupChangedDefaultCurrency;
use FireflyIII\Events\Test\UserTestNotificationChannel;
use FireflyIII\Exceptions\FireflyException;
use FireflyIII\Http\Requests\PreferencesRequest;
@@ -35,6 +36,7 @@ use Illuminate\Contracts\View\Factory;
use Illuminate\Http\RedirectResponse;
use Illuminate\Http\Request;
use Illuminate\Routing\Redirector;
+use Illuminate\Support\Facades\Log;
use Illuminate\View\View;
/**
@@ -258,6 +260,11 @@ class PreferencesController extends Controller
// convert native
$convertToNative = 1 === (int) $request->get('convertToNative');
+ if($convertToNative && !$this->convertToNative) {
+ // set to true!
+ Log::debug('User sets convertToNative to true.');
+ event(new UserGroupChangedDefaultCurrency(auth()->user()->userGroup));
+ }
app('preferences')->set('convert_to_native', $convertToNative);
// custom fiscal year
diff --git a/app/Http/Controllers/Recurring/CreateController.php b/app/Http/Controllers/Recurring/CreateController.php
index c8c91df86b..2a79a90092 100644
--- a/app/Http/Controllers/Recurring/CreateController.php
+++ b/app/Http/Controllers/Recurring/CreateController.php
@@ -84,7 +84,7 @@ class CreateController extends Controller
{
$budgets = app('expandedform')->makeSelectListWithEmpty($this->budgetRepos->getActiveBudgets());
$bills = app('expandedform')->makeSelectListWithEmpty($this->billRepository->getActiveBills());
- $defaultCurrency = app('amount')->getDefaultCurrency();
+ $defaultCurrency = $this->defaultCurrency;
$tomorrow = today(config('app.timezone'));
$oldRepetitionType = $request->old('repetition_type');
$tomorrow->addDay();
@@ -129,7 +129,7 @@ class CreateController extends Controller
{
$budgets = app('expandedform')->makeSelectListWithEmpty($this->budgetRepos->getActiveBudgets());
$bills = app('expandedform')->makeSelectListWithEmpty($this->billRepository->getActiveBills());
- $defaultCurrency = app('amount')->getDefaultCurrency();
+ $defaultCurrency = $this->defaultCurrency;
$tomorrow = today(config('app.timezone'));
$oldRepetitionType = $request->old('repetition_type');
$tomorrow->addDay();
diff --git a/app/Http/Controllers/Transaction/ConvertController.php b/app/Http/Controllers/Transaction/ConvertController.php
index ca3700b0eb..775d714d26 100644
--- a/app/Http/Controllers/Transaction/ConvertController.php
+++ b/app/Http/Controllers/Transaction/ConvertController.php
@@ -217,14 +217,13 @@ class ConvertController extends Controller
{
// make repositories
$accountList = $this->accountRepository->getActiveAccountsByType([AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE]);
- $defaultCurrency = app('amount')->getDefaultCurrency();
$grouped = [];
// group accounts:
/** @var Account $account */
foreach ($accountList as $account) {
$balance = Steam::finalAccountBalance($account, today()->endOfDay())['balance'];
- $currency = $this->accountRepository->getAccountCurrency($account) ?? $defaultCurrency;
+ $currency = $this->accountRepository->getAccountCurrency($account) ?? $this->defaultCurrency;
$role = 'l_'.$account->accountType->type;
$key = (string) trans('firefly.opt_group_'.$role);
$grouped[$key][$account->id] = $account->name.' ('.app('amount')->formatAnything($currency, $balance, false).')';
@@ -240,14 +239,13 @@ class ConvertController extends Controller
{
// make repositories
$accountList = $this->accountRepository->getActiveAccountsByType([AccountType::ASSET]);
- $defaultCurrency = app('amount')->getDefaultCurrency();
$grouped = [];
// group accounts:
/** @var Account $account */
foreach ($accountList as $account) {
$balance = Steam::finalAccountBalance($account, today()->endOfDay())['balance'];
- $currency = $this->accountRepository->getAccountCurrency($account) ?? $defaultCurrency;
+ $currency = $this->accountRepository->getAccountCurrency($account) ?? $this->defaultCurrency;
$role = (string) $this->accountRepository->getMetaValue($account, 'account_role');
if ('' === $role) {
$role = 'no_account_type';
diff --git a/app/Http/Controllers/Transaction/CreateController.php b/app/Http/Controllers/Transaction/CreateController.php
index a1b29b3877..fad87c640a 100644
--- a/app/Http/Controllers/Transaction/CreateController.php
+++ b/app/Http/Controllers/Transaction/CreateController.php
@@ -114,7 +114,7 @@ class CreateController extends Controller
$optionalFields = app('preferences')->get('transaction_journal_optional_fields', [])->data;
$allowedOpposingTypes = config('firefly.allowed_opposing_types');
$accountToTypes = config('firefly.account_to_transaction');
- $defaultCurrency = app('amount')->getDefaultCurrency();
+ $defaultCurrency = $this->defaultCurrency;
$previousUrl = $this->rememberPreviousUrl('transactions.create.url');
$parts = parse_url($previousUrl);
$search = sprintf('?%s', $parts['query'] ?? '');
diff --git a/app/Http/Controllers/Transaction/EditController.php b/app/Http/Controllers/Transaction/EditController.php
index 9f2da101d2..c638deb7c8 100644
--- a/app/Http/Controllers/Transaction/EditController.php
+++ b/app/Http/Controllers/Transaction/EditController.php
@@ -82,7 +82,7 @@ class EditController extends Controller
$title = $transactionGroup->transactionJournals()->count() > 1 ? $transactionGroup->title : $transactionGroup->transactionJournals()->first()->description;
$subTitle = (string) trans('firefly.edit_transaction_title', ['description' => $title]);
$subTitleIcon = 'fa-plus';
- $defaultCurrency = app('amount')->getDefaultCurrency();
+ $defaultCurrency = $this->defaultCurrency;
$cash = $repository->getCashAccount();
$previousUrl = $this->rememberPreviousUrl('transactions.edit.url');
$parts = parse_url($previousUrl);
diff --git a/app/Http/Middleware/Range.php b/app/Http/Middleware/Range.php
index 228b4bda88..3e0dc65f63 100644
--- a/app/Http/Middleware/Range.php
+++ b/app/Http/Middleware/Range.php
@@ -25,6 +25,7 @@ namespace FireflyIII\Http\Middleware;
use Carbon\Carbon;
use FireflyIII\Repositories\Journal\JournalRepositoryInterface;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Http\Controllers\RequestInformation;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Log;
@@ -108,7 +109,7 @@ class Range
setlocale(LC_TIME, $localeArray);
$moneyResult = setlocale(LC_MONETARY, $localeArray);
- // send error to view, if could not set money format
+ // send error to view, if it could not set money format
if (false === $moneyResult) {
app('log')->error('Could not set locale. The following array doesnt work: ', $localeArray);
app('view')->share('invalidMonetaryLocale', true);
@@ -117,7 +118,7 @@ class Range
// save some formats:
$monthAndDayFormat = (string) trans('config.month_and_day_js', [], $locale);
$dateTimeFormat = (string) trans('config.date_time_js', [], $locale);
- $defaultCurrency = app('amount')->getDefaultCurrency();
+ $defaultCurrency = Amount::getDefaultCurrency();
// also format for moment JS:
$madMomentJS = (string) trans('config.month_and_day_moment_js', [], $locale);
diff --git a/app/Http/Requests/PiggyBankStoreRequest.php b/app/Http/Requests/PiggyBankStoreRequest.php
index de06a31528..5dfe510745 100644
--- a/app/Http/Requests/PiggyBankStoreRequest.php
+++ b/app/Http/Requests/PiggyBankStoreRequest.php
@@ -26,6 +26,7 @@ namespace FireflyIII\Http\Requests;
use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
use FireflyIII\Rules\IsValidPositiveAmount;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Request\ChecksLogin;
use FireflyIII\Support\Request\ConvertsDataTypes;
use Illuminate\Foundation\Http\FormRequest;
@@ -125,7 +126,7 @@ class PiggyBankStoreRequest extends FormRequest
$currencyId = (int) ($data['transaction_currency_id'] ?? 0);
$currency = TransactionCurrency::find($currencyId);
if (null === $currency) {
- return app('amount')->getDefaultCurrency();
+ return Amount::getDefaultCurrency();
}
return $currency;
diff --git a/app/Http/Requests/PiggyBankUpdateRequest.php b/app/Http/Requests/PiggyBankUpdateRequest.php
index 7a76ae0ca2..e3deddb188 100644
--- a/app/Http/Requests/PiggyBankUpdateRequest.php
+++ b/app/Http/Requests/PiggyBankUpdateRequest.php
@@ -27,6 +27,7 @@ use FireflyIII\Models\PiggyBank;
use FireflyIII\Models\TransactionCurrency;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
use FireflyIII\Rules\IsValidPositiveAmount;
+use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Request\ChecksLogin;
use FireflyIII\Support\Request\ConvertsDataTypes;
use Illuminate\Foundation\Http\FormRequest;
@@ -128,7 +129,7 @@ class PiggyBankUpdateRequest extends FormRequest
$currencyId = (int) ($data['transaction_currency_id'] ?? 0);
$currency = TransactionCurrency::find($currencyId);
if (null === $currency) {
- return app('amount')->getDefaultCurrency();
+ return Amount::getDefaultCurrency();
}
return $currency;
diff --git a/app/Models/RecurrenceRepetition.php b/app/Models/RecurrenceRepetition.php
index f226d184ff..0d1453a986 100644
--- a/app/Models/RecurrenceRepetition.php
+++ b/app/Models/RecurrenceRepetition.php
@@ -38,16 +38,16 @@ class RecurrenceRepetition extends Model
use ReturnsIntegerIdTrait;
use SoftDeletes;
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const int WEEKEND_DO_NOTHING = 1;
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const int WEEKEND_SKIP_CREATION = 2;
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const int WEEKEND_TO_FRIDAY = 3;
- #[\Deprecated]
+ #[\Deprecated] /** @deprecated */
public const int WEEKEND_TO_MONDAY = 4;
protected $casts
diff --git a/app/Repositories/Bill/BillRepository.php b/app/Repositories/Bill/BillRepository.php
index a92ff5af30..b0d63df1d9 100644
--- a/app/Repositories/Bill/BillRepository.php
+++ b/app/Repositories/Bill/BillRepository.php
@@ -590,7 +590,7 @@ class BillRepository implements BillRepositoryInterface
if ($total > 0) {
$currency = $convertToNative && $bill->transactionCurrency->id !== $default->id ? $default : $bill->transactionCurrency;
- $average = bcdiv(bcadd($bill->{$maxField}, $bill->{$minField}), '2');
+ $average = bcdiv(bcadd($bill->{$maxField} ?? '0', $bill->{$minField} ?? '0'), '2');
Log::debug(sprintf('Amount to pay is %s %s (%d times)', $currency->code, $average, $total));
$return[$currency->id] ??= [
'id' => (string) $currency->id,
diff --git a/app/Repositories/Budget/AvailableBudgetRepository.php b/app/Repositories/Budget/AvailableBudgetRepository.php
index a1a23eb093..aac5c086c0 100644
--- a/app/Repositories/Budget/AvailableBudgetRepository.php
+++ b/app/Repositories/Budget/AvailableBudgetRepository.php
@@ -68,13 +68,14 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
if (null !== $start && null !== $end) {
$query->where(
static function (Builder $q1) use ($start, $end): void { // @phpstan-ignore-line
- $q1->where('start_date', '=', $start->format('Y-m-d H:i:s'));
- $q1->where('end_date', '=', $end->format('Y-m-d H:i:s'));
+ $q1->where('start_date', '=', $start->format('Y-m-d'));
+ $q1->where('end_date', '=', $end->format('Y-m-d'));
}
);
}
-
- return $query->get(['available_budgets.*']);
+ $result = $query->get(['available_budgets.*']);
+ Log::debug(sprintf('Found %d available budgets between %s and %s', $result->count(), $start->format('Y-m-d'), $end->format('Y-m-d')));
+ return $result;
}
/**
diff --git a/app/Support/Report/Summarizer/TransactionSummarizer.php b/app/Support/Report/Summarizer/TransactionSummarizer.php
index 17368c53b8..e0890270a8 100644
--- a/app/Support/Report/Summarizer/TransactionSummarizer.php
+++ b/app/Support/Report/Summarizer/TransactionSummarizer.php
@@ -97,7 +97,7 @@ class TransactionSummarizer
'currency_decimal_places' => $currencyDecimalPlaces,
];
$array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->{$method}($amount));
- Log::debug(sprintf('Journal #%d adds amount %s %s', $journal['transaction_journal_id'], $currencyCode, $amount));
+ //Log::debug(sprintf('Journal #%d adds amount %s %s', $journal['transaction_journal_id'], $currencyCode, $amount));
}
Log::debug('End of sumExpenses.', $array);
From d37304fa688b460e5bc6dbce31935e7b9d308075 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Mon, 30 Dec 2024 12:22:39 +0100
Subject: [PATCH 165/167] Fix available budgets.
---
.../Observer/AvailableBudgetObserver.php | 2 +-
app/Handlers/Observer/BudgetLimitObserver.php | 2 +-
app/Models/AvailableBudget.php | 24 +++++++++++++++----
.../Budget/AvailableBudgetRepository.php | 14 +++++------
resources/assets/v1/package.json | 2 +-
5 files changed, 30 insertions(+), 14 deletions(-)
diff --git a/app/Handlers/Observer/AvailableBudgetObserver.php b/app/Handlers/Observer/AvailableBudgetObserver.php
index ec23dd7df6..530ee8c00e 100644
--- a/app/Handlers/Observer/AvailableBudgetObserver.php
+++ b/app/Handlers/Observer/AvailableBudgetObserver.php
@@ -46,7 +46,7 @@ class AvailableBudgetObserver
private function updateNativeAmount(AvailableBudget $availableBudget): void
{
if (!Amount::convertToNative($availableBudget->user)) {
- Log::debug('Do not update native available amount of the available budget.');
+ //Log::debug('Do not update native available amount of the available budget.');
return;
}
diff --git a/app/Handlers/Observer/BudgetLimitObserver.php b/app/Handlers/Observer/BudgetLimitObserver.php
index dbc3493415..a1aba94c24 100644
--- a/app/Handlers/Observer/BudgetLimitObserver.php
+++ b/app/Handlers/Observer/BudgetLimitObserver.php
@@ -46,7 +46,7 @@ class BudgetLimitObserver
private function updateNativeAmount(BudgetLimit $budgetLimit): void
{
if (!Amount::convertToNative($budgetLimit->budget->user)) {
- Log::debug('Do not update native amount of the budget limit.');
+ //Log::debug('Do not update native amount of the budget limit.');
return;
}
diff --git a/app/Models/AvailableBudget.php b/app/Models/AvailableBudget.php
index c88b5d7a3c..5d335435bd 100644
--- a/app/Models/AvailableBudget.php
+++ b/app/Models/AvailableBudget.php
@@ -23,6 +23,7 @@ declare(strict_types=1);
namespace FireflyIII\Models;
+use Carbon\Carbon;
use FireflyIII\Support\Models\ReturnsIntegerIdTrait;
use FireflyIII\Support\Models\ReturnsIntegerUserIdTrait;
use FireflyIII\User;
@@ -66,10 +67,10 @@ class AvailableBudget extends Model
$availableBudgetId = (int) $value;
/** @var User $user */
- $user = auth()->user();
+ $user = auth()->user();
/** @var null|AvailableBudget $availableBudget */
- $availableBudget = $user->availableBudgets()->find($availableBudgetId);
+ $availableBudget = $user->availableBudgets()->find($availableBudgetId);
if (null !== $availableBudget) {
return $availableBudget;
}
@@ -91,14 +92,29 @@ class AvailableBudget extends Model
protected function amount(): Attribute
{
return Attribute::make(
- get: static fn ($value) => (string) $value,
+ get: static fn($value) => (string) $value,
);
}
protected function transactionCurrencyId(): Attribute
{
return Attribute::make(
- get: static fn ($value) => (int) $value,
+ get: static fn($value) => (int) $value,
+ );
+ }
+ protected function startDate(): Attribute
+ {
+ return Attribute::make(
+ get: fn (string $value) => Carbon::parse($value),
+ set: fn (Carbon $value) => $value->format('Y-m-d'),
+ );
+ }
+
+ protected function endDate(): Attribute
+ {
+ return Attribute::make(
+ get: fn (string $value) => Carbon::parse($value),
+ set: fn (Carbon $value) => $value->format('Y-m-d'),
);
}
}
diff --git a/app/Repositories/Budget/AvailableBudgetRepository.php b/app/Repositories/Budget/AvailableBudgetRepository.php
index aac5c086c0..753ce16e52 100644
--- a/app/Repositories/Budget/AvailableBudgetRepository.php
+++ b/app/Repositories/Budget/AvailableBudgetRepository.php
@@ -74,7 +74,7 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
);
}
$result = $query->get(['available_budgets.*']);
- Log::debug(sprintf('Found %d available budgets between %s and %s', $result->count(), $start->format('Y-m-d'), $end->format('Y-m-d')));
+ Log::debug(sprintf('Found %d available budgets between %s and %s', $result->count(), $start->format('Y-m-d H:i:s'), $end->format('Y-m-d H:i:s')));
return $result;
}
@@ -215,9 +215,9 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
$availableBudget = new AvailableBudget();
$availableBudget->user()->associate($this->user);
$availableBudget->transactionCurrency()->associate($currency);
- $availableBudget->start_date = $start->startOfDay()->format('Y-m-d'); // @phpstan-ignore-line
+ $availableBudget->start_date = $start->startOfDay();
$availableBudget->start_date_tz = $start->format('e');
- $availableBudget->end_date = $end->endOfDay()->format('Y-m-d'); // @phpstan-ignore-line
+ $availableBudget->end_date = $end->endOfDay();
$availableBudget->end_date_tz = $end->format('e');
}
$availableBudget->amount = $amount;
@@ -250,9 +250,9 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
'user_group_id' => $this->user->user_group_id,
'transaction_currency_id' => $data['currency_id'],
'amount' => $data['amount'],
- 'start_date' => $start->format('Y-m-d'),
+ 'start_date' => $start,
'start_date_tz' => $start->format('e'),
- 'end_date' => $end->format('Y-m-d'),
+ 'end_date' => $end,
'end_date_tz' => $end->format('e'),
]
);
@@ -274,7 +274,7 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
$start = $data['start'];
if ($start instanceof Carbon) {
$start = $data['start']->startOfDay();
- $availableBudget->start_date = $start->format('Y-m-d');
+ $availableBudget->start_date = $start;
$availableBudget->start_date_tz = $start->format('e');
$availableBudget->save();
}
@@ -284,7 +284,7 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
$end = $data['end'];
if ($end instanceof Carbon) {
$end = $data['end']->endOfDay();
- $availableBudget->end_date = $end->format('Y-m-d');
+ $availableBudget->end_date = $end;
$availableBudget->end_date_tz = $end->format('e');
$availableBudget->save();
}
diff --git a/resources/assets/v1/package.json b/resources/assets/v1/package.json
index 9e317ca79f..bb89e057a6 100644
--- a/resources/assets/v1/package.json
+++ b/resources/assets/v1/package.json
@@ -25,7 +25,7 @@
"postcss": "^8.4.47",
"uiv": "^1.4",
"vue": "^2.7",
- "vue-i18n": "^8",
+ "vue-i18n": "^11",
"vue-loader": "^15",
"vue-template-compiler": "^2.7"
}
From 146e164f044690a1cf4f8444c84e77a24c6a5cb8 Mon Sep 17 00:00:00 2001
From: James Cole
Date: Mon, 30 Dec 2024 15:31:27 +0100
Subject: [PATCH 166/167] Back to 8.
---
resources/assets/v1/package.json | 2 +-
1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/resources/assets/v1/package.json b/resources/assets/v1/package.json
index bb89e057a6..9e317ca79f 100644
--- a/resources/assets/v1/package.json
+++ b/resources/assets/v1/package.json
@@ -25,7 +25,7 @@
"postcss": "^8.4.47",
"uiv": "^1.4",
"vue": "^2.7",
- "vue-i18n": "^11",
+ "vue-i18n": "^8",
"vue-loader": "^15",
"vue-template-compiler": "^2.7"
}
From ec821054339ffbead90f334cb2d3371fc07d6aff Mon Sep 17 00:00:00 2001
From: github-actions <41898282+github-actions[bot]@users.noreply.github.com>
Date: Mon, 30 Dec 2024 15:35:26 +0100
Subject: [PATCH 167/167] Auto commit for release 'develop' on 2024-12-30
---
THANKS.md | 1 +
.../Observer/AvailableBudgetObserver.php | 2 +-
app/Handlers/Observer/BudgetLimitObserver.php | 2 +-
.../Controllers/Account/ShowController.php | 1 -
app/Http/Controllers/Json/BoxController.php | 5 ++-
.../Controllers/PreferencesController.php | 2 +-
.../Transaction/ConvertController.php | 8 ++--
app/Models/AvailableBudget.php | 9 +++--
.../Budget/AvailableBudgetRepository.php | 3 +-
.../Summarizer/TransactionSummarizer.php | 2 +-
composer.lock | 40 +++++++++----------
resources/assets/v1/src/locales/de.json | 26 ++++++------
resources/assets/v1/src/locales/nl.json | 26 ++++++------
.../Api/Autocomplete/BillControllerTest.php | 6 ++-
.../Api/Autocomplete/BudgetControllerTest.php | 5 ++-
.../Autocomplete/CategoryControllerTest.php | 5 ++-
.../Autocomplete/CurrencyControllerTest.php | 29 ++++++--------
.../ObjectGroupControllerTest.php | 17 ++++----
18 files changed, 96 insertions(+), 93 deletions(-)
diff --git a/THANKS.md b/THANKS.md
index 6d853990d6..d18178f45d 100755
--- a/THANKS.md
+++ b/THANKS.md
@@ -4,6 +4,7 @@ Over time, many people have contributed to Firefly III. Their efforts are not al
Please find below all the people who contributed to the Firefly III code. Their names are mentioned in the year of their first contribution.
## 2024
+- TasneemTantawy
- Antônio Franco
- yparitcher
- Jhon Pedroza
diff --git a/app/Handlers/Observer/AvailableBudgetObserver.php b/app/Handlers/Observer/AvailableBudgetObserver.php
index 530ee8c00e..7d749af5b2 100644
--- a/app/Handlers/Observer/AvailableBudgetObserver.php
+++ b/app/Handlers/Observer/AvailableBudgetObserver.php
@@ -46,7 +46,7 @@ class AvailableBudgetObserver
private function updateNativeAmount(AvailableBudget $availableBudget): void
{
if (!Amount::convertToNative($availableBudget->user)) {
- //Log::debug('Do not update native available amount of the available budget.');
+ // Log::debug('Do not update native available amount of the available budget.');
return;
}
diff --git a/app/Handlers/Observer/BudgetLimitObserver.php b/app/Handlers/Observer/BudgetLimitObserver.php
index a1aba94c24..aaac82cb5d 100644
--- a/app/Handlers/Observer/BudgetLimitObserver.php
+++ b/app/Handlers/Observer/BudgetLimitObserver.php
@@ -46,7 +46,7 @@ class BudgetLimitObserver
private function updateNativeAmount(BudgetLimit $budgetLimit): void
{
if (!Amount::convertToNative($budgetLimit->budget->user)) {
- //Log::debug('Do not update native amount of the budget limit.');
+ // Log::debug('Do not update native amount of the budget limit.');
return;
}
diff --git a/app/Http/Controllers/Account/ShowController.php b/app/Http/Controllers/Account/ShowController.php
index 2840229849..badc25693d 100644
--- a/app/Http/Controllers/Account/ShowController.php
+++ b/app/Http/Controllers/Account/ShowController.php
@@ -30,7 +30,6 @@ use FireflyIII\Helpers\Collector\GroupCollectorInterface;
use FireflyIII\Http\Controllers\Controller;
use FireflyIII\Models\Account;
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
-use FireflyIII\Support\Facades\Amount;
use FireflyIII\Support\Facades\Steam;
use FireflyIII\Support\Http\Controllers\PeriodOverview;
use Illuminate\Contracts\View\Factory;
diff --git a/app/Http/Controllers/Json/BoxController.php b/app/Http/Controllers/Json/BoxController.php
index a20d2d8306..5bd00fb5f4 100644
--- a/app/Http/Controllers/Json/BoxController.php
+++ b/app/Http/Controllers/Json/BoxController.php
@@ -78,7 +78,8 @@ class BoxController extends Controller
$incomes = [];
$expenses = [];
$sums = [];
- $currency = $this->defaultCurrency;
+ $currency = $this->defaultCurrency;
+
// collect income of user:
/** @var GroupCollectorInterface $collector */
$collector = app(GroupCollectorInterface::class);
@@ -124,7 +125,7 @@ class BoxController extends Controller
$expenses[$currencyId] = app('amount')->formatAnything($currency, $expenses[$currencyId] ?? '0', false);
}
if (0 === count($sums)) {
- $currency = $this->defaultCurrency;
+ $currency = $this->defaultCurrency;
$sums[$this->defaultCurrency->id] = app('amount')->formatAnything($this->defaultCurrency, '0', false);
$incomes[$this->defaultCurrency->id] = app('amount')->formatAnything($this->defaultCurrency, '0', false);
$expenses[$this->defaultCurrency->id] = app('amount')->formatAnything($this->defaultCurrency, '0', false);
diff --git a/app/Http/Controllers/PreferencesController.php b/app/Http/Controllers/PreferencesController.php
index 811da4c325..702eb0bd62 100644
--- a/app/Http/Controllers/PreferencesController.php
+++ b/app/Http/Controllers/PreferencesController.php
@@ -260,7 +260,7 @@ class PreferencesController extends Controller
// convert native
$convertToNative = 1 === (int) $request->get('convertToNative');
- if($convertToNative && !$this->convertToNative) {
+ if ($convertToNative && !$this->convertToNative) {
// set to true!
Log::debug('User sets convertToNative to true.');
event(new UserGroupChangedDefaultCurrency(auth()->user()->userGroup));
diff --git a/app/Http/Controllers/Transaction/ConvertController.php b/app/Http/Controllers/Transaction/ConvertController.php
index 775d714d26..b7cd58506c 100644
--- a/app/Http/Controllers/Transaction/ConvertController.php
+++ b/app/Http/Controllers/Transaction/ConvertController.php
@@ -216,8 +216,8 @@ class ConvertController extends Controller
private function getLiabilities(): array
{
// make repositories
- $accountList = $this->accountRepository->getActiveAccountsByType([AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE]);
- $grouped = [];
+ $accountList = $this->accountRepository->getActiveAccountsByType([AccountType::LOAN, AccountType::DEBT, AccountType::MORTGAGE]);
+ $grouped = [];
// group accounts:
/** @var Account $account */
@@ -238,8 +238,8 @@ class ConvertController extends Controller
private function getAssetAccounts(): array
{
// make repositories
- $accountList = $this->accountRepository->getActiveAccountsByType([AccountType::ASSET]);
- $grouped = [];
+ $accountList = $this->accountRepository->getActiveAccountsByType([AccountType::ASSET]);
+ $grouped = [];
// group accounts:
/** @var Account $account */
diff --git a/app/Models/AvailableBudget.php b/app/Models/AvailableBudget.php
index 5d335435bd..45e2eb91bb 100644
--- a/app/Models/AvailableBudget.php
+++ b/app/Models/AvailableBudget.php
@@ -67,10 +67,10 @@ class AvailableBudget extends Model
$availableBudgetId = (int) $value;
/** @var User $user */
- $user = auth()->user();
+ $user = auth()->user();
/** @var null|AvailableBudget $availableBudget */
- $availableBudget = $user->availableBudgets()->find($availableBudgetId);
+ $availableBudget = $user->availableBudgets()->find($availableBudgetId);
if (null !== $availableBudget) {
return $availableBudget;
}
@@ -92,16 +92,17 @@ class AvailableBudget extends Model
protected function amount(): Attribute
{
return Attribute::make(
- get: static fn($value) => (string) $value,
+ get: static fn ($value) => (string) $value,
);
}
protected function transactionCurrencyId(): Attribute
{
return Attribute::make(
- get: static fn($value) => (int) $value,
+ get: static fn ($value) => (int) $value,
);
}
+
protected function startDate(): Attribute
{
return Attribute::make(
diff --git a/app/Repositories/Budget/AvailableBudgetRepository.php b/app/Repositories/Budget/AvailableBudgetRepository.php
index 753ce16e52..3a990a3b18 100644
--- a/app/Repositories/Budget/AvailableBudgetRepository.php
+++ b/app/Repositories/Budget/AvailableBudgetRepository.php
@@ -64,7 +64,7 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
*/
public function get(?Carbon $start = null, ?Carbon $end = null): Collection
{
- $query = $this->user->availableBudgets()->with(['transactionCurrency']);
+ $query = $this->user->availableBudgets()->with(['transactionCurrency']);
if (null !== $start && null !== $end) {
$query->where(
static function (Builder $q1) use ($start, $end): void { // @phpstan-ignore-line
@@ -75,6 +75,7 @@ class AvailableBudgetRepository implements AvailableBudgetRepositoryInterface
}
$result = $query->get(['available_budgets.*']);
Log::debug(sprintf('Found %d available budgets between %s and %s', $result->count(), $start->format('Y-m-d H:i:s'), $end->format('Y-m-d H:i:s')));
+
return $result;
}
diff --git a/app/Support/Report/Summarizer/TransactionSummarizer.php b/app/Support/Report/Summarizer/TransactionSummarizer.php
index e0890270a8..7e74cd09f0 100644
--- a/app/Support/Report/Summarizer/TransactionSummarizer.php
+++ b/app/Support/Report/Summarizer/TransactionSummarizer.php
@@ -97,7 +97,7 @@ class TransactionSummarizer
'currency_decimal_places' => $currencyDecimalPlaces,
];
$array[$currencyId]['sum'] = bcadd($array[$currencyId]['sum'], app('steam')->{$method}($amount));
- //Log::debug(sprintf('Journal #%d adds amount %s %s', $journal['transaction_journal_id'], $currencyCode, $amount));
+ // Log::debug(sprintf('Journal #%d adds amount %s %s', $journal['transaction_journal_id'], $currencyCode, $amount));
}
Log::debug('End of sumExpenses.', $array);
diff --git a/composer.lock b/composer.lock
index c28f738963..2e5b9f9a3c 100644
--- a/composer.lock
+++ b/composer.lock
@@ -6364,16 +6364,16 @@
},
{
"name": "spatie/laravel-package-tools",
- "version": "1.17.0",
+ "version": "1.18.0",
"source": {
"type": "git",
"url": "https://github.com/spatie/laravel-package-tools.git",
- "reference": "9ab30fd24f677e5aa370ea4cf6b41c517d16cf85"
+ "reference": "8332205b90d17164913244f4a8e13ab7e6761d29"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/spatie/laravel-package-tools/zipball/9ab30fd24f677e5aa370ea4cf6b41c517d16cf85",
- "reference": "9ab30fd24f677e5aa370ea4cf6b41c517d16cf85",
+ "url": "https://api.github.com/repos/spatie/laravel-package-tools/zipball/8332205b90d17164913244f4a8e13ab7e6761d29",
+ "reference": "8332205b90d17164913244f4a8e13ab7e6761d29",
"shasum": ""
},
"require": {
@@ -6412,7 +6412,7 @@
],
"support": {
"issues": "https://github.com/spatie/laravel-package-tools/issues",
- "source": "https://github.com/spatie/laravel-package-tools/tree/1.17.0"
+ "source": "https://github.com/spatie/laravel-package-tools/tree/1.18.0"
},
"funding": [
{
@@ -6420,7 +6420,7 @@
"type": "github"
}
],
- "time": "2024-12-09T16:29:14+00:00"
+ "time": "2024-12-30T13:13:39+00:00"
},
{
"name": "spatie/period",
@@ -10287,20 +10287,20 @@
},
{
"name": "barryvdh/reflection-docblock",
- "version": "v2.2.0",
+ "version": "v2.3.0",
"source": {
"type": "git",
"url": "https://github.com/barryvdh/ReflectionDocBlock.git",
- "reference": "db125e8df4329bd45f2da405aab007f502f38531"
+ "reference": "818be8de6af4d16ef3ad51ea9234b3d37026ee5f"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/barryvdh/ReflectionDocBlock/zipball/db125e8df4329bd45f2da405aab007f502f38531",
- "reference": "db125e8df4329bd45f2da405aab007f502f38531",
+ "url": "https://api.github.com/repos/barryvdh/ReflectionDocBlock/zipball/818be8de6af4d16ef3ad51ea9234b3d37026ee5f",
+ "reference": "818be8de6af4d16ef3ad51ea9234b3d37026ee5f",
"shasum": ""
},
"require": {
- "php": ">=5.3.3"
+ "php": ">=7.1"
},
"require-dev": {
"phpunit/phpunit": "^8.5.14|^9"
@@ -10312,7 +10312,7 @@
"type": "library",
"extra": {
"branch-alias": {
- "dev-master": "2.2.x-dev"
+ "dev-master": "2.3.x-dev"
}
},
"autoload": {
@@ -10333,9 +10333,9 @@
}
],
"support": {
- "source": "https://github.com/barryvdh/ReflectionDocBlock/tree/v2.2.0"
+ "source": "https://github.com/barryvdh/ReflectionDocBlock/tree/v2.3.0"
},
- "time": "2024-12-28T10:00:03+00:00"
+ "time": "2024-12-30T10:35:04+00:00"
},
{
"name": "cloudcreativity/json-api-testing",
@@ -11147,16 +11147,16 @@
},
{
"name": "nikic/php-parser",
- "version": "v5.3.1",
+ "version": "v5.4.0",
"source": {
"type": "git",
"url": "https://github.com/nikic/PHP-Parser.git",
- "reference": "8eea230464783aa9671db8eea6f8c6ac5285794b"
+ "reference": "447a020a1f875a434d62f2a401f53b82a396e494"
},
"dist": {
"type": "zip",
- "url": "https://api.github.com/repos/nikic/PHP-Parser/zipball/8eea230464783aa9671db8eea6f8c6ac5285794b",
- "reference": "8eea230464783aa9671db8eea6f8c6ac5285794b",
+ "url": "https://api.github.com/repos/nikic/PHP-Parser/zipball/447a020a1f875a434d62f2a401f53b82a396e494",
+ "reference": "447a020a1f875a434d62f2a401f53b82a396e494",
"shasum": ""
},
"require": {
@@ -11199,9 +11199,9 @@
],
"support": {
"issues": "https://github.com/nikic/PHP-Parser/issues",
- "source": "https://github.com/nikic/PHP-Parser/tree/v5.3.1"
+ "source": "https://github.com/nikic/PHP-Parser/tree/v5.4.0"
},
- "time": "2024-10-08T18:51:32+00:00"
+ "time": "2024-12-30T11:07:19+00:00"
},
{
"name": "phar-io/manifest",
diff --git a/resources/assets/v1/src/locales/de.json b/resources/assets/v1/src/locales/de.json
index 46b17f4116..cfb4797d99 100644
--- a/resources/assets/v1/src/locales/de.json
+++ b/resources/assets/v1/src/locales/de.json
@@ -21,7 +21,7 @@
"apply_rules_checkbox": "Regeln anwenden",
"fire_webhooks_checkbox": "Webhooks abfeuern",
"no_budget_pointer": "Sie scheinen noch keine Budgets festgelegt zu haben. Sie sollten einige davon auf der Seite Budgets<\/a> anlegen. Budgets k\u00f6nnen Ihnen dabei helfen, den \u00dcberblick \u00fcber die Ausgaben zu behalten.",
- "no_bill_pointer": "Sie scheinen noch kein Abonnement zu haben. Sie sollten einige auf der Seite Abonnement<\/a> erstellen. Abonnements k\u00f6nnen Ihnen helfen, den \u00dcberblick \u00fcber Ihre Ausgaben zu behalten.",
+ "no_bill_pointer": "You seem to have no subscription yet. You should create some on the subscription<\/a>-page. Subscriptions can help you keep track of expenses.",
"source_account": "Quellkonto",
"hidden_fields_preferences": "Sie k\u00f6nnen weitere Buchungsoptionen in Ihren Einstellungen<\/a> aktivieren.",
"destination_account": "Zielkonto",
@@ -36,7 +36,7 @@
"is_reconciled_fields_dropped": "Da diese Buchung abgeglichen ist, k\u00f6nnen Sie weder die Konten noch den\/die Betrag\/Betr\u00e4ge aktualisieren.",
"tags": "Schlagw\u00f6rter",
"no_budget": "(kein Budget)",
- "no_bill": "(kein Abonnement)",
+ "no_bill": "(no subscription)",
"category": "Kategorie",
"attachments": "Anh\u00e4nge",
"notes": "Notizen",
@@ -52,7 +52,7 @@
"destination_account_reconciliation": "Sie k\u00f6nnen das Zielkonto einer Kontenausgleichsbuchung nicht bearbeiten.",
"source_account_reconciliation": "Sie k\u00f6nnen das Quellkonto einer Kontenausgleichsbuchung nicht bearbeiten.",
"budget": "Budget",
- "bill": "Abonnement",
+ "bill": "Subscription",
"you_create_withdrawal": "Sie haben eine Ausgabe erstellt.",
"you_create_transfer": "Sie erstellen eine Umbuchung.",
"you_create_deposit": "Sie haben eine Einnahme erstellt.",
@@ -130,15 +130,15 @@
"response": "Antwort",
"visit_webhook_url": "Webhook-URL besuchen",
"reset_webhook_secret": "Webhook Secret zur\u00fccksetzen",
- "header_exchange_rates": "Wechselkurse",
- "exchange_rates_intro": "Firefly III unterst\u00fctzt das Herunterladen und Verwenden von Wechselkursen. Lesen Sie mehr dar\u00fcber in der Dokumentation<\/a>.",
- "exchange_rates_from_to": "Zwischen {from} und {to} (und umgekehrt)",
- "exchange_rates_intro_rates": "Firefly III verwendet die folgenden Wechselkurse. Der Kehrwert wird automatisch berechnet, wenn er nicht angegeben wurde. Wenn f\u00fcr das Datum der Transaktion kein Wechselkurs vorhanden ist, sucht Firefly III in der Vergangenheit nach einem Kurs. Wenn keine vorhanden sind, wird der Kurs \u201e1\u201c verwendet.",
- "header_exchange_rates_rates": "Wechselkurse",
- "header_exchange_rates_table": "Tabelle mit Wechselkursen",
- "help_rate_form": "An diesem Tag, wie viele {to} werden Sie f\u00fcr {from} bekommen?",
- "add_new_rate": "Neuen Wechselkurs hinzuf\u00fcgen",
- "save_new_rate": "Neuen Kurs speichern"
+ "header_exchange_rates": "Exchange rates",
+ "exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
+ "exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
+ "header_exchange_rates_rates": "Exchange rates",
+ "header_exchange_rates_table": "Table with exchange rates",
+ "help_rate_form": "On this day, how many {to} will you get for one {from}?",
+ "add_new_rate": "Add a new exchange rate",
+ "save_new_rate": "Save new rate"
},
"form": {
"url": "URL",
@@ -158,7 +158,7 @@
"webhook_delivery": "Zustellung",
"from_currency_to_currency": "{from} → {to}",
"to_currency_from_currency": "{to} → {from}",
- "rate": "Kurs"
+ "rate": "Rate"
},
"list": {
"active": "Aktiv?",
diff --git a/resources/assets/v1/src/locales/nl.json b/resources/assets/v1/src/locales/nl.json
index ae4088faf6..b4dc805008 100644
--- a/resources/assets/v1/src/locales/nl.json
+++ b/resources/assets/v1/src/locales/nl.json
@@ -21,7 +21,7 @@
"apply_rules_checkbox": "Regels toepassen",
"fire_webhooks_checkbox": "Webhooks starten",
"no_budget_pointer": "Je hebt nog geen budgetten. Maak er een aantal op de budgetten<\/a>-pagina. Met budgetten kan je je uitgaven beter bijhouden.",
- "no_bill_pointer": "Je hebt nog geen abonnementen. Maak er een aantal op de abonnementenpagina<\/a>. Met abonnementen kan je uitgaven bijhouden.",
+ "no_bill_pointer": "You seem to have no subscription yet. You should create some on the subscription<\/a>-page. Subscriptions can help you keep track of expenses.",
"source_account": "Bronrekening",
"hidden_fields_preferences": "Je kan meer transactieopties inschakelen in je instellingen<\/a>.",
"destination_account": "Doelrekening",
@@ -36,7 +36,7 @@
"is_reconciled_fields_dropped": "Omdat deze transactie al is afgestemd, kan je het bedrag noch de rekeningen wijzigen.",
"tags": "Tags",
"no_budget": "(geen budget)",
- "no_bill": "(geen abonnement)",
+ "no_bill": "(no subscription)",
"category": "Categorie",
"attachments": "Bijlagen",
"notes": "Notities",
@@ -52,7 +52,7 @@
"destination_account_reconciliation": "Je kan de doelrekening van een afstemming niet wijzigen.",
"source_account_reconciliation": "Je kan de bronrekening van een afstemming niet wijzigen.",
"budget": "Budget",
- "bill": "Abonnement",
+ "bill": "Subscription",
"you_create_withdrawal": "Je maakt een uitgave.",
"you_create_transfer": "Je maakt een overschrijving.",
"you_create_deposit": "Je maakt inkomsten.",
@@ -130,15 +130,15 @@
"response": "Reactie",
"visit_webhook_url": "Bezoek URL van webhook",
"reset_webhook_secret": "Reset webhook-geheim",
- "header_exchange_rates": "Wisselkoersen",
- "exchange_rates_intro": "Firefly III kan wisselkoersen downloaden en gebruiken. Lees hier meer over in de documentatie<\/a>.",
- "exchange_rates_from_to": "Tussen {from} en {to} (en andersom)",
- "exchange_rates_intro_rates": "Firefly III gebruikt de volgende wisselkoersen. De inverse berekent zichzelf als deze niet is opgegeven. Als er geen wisselkoers bestaat voor de datum van de transactie, gaat Firefly III terug in de tijd om er een te vinden. Als er geen aanwezig is, zal de koers \"1\" gebruikt worden.",
- "header_exchange_rates_rates": "Wisselkoersen",
- "header_exchange_rates_table": "Tabel met wisselkoersen",
- "help_rate_form": "Hoeveel {to} krijg je op deze dag voor \u00e9\u00e9n {from}?",
- "add_new_rate": "Nieuwe wisselkoers toevoegen",
- "save_new_rate": "Nieuwe wisselkoers opslaan"
+ "header_exchange_rates": "Exchange rates",
+ "exchange_rates_intro": "Firefly III supports downloading and using exchange rates. Read more about this in the documentation<\/a>.",
+ "exchange_rates_from_to": "Between {from} and {to} (and the other way around)",
+ "exchange_rates_intro_rates": "Firefly III uses the following exchange rates. The inverse is automatically calculated when it is not provided. If no exchange rate exists for the date of the transaction, Firefly III will go back in time to find one. If none are present, the rate \"1\" will be used.",
+ "header_exchange_rates_rates": "Exchange rates",
+ "header_exchange_rates_table": "Table with exchange rates",
+ "help_rate_form": "On this day, how many {to} will you get for one {from}?",
+ "add_new_rate": "Add a new exchange rate",
+ "save_new_rate": "Save new rate"
},
"form": {
"url": "URL",
@@ -158,7 +158,7 @@
"webhook_delivery": "Bericht",
"from_currency_to_currency": "{from} → {to}",
"to_currency_from_currency": "{to} → {from}",
- "rate": "Wisselkoers"
+ "rate": "Rate"
},
"list": {
"active": "Actief?",
diff --git a/tests/integration/Api/Autocomplete/BillControllerTest.php b/tests/integration/Api/Autocomplete/BillControllerTest.php
index 11a69a1c23..134f3517e4 100644
--- a/tests/integration/Api/Autocomplete/BillControllerTest.php
+++ b/tests/integration/Api/Autocomplete/BillControllerTest.php
@@ -46,16 +46,18 @@ final class BillControllerTest extends TestCase
protected function createAuthenticatedUser(): User
{
- $userGroup = UserGroup::create(['title' => 'Test Group']);
+ $userGroup = UserGroup::create(['title' => 'Test Group']);
- $user= User::create([
+ $user = User::create([
'email' => 'test@email.com',
'password' => 'password',
]);
$user->user_group_id = $userGroup->id;
$user->save();
+
return $user;
}
+
private function createTestBills(int $count, User $user): void
{
for ($i = 1; $i <= $count; ++$i) {
diff --git a/tests/integration/Api/Autocomplete/BudgetControllerTest.php b/tests/integration/Api/Autocomplete/BudgetControllerTest.php
index b69157fe1e..542cc4fc70 100644
--- a/tests/integration/Api/Autocomplete/BudgetControllerTest.php
+++ b/tests/integration/Api/Autocomplete/BudgetControllerTest.php
@@ -46,14 +46,15 @@ final class BudgetControllerTest extends TestCase
protected function createAuthenticatedUser(): User
{
- $userGroup = UserGroup::create(['title' => 'Test Group']);
+ $userGroup = UserGroup::create(['title' => 'Test Group']);
- $user= User::create([
+ $user = User::create([
'email' => 'test@email.com',
'password' => 'password',
]);
$user->user_group_id = $userGroup->id;
$user->save();
+
return $user;
}
diff --git a/tests/integration/Api/Autocomplete/CategoryControllerTest.php b/tests/integration/Api/Autocomplete/CategoryControllerTest.php
index d360bbb000..7cdc632c9d 100644
--- a/tests/integration/Api/Autocomplete/CategoryControllerTest.php
+++ b/tests/integration/Api/Autocomplete/CategoryControllerTest.php
@@ -46,14 +46,15 @@ final class CategoryControllerTest extends TestCase
protected function createAuthenticatedUser(): User
{
- $userGroup = UserGroup::create(['title' => 'Test Group']);
+ $userGroup = UserGroup::create(['title' => 'Test Group']);
- $user= User::create([
+ $user = User::create([
'email' => 'test@email.com',
'password' => 'password',
]);
$user->user_group_id = $userGroup->id;
$user->save();
+
return $user;
}
diff --git a/tests/integration/Api/Autocomplete/CurrencyControllerTest.php b/tests/integration/Api/Autocomplete/CurrencyControllerTest.php
index cc1f64a56a..577dd57ac7 100644
--- a/tests/integration/Api/Autocomplete/CurrencyControllerTest.php
+++ b/tests/integration/Api/Autocomplete/CurrencyControllerTest.php
@@ -30,7 +30,6 @@ use Tests\integration\TestCase;
use FireflyIII\User;
use FireflyIII\Models\UserGroup;
-
/**
* Class CurrencyControllerTest
*
@@ -38,7 +37,8 @@ use FireflyIII\Models\UserGroup;
*
* @coversNothing
*/
-final class CurrencyControllerTest extends TestCase {
+final class CurrencyControllerTest extends TestCase
+{
/**
* @covers \FireflyIII\Api\V1\Controllers\Autocomplete\CurrencyController
*/
@@ -46,15 +46,16 @@ final class CurrencyControllerTest extends TestCase {
protected function createAuthenticatedUser(): User
{
- $userGroup = UserGroup::create(['title' => 'Test Group']);
+ $userGroup = UserGroup::create(['title' => 'Test Group']);
- $user= User::create([
+ $user = User::create([
'email' => 'test@email.com',
'password' => 'password',
]);
$user->user_group_id = $userGroup->id;
$user->save();
+
return $user;
}
@@ -62,11 +63,11 @@ final class CurrencyControllerTest extends TestCase {
{
for ($i = 1; $i <= $count; ++$i) {
$currency = TransactionCurrency::create([
- 'name' => 'Currency '.$i,
- 'code' => 'CUR'.$i,
- 'symbol' => 'C'.$i,
+ 'name' => 'Currency '.$i,
+ 'code' => 'CUR'.$i,
+ 'symbol' => 'C'.$i,
'decimal_places' => $i,
- 'enabled' => $enabled
+ 'enabled' => $enabled,
]);
}
}
@@ -162,13 +163,11 @@ final class CurrencyControllerTest extends TestCase {
$response->assertJsonCount(1);
-}
-
-
+ }
public function testGivenAuthenticatedRequestWhenCallingTheCurrenciesEndpointWithQueryThenReturnsCurrenciesThatMatchQuery(): void
{
- $user = $this->createAuthenticatedUser();
+ $user = $this->createAuthenticatedUser();
$this->actingAs($user);
$this->createTestCurrencies(20, true);
@@ -178,9 +177,7 @@ final class CurrencyControllerTest extends TestCase {
]), ['Accept' => 'application/json']);
$response->assertStatus(200);
$response->assertHeader('Content-Type', 'application/json');
- // Currency 1, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19 (11)
+ // Currency 1, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19 (11)
$response->assertJsonCount(11);
}
-
-
-}
\ No newline at end of file
+}
diff --git a/tests/integration/Api/Autocomplete/ObjectGroupControllerTest.php b/tests/integration/Api/Autocomplete/ObjectGroupControllerTest.php
index b68912450e..189290e319 100644
--- a/tests/integration/Api/Autocomplete/ObjectGroupControllerTest.php
+++ b/tests/integration/Api/Autocomplete/ObjectGroupControllerTest.php
@@ -37,26 +37,28 @@ use FireflyIII\Models\UserGroup;
*
* @coversNothing
*/
-final class ObjectGroupControllerTest extends TestCase {
+final class ObjectGroupControllerTest extends TestCase
+{
/**
* @covers \FireflyIII\Api\V1\Controllers\Autocomplete\ObjectGroupController
*/
use RefreshDatabase;
+
protected function createAuthenticatedUser(): User
{
- $userGroup = UserGroup::create(['title' => 'Test Group']);
+ $userGroup = UserGroup::create(['title' => 'Test Group']);
- $user= User::create([
+ $user = User::create([
'email' => 'test@email.com',
'password' => 'password',
]);
$user->user_group_id = $userGroup->id;
$user->save();
+
return $user;
}
-
private function createTestObjectGroups(int $count, User $user): void
{
for ($i = 1; $i <= $count; ++$i) {
@@ -89,7 +91,6 @@ final class ObjectGroupControllerTest extends TestCase {
$response->assertHeader('Content-Type', 'application/json');
}
-
public function testGivenAuthenticatedRequestWhenCallingTheObjectGroupsEndpointThenReturnsObjectGroups(): void
{
$user = $this->createAuthenticatedUser();
@@ -105,7 +106,7 @@ final class ObjectGroupControllerTest extends TestCase {
'*' => [
'id',
'name',
- 'title'
+ 'title',
],
]);
}
@@ -152,6 +153,4 @@ final class ObjectGroupControllerTest extends TestCase {
$response->assertJsonCount(11);
$response->assertJsonMissing(['name' => 'Object Group 2']);
}
-
-
-}
\ No newline at end of file
+}