Compare commits

..

108 Commits

Author SHA1 Message Date
James Cole
58b3338f6c Expand layout 2026-05-25 19:45:50 +02:00
James Cole
eee46562be Expand index. 2026-05-25 19:36:08 +02:00
James Cole
0579049b8b Merge branch 'develop' into adminlte 2026-05-25 13:40:19 +02:00
James Cole
db73ae39d1 Merge pull request #12288 from firefly-iii/dependabot/npm_and_yarn/develop/vite-8.0.14
Bump vite from 8.0.13 to 8.0.14
2026-05-25 13:39:38 +02:00
James Cole
972d75dc41 Merge pull request #12290 from firefly-iii/dependabot/npm_and_yarn/develop/date-fns-4.3.0
Bump date-fns from 4.1.0 to 4.3.0
2026-05-25 13:39:23 +02:00
James Cole
7891c24f5c Merge pull request #12291 from firefly-iii/dependabot/npm_and_yarn/develop/webpack-5.107.1
Bump webpack from 5.105.4 to 5.107.1
2026-05-25 13:39:03 +02:00
dependabot[bot]
7fa4d67a3f Bump webpack from 5.105.4 to 5.107.1
Bumps [webpack](https://github.com/webpack/webpack) from 5.105.4 to 5.107.1.
- [Release notes](https://github.com/webpack/webpack/releases)
- [Changelog](https://github.com/webpack/webpack/blob/main/CHANGELOG.md)
- [Commits](https://github.com/webpack/webpack/compare/v5.105.4...v5.107.1)

---
updated-dependencies:
- dependency-name: webpack
  dependency-version: 5.107.1
  dependency-type: direct:development
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-05-25 06:37:17 +00:00
github-actions[bot]
bd2e830637 Merge pull request #12293 from firefly-iii/release-1779690884
🤖 Automatically merge the PR into the develop branch.
2026-05-25 08:34:52 +02:00
JC5
b1bb0b1e84 🤖 Auto commit for release 'develop' on 2026-05-25 2026-05-25 08:34:45 +02:00
James Cole
673e3a21f9 Had the case right the first time, duh. 2026-05-25 08:29:33 +02:00
James Cole
5e4d6bbdb5 Merge branch 'develop' into adminlte 2026-05-25 08:22:43 +02:00
James Cole
a240074343 Fix case 2026-05-25 08:22:26 +02:00
James Cole
3cd030cd69 Expand code for boxes. 2026-05-25 08:22:13 +02:00
dependabot[bot]
12baa27de9 Bump date-fns from 4.1.0 to 4.3.0
Bumps [date-fns](https://github.com/date-fns/date-fns) from 4.1.0 to 4.3.0.
- [Release notes](https://github.com/date-fns/date-fns/releases)
- [Commits](https://github.com/date-fns/date-fns/compare/v4.1.0...v4.3.0)

---
updated-dependencies:
- dependency-name: date-fns
  dependency-version: 4.3.0
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-05-25 04:22:37 +00:00
dependabot[bot]
9e60d0ca0d Bump vite from 8.0.13 to 8.0.14
Bumps [vite](https://github.com/vitejs/vite/tree/HEAD/packages/vite) from 8.0.13 to 8.0.14.
- [Release notes](https://github.com/vitejs/vite/releases)
- [Changelog](https://github.com/vitejs/vite/blob/main/packages/vite/CHANGELOG.md)
- [Commits](https://github.com/vitejs/vite/commits/v8.0.14/packages/vite)

---
updated-dependencies:
- dependency-name: vite
  dependency-version: 8.0.14
  dependency-type: direct:development
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-05-25 04:22:28 +00:00
James Cole
b3bf43e6b2 Update pages. 2026-05-24 18:44:29 +02:00
James Cole
8115294582 Expand views and todos. 2026-05-24 16:22:14 +02:00
James Cole
b99c97740d Fix some icons 2026-05-24 14:15:47 +02:00
James Cole
e511b55c76 Expand v2 and v3 code. 2026-05-24 14:10:38 +02:00
James Cole
9ccb8e8527 Add new layout stuff. 2026-05-21 19:04:18 +02:00
James Cole
a86039aa78 Merge branch 'main' into develop 2026-05-21 14:59:59 +02:00
James Cole
2c14a605e4 Remove AI assistance disclosure comments
Removed AI assistance disclosure comments from the workflow.

Signed-off-by: James Cole <james@firefly-iii.org>
2026-05-21 12:32:32 +02:00
James Cole
3b94e0479a Merge branch 'main' into develop 2026-05-21 12:16:04 +02:00
James Cole
c08e3c8797 Add debug for the notification channel thing. 2026-05-21 12:15:48 +02:00
github-actions[bot]
1678c15905 Merge pull request #12276 from firefly-iii/develop
🤖 Automatically merge the PR into the main branch.
2026-05-21 06:59:51 +02:00
github-actions[bot]
37a3444816 Merge pull request #12275 from firefly-iii/release-1779339576
🤖 Automatically merge the PR into the develop branch.
2026-05-21 06:59:45 +02:00
JC5
008c9b4d8f 🤖 Auto commit for release 'v6.6.3' on 2026-05-21 2026-05-21 06:59:36 +02:00
github-actions[bot]
1c21154799 Merge pull request #12274 from firefly-iii/release-1779338975
🤖 Automatically merge the PR into the develop branch.
2026-05-21 06:49:43 +02:00
JC5
b8c05d6f26 🤖 Auto commit for release 'develop' on 2026-05-21 2026-05-21 06:49:35 +02:00
James Cole
85998cd3d7 Fix mago issues. 2026-05-21 06:44:16 +02:00
James Cole
67a048c279 Fix issues. 2026-05-21 06:38:35 +02:00
James Cole
b81943fad6 Lots of mago fixes applied. 2026-05-21 06:31:24 +02:00
github-actions[bot]
9ee1b4587c Merge pull request #12273 from firefly-iii/release-1779337714
🤖 Automatically merge the PR into the develop branch.
2026-05-21 06:28:41 +02:00
JC5
7579ae2615 🤖 Auto commit for release 'develop' on 2026-05-21 2026-05-21 06:28:34 +02:00
James Cole
c002cb795d Fix date fns 2026-05-21 06:23:17 +02:00
James Cole
f00852aa6a Merge branch 'main' into develop 2026-05-21 06:22:28 +02:00
James Cole
3e26f21bc4 Fix patch and lock version. 2026-05-21 06:22:15 +02:00
James Cole
195fb6cdb7 Update pr-reply-no-disclosure.yml
Signed-off-by: James Cole <james@firefly-iii.org>
2026-05-21 06:07:37 +02:00
James Cole
034280ca17 Update changelog. 2026-05-20 20:53:55 +02:00
github-actions[bot]
c5ce9fd1e2 Merge pull request #12272 from firefly-iii/release-1779302299
🤖 Automatically merge the PR into the develop branch.
2026-05-20 20:38:28 +02:00
JC5
3d64f7fe08 🤖 Auto commit for release 'develop' on 2026-05-20 2026-05-20 20:38:20 +02:00
James Cole
f2efb69b76 Fix broken if statement 2026-05-20 20:30:30 +02:00
James Cole
7499a414f4 Expand changelog 2026-05-20 20:24:50 +02:00
James Cole
8b0f790a56 Merge branch 'main' into develop 2026-05-20 20:18:10 +02:00
James Cole
b70ed32952 Merge pull request #12271 from alanturing881/fix/stored-xss-ale-piggy-name
Fix stored XSS in audit log view via piggy bank name (ale.twig)
2026-05-20 20:16:16 +02:00
James Cole
9e511c822e Update pr-reply-no-disclosure.yml
Signed-off-by: James Cole <james@firefly-iii.org>
2026-05-20 20:12:40 +02:00
iaohkut
fa6c123595 Fix stored XSS in ALE view by HTML-escaping piggy bank name
The Twig template ale.twig rendered the piggy bank name from
AuditLogEntry.after.piggy using |raw, bypassing auto-escaping.
A user-controlled name containing HTML (e.g. <img onerror=...>)
would execute as JavaScript in any browser viewing the transaction
audit log (CWE-79).

Apply |e filter to escape only the user-controlled `name` parameter
before substitution into the trans() string. The |raw filter is
preserved because the `amount` parameter legitimately contains
<span> tags for currency styling.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
2026-05-20 11:07:57 -04:00
James Cole
ec1dfca2b5 Enhance PR workflow to check for author
Added logic to check for the author of the pull request.

Signed-off-by: James Cole <james@firefly-iii.org>
2026-05-19 08:15:40 +02:00
James Cole
bebd3b189e Merge pull request #12265 from firefly-iii/dependabot/npm_and_yarn/develop/vite-8.0.13
Bump vite from 8.0.11 to 8.0.13
2026-05-18 08:11:34 +02:00
github-actions[bot]
e3319dca5d Merge pull request #12266 from firefly-iii/release-1779078811
🤖 Automatically merge the PR into the develop branch.
2026-05-18 06:33:40 +02:00
JC5
a38cb85f55 🤖 Auto commit for release 'develop' on 2026-05-18 2026-05-18 06:33:31 +02:00
dependabot[bot]
0226673a01 Bump vite from 8.0.11 to 8.0.13
Bumps [vite](https://github.com/vitejs/vite/tree/HEAD/packages/vite) from 8.0.11 to 8.0.13.
- [Release notes](https://github.com/vitejs/vite/releases)
- [Changelog](https://github.com/vitejs/vite/blob/main/packages/vite/CHANGELOG.md)
- [Commits](https://github.com/vitejs/vite/commits/v8.0.13/packages/vite)

---
updated-dependencies:
- dependency-name: vite
  dependency-version: 8.0.13
  dependency-type: direct:development
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-05-18 04:27:29 +00:00
github-actions[bot]
7816f1be9b Merge pull request #12263 from firefly-iii/release-1779030686
🤖 Automatically merge the PR into the develop branch.
2026-05-17 17:11:33 +02:00
JC5
5878173e80 🤖 Auto commit for release 'develop' on 2026-05-17 2026-05-17 17:11:26 +02:00
github-actions[bot]
45c30f11bc Merge pull request #12260 from firefly-iii/release-1778986654
🤖 Automatically merge the PR into the develop branch.
2026-05-17 04:57:40 +02:00
JC5
fea97efdbf 🤖 Auto commit for release 'develop' on 2026-05-17 2026-05-17 04:57:34 +02:00
James Cole
fe0e8796ca Merge branch 'main' into develop 2026-05-17 04:50:57 +02:00
James Cole
e83c5b9f86 New workflow. 2026-05-17 04:50:34 +02:00
James Cole
9558f05947 Merge branch 'main' into develop 2026-05-17 04:29:39 +02:00
James Cole
f3d6bb0fb5 Possible fix for https://github.com/firefly-iii/firefly-iii/issues/12258 2026-05-17 04:28:06 +02:00
James Cole
57010cd2e0 Fix https://github.com/firefly-iii/firefly-iii/issues/12257 2026-05-17 04:26:45 +02:00
James Cole
9436eeacaf Update warning about AI-generated security advisories
Clarified consequences of reporting AI-generated security advisories.

Signed-off-by: James Cole <james@firefly-iii.org>
2026-05-17 03:44:01 +02:00
github-actions[bot]
7ddf395ea9 Merge pull request #12256 from firefly-iii/release-1778958406
🤖 Automatically merge the PR into the develop branch.
2026-05-16 21:06:52 +02:00
JC5
492c55bd76 🤖 Auto commit for release 'develop' on 2026-05-16 2026-05-16 21:06:46 +02:00
James Cole
894dea5c9c Fix https://github.com/firefly-iii/firefly-iii/issues/12254 as suggested by @imjuzcy 2026-05-16 21:01:50 +02:00
github-actions[bot]
fecf12790d Merge pull request #12255 from firefly-iii/release-1778957079
🤖 Automatically merge the PR into the develop branch.
2026-05-16 20:44:49 +02:00
JC5
883c083860 🤖 Auto commit for release 'develop' on 2026-05-16 2026-05-16 20:44:39 +02:00
James Cole
e059753c43 Merge branch 'main' into develop 2026-05-16 20:39:12 +02:00
James Cole
0bac0aaaee Add some debug logging. 2026-05-16 20:38:50 +02:00
James Cole
2a68c48e2a Update security reporting guidelines in security.md
Clarified instructions for reporting false security issues.

Signed-off-by: James Cole <james@firefly-iii.org>
2026-05-16 20:05:44 +02:00
James Cole
c394034876 Clarify AI hallucinations in security reporting
Reworded the third point to clarify AI hallucinations in security issues.

Signed-off-by: James Cole <james@firefly-iii.org>
2026-05-16 20:05:20 +02:00
James Cole
7bd91048ea Update security.md with reporting guidelines
Clarified reporting guidelines for security issues to prevent false reports.

Signed-off-by: James Cole <james@firefly-iii.org>
2026-05-16 20:03:49 +02:00
James Cole
d64bca7700 Merge branch 'main' into develop 2026-05-16 19:54:22 +02:00
James Cole
7d768cfa23 Add AI-generated security advisories section
Added a section regarding AI-generated security advisories to clarify reporting policies and potential consequences.

Signed-off-by: James Cole <james@firefly-iii.org>
2026-05-16 19:52:56 +02:00
James Cole
fd50fbf193 Merge branch 'main' into develop 2026-05-12 18:48:04 +02:00
James Cole
134c232f45 Merge branch 'develop' of github.com:firefly-iii/firefly-iii into develop 2026-05-12 18:47:48 +02:00
James Cole
ce603f50d8 Fix https://github.com/firefly-iii/firefly-iii/issues/12243 2026-05-12 18:45:33 +02:00
github-actions[bot]
3b7bff4c57 Merge pull request #12240 from firefly-iii/release-1778473850
🤖 Automatically merge the PR into the develop branch.
2026-05-11 06:30:59 +02:00
JC5
1485f99579 🤖 Auto commit for release 'develop' on 2026-05-11 2026-05-11 06:30:51 +02:00
James Cole
7d24783c49 Merge pull request #12238 from firefly-iii/dependabot/npm_and_yarn/develop/vite-8.0.11
Bump vite from 8.0.10 to 8.0.11
2026-05-11 06:09:04 +02:00
James Cole
c4ee3598e1 Merge pull request #12239 from firefly-iii/dependabot/github_actions/actions/dependency-review-action-5
Bump actions/dependency-review-action from 4 to 5
2026-05-11 06:08:49 +02:00
dependabot[bot]
8cf8e91448 Bump actions/dependency-review-action from 4 to 5
Bumps [actions/dependency-review-action](https://github.com/actions/dependency-review-action) from 4 to 5.
- [Release notes](https://github.com/actions/dependency-review-action/releases)
- [Commits](https://github.com/actions/dependency-review-action/compare/v4...v5)

---
updated-dependencies:
- dependency-name: actions/dependency-review-action
  dependency-version: '5'
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-05-11 03:56:03 +00:00
dependabot[bot]
28f2de0df7 Bump vite from 8.0.10 to 8.0.11
Bumps [vite](https://github.com/vitejs/vite/tree/HEAD/packages/vite) from 8.0.10 to 8.0.11.
- [Release notes](https://github.com/vitejs/vite/releases)
- [Changelog](https://github.com/vitejs/vite/blob/main/packages/vite/CHANGELOG.md)
- [Commits](https://github.com/vitejs/vite/commits/v8.0.11/packages/vite)

---
updated-dependencies:
- dependency-name: vite
  dependency-version: 8.0.11
  dependency-type: direct:development
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-05-11 03:54:53 +00:00
github-actions[bot]
86adf11263 Merge pull request #12229 from firefly-iii/release-1778308665
🤖 Automatically merge the PR into the develop branch.
2026-05-09 08:37:52 +02:00
JC5
045f875041 🤖 Auto commit for release 'develop' on 2026-05-09 2026-05-09 08:37:45 +02:00
James Cole
f781e9f2b6 Merge branch 'develop' of github.com:firefly-iii/firefly-iii into develop
# Conflicts:
#	package-lock.json
2026-05-09 08:32:43 +02:00
James Cole
5eb52812f0 Merge branch 'main' into develop
# Conflicts:
#	package-lock.json
2026-05-09 08:32:08 +02:00
James Cole
916abd8464 Merge pull request #12228 from firefly-iii/dependabot/npm_and_yarn/npm_and_yarn-3d438dea79
Bump @babel/plugin-transform-modules-systemjs from 7.29.0 to 7.29.4 in the npm_and_yarn group across 1 directory
2026-05-09 08:27:14 +02:00
dependabot[bot]
6baca9510f Bump @babel/plugin-transform-modules-systemjs
Bumps the npm_and_yarn group with 1 update in the / directory: [@babel/plugin-transform-modules-systemjs](https://github.com/babel/babel/tree/HEAD/packages/babel-plugin-transform-modules-systemjs).


Updates `@babel/plugin-transform-modules-systemjs` from 7.29.0 to 7.29.4
- [Release notes](https://github.com/babel/babel/releases)
- [Changelog](https://github.com/babel/babel/blob/main/CHANGELOG.md)
- [Commits](https://github.com/babel/babel/commits/v7.29.4/packages/babel-plugin-transform-modules-systemjs)

---
updated-dependencies:
- dependency-name: "@babel/plugin-transform-modules-systemjs"
  dependency-version: 7.29.4
  dependency-type: indirect
  dependency-group: npm_and_yarn
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-05-09 05:54:10 +00:00
github-actions[bot]
5c22a40849 Merge pull request #12227 from firefly-iii/release-1778303410
🤖 Automatically merge the PR into the develop branch.
2026-05-09 07:10:19 +02:00
JC5
51e994056a 🤖 Auto commit for release 'develop' on 2026-05-09 2026-05-09 07:10:10 +02:00
James Cole
984e735bc1 Fix https://github.com/firefly-iii/firefly-iii/issues/12223 2026-05-09 07:02:06 +02:00
James Cole
c1a271d9c4 Merge pull request #12226 from firefly-iii/dependabot/npm_and_yarn/npm_and_yarn-053c9c4054 2026-05-09 05:50:33 +02:00
dependabot[bot]
0f9a2f010c Bump fast-uri in the npm_and_yarn group across 1 directory
Bumps the npm_and_yarn group with 1 update in the / directory: [fast-uri](https://github.com/fastify/fast-uri).


Updates `fast-uri` from 3.1.0 to 3.1.2
- [Release notes](https://github.com/fastify/fast-uri/releases)
- [Commits](https://github.com/fastify/fast-uri/compare/v3.1.0...v3.1.2)

---
updated-dependencies:
- dependency-name: fast-uri
  dependency-version: 3.1.2
  dependency-type: indirect
  dependency-group: npm_and_yarn
...

Signed-off-by: dependabot[bot] <support@github.com>
2026-05-08 23:26:04 +00:00
James Cole
ed9557aaa0 Merge branch 'develop' of github.com:firefly-iii/firefly-iii into develop 2026-05-05 19:52:46 +02:00
James Cole
1cc471fcc4 New guidelines. 2026-05-05 19:51:57 +02:00
github-actions[bot]
6c27424bfe Merge pull request #12219 from firefly-iii/release-1777868588
🤖 Automatically merge the PR into the develop branch.
2026-05-04 06:23:15 +02:00
JC5
38576f7fe0 🤖 Auto commit for release 'develop' on 2026-05-04 2026-05-04 06:23:09 +02:00
github-actions[bot]
5b80a5bdbe Merge pull request #12215 from firefly-iii/release-1777795578
🤖 Automatically merge the PR into the develop branch.
2026-05-03 10:06:25 +02:00
JC5
0202f4abd9 🤖 Auto commit for release 'develop' on 2026-05-03 2026-05-03 10:06:18 +02:00
James Cole
615d568479 Change sentence 2026-05-03 10:00:29 +02:00
github-actions[bot]
2ace0d3f23 Merge pull request #12214 from firefly-iii/release-1777794370
🤖 Automatically merge the PR into the develop branch.
2026-05-03 09:46:17 +02:00
JC5
42204f8dc1 🤖 Auto commit for release 'develop' on 2026-05-03 2026-05-03 09:46:10 +02:00
James Cole
cfac8fa569 Merge branch 'develop' of github.com:firefly-iii/firefly-iii into develop 2026-05-03 09:24:38 +02:00
James Cole
04704392f3 Fix amount display in budget overview. 2026-05-03 09:24:03 +02:00
github-actions[bot]
4b9bbc9d6a Merge pull request #12213 from firefly-iii/release-1777786936
🤖 Automatically merge the PR into the develop branch.
2026-05-03 07:42:23 +02:00
JC5
f24f535d39 🤖 Auto commit for release 'develop' on 2026-05-03 2026-05-03 07:42:17 +02:00
James Cole
3a9ac03358 Add entry in preferences. 2026-05-02 15:04:23 +02:00
328 changed files with 4739 additions and 1624 deletions

View File

@@ -294,42 +294,42 @@
},
{
"name": "ergebnis/agent-detector",
"version": "1.1.1",
"version": "1.2.0",
"source": {
"type": "git",
"url": "https://github.com/ergebnis/agent-detector.git",
"reference": "5b654a9f1ff8a5d2ce6a57568df5ae8801c87f64"
"reference": "e211f17928c8b95a51e06040792d57f5462fb271"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/ergebnis/agent-detector/zipball/5b654a9f1ff8a5d2ce6a57568df5ae8801c87f64",
"reference": "5b654a9f1ff8a5d2ce6a57568df5ae8801c87f64",
"url": "https://api.github.com/repos/ergebnis/agent-detector/zipball/e211f17928c8b95a51e06040792d57f5462fb271",
"reference": "e211f17928c8b95a51e06040792d57f5462fb271",
"shasum": ""
},
"require": {
"php": "~7.4.0 || ~8.0.0 || ~8.1.0 || ~8.2.0 || ~8.3.0 || ~8.4.0 || ~8.5.0 || ~8.6.0"
},
"require-dev": {
"ergebnis/composer-normalize": "^2.50.0",
"ergebnis/composer-normalize": "^2.51.0",
"ergebnis/license": "^2.7.0",
"ergebnis/php-cs-fixer-config": "^6.60.2",
"ergebnis/phpstan-rules": "^2.13.1",
"ergebnis/phpunit-slow-test-detector": "^2.24.0",
"ergebnis/rector-rules": "^1.16.0",
"ergebnis/rector-rules": "^1.18.1",
"fakerphp/faker": "^1.24.1",
"infection/infection": "^0.26.6",
"phpstan/extension-installer": "^1.4.3",
"phpstan/phpstan": "^2.1.46",
"phpstan/phpstan": "^2.1.54",
"phpstan/phpstan-deprecation-rules": "^2.0.4",
"phpstan/phpstan-phpunit": "^2.0.16",
"phpstan/phpstan-strict-rules": "^2.0.10",
"phpunit/phpunit": "^9.6.34",
"rector/rector": "^2.4.1"
"rector/rector": "^2.4.2"
},
"type": "library",
"extra": {
"branch-alias": {
"dev-main": "1.0-dev"
"dev-main": "1.2-dev"
},
"composer-normalize": {
"indent-size": 2,
@@ -359,7 +359,7 @@
"security": "https://github.com/ergebnis/agent-detector/blob/main/.github/SECURITY.md",
"source": "https://github.com/ergebnis/agent-detector"
},
"time": "2026-04-10T13:45:13+00:00"
"time": "2026-05-07T08:19:07+00:00"
},
{
"name": "evenement/evenement",
@@ -471,16 +471,16 @@
},
{
"name": "friendsofphp/php-cs-fixer",
"version": "v3.95.1",
"version": "v3.95.2",
"source": {
"type": "git",
"url": "https://github.com/PHP-CS-Fixer/PHP-CS-Fixer.git",
"reference": "a9727678fbd12997f1d9de8f4a37824ed9df1065"
"reference": "a28d88a5e172b27e78d0816992b15a9df3da20f1"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/PHP-CS-Fixer/PHP-CS-Fixer/zipball/a9727678fbd12997f1d9de8f4a37824ed9df1065",
"reference": "a9727678fbd12997f1d9de8f4a37824ed9df1065",
"url": "https://api.github.com/repos/PHP-CS-Fixer/PHP-CS-Fixer/zipball/a28d88a5e172b27e78d0816992b15a9df3da20f1",
"reference": "a28d88a5e172b27e78d0816992b15a9df3da20f1",
"shasum": ""
},
"require": {
@@ -512,8 +512,8 @@
"symfony/stopwatch": "^5.4.45 || ^6.4.24 || ^7.0 || ^8.0"
},
"require-dev": {
"facile-it/paraunit": "^1.3.1 || ^2.8.0",
"infection/infection": "^0.32.6",
"facile-it/paraunit": "^1.3.1 || ^2.11.0",
"infection/infection": "^0.32.7",
"justinrainbow/json-schema": "^6.8.0",
"keradus/cli-executor": "^2.3",
"mikey179/vfsstream": "^1.6.12",
@@ -564,7 +564,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.95.1"
"source": "https://github.com/PHP-CS-Fixer/PHP-CS-Fixer/tree/v3.95.2"
},
"funding": [
{
@@ -572,7 +572,7 @@
"type": "github"
}
],
"time": "2026-04-12T17:00:09+00:00"
"time": "2026-05-15T09:20:44+00:00"
},
{
"name": "psr/container",
@@ -1255,16 +1255,16 @@
},
{
"name": "sebastian/diff",
"version": "8.1.0",
"version": "8.3.0",
"source": {
"type": "git",
"url": "https://github.com/sebastianbergmann/diff.git",
"reference": "9c957d730257f49c873f3761674559bd90098a7d"
"reference": "b36d33b6e796513de7cb7df053afb3f55eefcd47"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/sebastianbergmann/diff/zipball/9c957d730257f49c873f3761674559bd90098a7d",
"reference": "9c957d730257f49c873f3761674559bd90098a7d",
"url": "https://api.github.com/repos/sebastianbergmann/diff/zipball/b36d33b6e796513de7cb7df053afb3f55eefcd47",
"reference": "b36d33b6e796513de7cb7df053afb3f55eefcd47",
"shasum": ""
},
"require": {
@@ -1277,7 +1277,7 @@
"type": "library",
"extra": {
"branch-alias": {
"dev-main": "8.1-dev"
"dev-main": "8.3-dev"
}
},
"autoload": {
@@ -1310,7 +1310,7 @@
"support": {
"issues": "https://github.com/sebastianbergmann/diff/issues",
"security": "https://github.com/sebastianbergmann/diff/security/policy",
"source": "https://github.com/sebastianbergmann/diff/tree/8.1.0"
"source": "https://github.com/sebastianbergmann/diff/tree/8.3.0"
},
"funding": [
{
@@ -1330,20 +1330,20 @@
"type": "tidelift"
}
],
"time": "2026-04-05T12:02:33+00:00"
"time": "2026-05-15T04:58:09+00:00"
},
{
"name": "symfony/console",
"version": "v8.0.9",
"version": "v8.0.11",
"source": {
"type": "git",
"url": "https://github.com/symfony/console.git",
"reference": "7113778e2e91f4709cb3194a75dfa9c0d028d94d"
"reference": "3156577f46a38aa1b9323aad223de7a9cd426782"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/console/zipball/7113778e2e91f4709cb3194a75dfa9c0d028d94d",
"reference": "7113778e2e91f4709cb3194a75dfa9c0d028d94d",
"url": "https://api.github.com/repos/symfony/console/zipball/3156577f46a38aa1b9323aad223de7a9cd426782",
"reference": "3156577f46a38aa1b9323aad223de7a9cd426782",
"shasum": ""
},
"require": {
@@ -1400,7 +1400,7 @@
"terminal"
],
"support": {
"source": "https://github.com/symfony/console/tree/v8.0.9"
"source": "https://github.com/symfony/console/tree/v8.0.11"
},
"funding": [
{
@@ -1420,20 +1420,20 @@
"type": "tidelift"
}
],
"time": "2026-04-29T15:02:55+00:00"
"time": "2026-05-13T12:07:53+00:00"
},
{
"name": "symfony/deprecation-contracts",
"version": "v3.6.0",
"version": "v3.7.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/deprecation-contracts.git",
"reference": "63afe740e99a13ba87ec199bb07bbdee937a5b62"
"reference": "50f59d1f3ca46d41ac911f97a78626b6756af35b"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/deprecation-contracts/zipball/63afe740e99a13ba87ec199bb07bbdee937a5b62",
"reference": "63afe740e99a13ba87ec199bb07bbdee937a5b62",
"url": "https://api.github.com/repos/symfony/deprecation-contracts/zipball/50f59d1f3ca46d41ac911f97a78626b6756af35b",
"reference": "50f59d1f3ca46d41ac911f97a78626b6756af35b",
"shasum": ""
},
"require": {
@@ -1446,7 +1446,7 @@
"name": "symfony/contracts"
},
"branch-alias": {
"dev-main": "3.6-dev"
"dev-main": "3.7-dev"
}
},
"autoload": {
@@ -1471,7 +1471,7 @@
"description": "A generic function and convention to trigger deprecation notices",
"homepage": "https://symfony.com",
"support": {
"source": "https://github.com/symfony/deprecation-contracts/tree/v3.6.0"
"source": "https://github.com/symfony/deprecation-contracts/tree/v3.7.0"
},
"funding": [
{
@@ -1482,12 +1482,16 @@
"url": "https://github.com/fabpot",
"type": "github"
},
{
"url": "https://github.com/nicolas-grekas",
"type": "github"
},
{
"url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
"type": "tidelift"
}
],
"time": "2024-09-25T14:21:43+00:00"
"time": "2026-04-13T15:52:40+00:00"
},
{
"name": "symfony/event-dispatcher",
@@ -1576,16 +1580,16 @@
},
{
"name": "symfony/event-dispatcher-contracts",
"version": "v3.6.0",
"version": "v3.7.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/event-dispatcher-contracts.git",
"reference": "59eb412e93815df44f05f342958efa9f46b1e586"
"reference": "ccba7060602b7fed0b03c85bf025257f76d9ef32"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/event-dispatcher-contracts/zipball/59eb412e93815df44f05f342958efa9f46b1e586",
"reference": "59eb412e93815df44f05f342958efa9f46b1e586",
"url": "https://api.github.com/repos/symfony/event-dispatcher-contracts/zipball/ccba7060602b7fed0b03c85bf025257f76d9ef32",
"reference": "ccba7060602b7fed0b03c85bf025257f76d9ef32",
"shasum": ""
},
"require": {
@@ -1599,7 +1603,7 @@
"name": "symfony/contracts"
},
"branch-alias": {
"dev-main": "3.6-dev"
"dev-main": "3.7-dev"
}
},
"autoload": {
@@ -1632,7 +1636,7 @@
"standards"
],
"support": {
"source": "https://github.com/symfony/event-dispatcher-contracts/tree/v3.6.0"
"source": "https://github.com/symfony/event-dispatcher-contracts/tree/v3.7.0"
},
"funding": [
{
@@ -1643,25 +1647,29 @@
"url": "https://github.com/fabpot",
"type": "github"
},
{
"url": "https://github.com/nicolas-grekas",
"type": "github"
},
{
"url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
"type": "tidelift"
}
],
"time": "2024-09-25T14:21:43+00:00"
"time": "2026-01-05T13:30:16+00:00"
},
{
"name": "symfony/filesystem",
"version": "v8.0.9",
"version": "v8.0.11",
"source": {
"type": "git",
"url": "https://github.com/symfony/filesystem.git",
"reference": "d1ec4543d5c6c2dac78503c2fae5ea0b3608ce40"
"reference": "224db910898ce1317b892a9a1338f1f8f17eb7c7"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/filesystem/zipball/d1ec4543d5c6c2dac78503c2fae5ea0b3608ce40",
"reference": "d1ec4543d5c6c2dac78503c2fae5ea0b3608ce40",
"url": "https://api.github.com/repos/symfony/filesystem/zipball/224db910898ce1317b892a9a1338f1f8f17eb7c7",
"reference": "224db910898ce1317b892a9a1338f1f8f17eb7c7",
"shasum": ""
},
"require": {
@@ -1698,7 +1706,7 @@
"description": "Provides basic utilities for the filesystem",
"homepage": "https://symfony.com",
"support": {
"source": "https://github.com/symfony/filesystem/tree/v8.0.9"
"source": "https://github.com/symfony/filesystem/tree/v8.0.11"
},
"funding": [
{
@@ -1718,7 +1726,7 @@
"type": "tidelift"
}
],
"time": "2026-04-18T13:51:42+00:00"
"time": "2026-05-11T16:39:47+00:00"
},
{
"name": "symfony/finder",
@@ -2440,16 +2448,16 @@
},
{
"name": "symfony/process",
"version": "v8.0.8",
"version": "v8.0.11",
"source": {
"type": "git",
"url": "https://github.com/symfony/process.git",
"reference": "cb8939aff03470d1a9d1d1b66d08c6fa71b3bbdc"
"reference": "26d89e459f037d2873300605d0a07e7a8ef84db0"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/process/zipball/cb8939aff03470d1a9d1d1b66d08c6fa71b3bbdc",
"reference": "cb8939aff03470d1a9d1d1b66d08c6fa71b3bbdc",
"url": "https://api.github.com/repos/symfony/process/zipball/26d89e459f037d2873300605d0a07e7a8ef84db0",
"reference": "26d89e459f037d2873300605d0a07e7a8ef84db0",
"shasum": ""
},
"require": {
@@ -2481,7 +2489,7 @@
"description": "Executes commands in sub-processes",
"homepage": "https://symfony.com",
"support": {
"source": "https://github.com/symfony/process/tree/v8.0.8"
"source": "https://github.com/symfony/process/tree/v8.0.11"
},
"funding": [
{
@@ -2501,20 +2509,20 @@
"type": "tidelift"
}
],
"time": "2026-03-30T15:14:47+00:00"
"time": "2026-05-11T16:56:32+00:00"
},
{
"name": "symfony/service-contracts",
"version": "v3.6.1",
"version": "v3.7.0",
"source": {
"type": "git",
"url": "https://github.com/symfony/service-contracts.git",
"reference": "45112560a3ba2d715666a509a0bc9521d10b6c43"
"reference": "d25d82433a80eba6aa0e6c24b61d7370d99e444a"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/service-contracts/zipball/45112560a3ba2d715666a509a0bc9521d10b6c43",
"reference": "45112560a3ba2d715666a509a0bc9521d10b6c43",
"url": "https://api.github.com/repos/symfony/service-contracts/zipball/d25d82433a80eba6aa0e6c24b61d7370d99e444a",
"reference": "d25d82433a80eba6aa0e6c24b61d7370d99e444a",
"shasum": ""
},
"require": {
@@ -2532,7 +2540,7 @@
"name": "symfony/contracts"
},
"branch-alias": {
"dev-main": "3.6-dev"
"dev-main": "3.7-dev"
}
},
"autoload": {
@@ -2568,7 +2576,7 @@
"standards"
],
"support": {
"source": "https://github.com/symfony/service-contracts/tree/v3.6.1"
"source": "https://github.com/symfony/service-contracts/tree/v3.7.0"
},
"funding": [
{
@@ -2588,7 +2596,7 @@
"type": "tidelift"
}
],
"time": "2025-07-15T11:30:57+00:00"
"time": "2026-03-28T09:44:51+00:00"
},
{
"name": "symfony/stopwatch",
@@ -2658,16 +2666,16 @@
},
{
"name": "symfony/string",
"version": "v8.0.8",
"version": "v8.0.11",
"source": {
"type": "git",
"url": "https://github.com/symfony/string.git",
"reference": "ae9488f874d7603f9d2dfbf120203882b645d963"
"reference": "39be2ad058a3c0bd558edca23e65f009865d75ff"
},
"dist": {
"type": "zip",
"url": "https://api.github.com/repos/symfony/string/zipball/ae9488f874d7603f9d2dfbf120203882b645d963",
"reference": "ae9488f874d7603f9d2dfbf120203882b645d963",
"url": "https://api.github.com/repos/symfony/string/zipball/39be2ad058a3c0bd558edca23e65f009865d75ff",
"reference": "39be2ad058a3c0bd558edca23e65f009865d75ff",
"shasum": ""
},
"require": {
@@ -2724,7 +2732,7 @@
"utf8"
],
"support": {
"source": "https://github.com/symfony/string/tree/v8.0.8"
"source": "https://github.com/symfony/string/tree/v8.0.11"
},
"funding": [
{
@@ -2744,7 +2752,7 @@
"type": "tidelift"
}
],
"time": "2026-03-30T15:14:47+00:00"
"time": "2026-05-13T12:07:53+00:00"
}
],
"packages-dev": [],

View File

@@ -1,3 +1,5 @@
# [Contributing guidelines](https://docs.firefly-iii.org/explanation/support/#contributing-code)
# Contributing guidelines
[Contributing guidelines](https://docs.firefly-iii.org/explanation/support/#contributing-code)
This repository is part of "Firefly III", by being either a main repository for code, a supporting repository with guidelines and documentation, or a repository with tools and secondary code.
The [contribution guidelines](https://docs.firefly-iii.org/explanation/contributing/) for this repository are the same as they are for ALL Firefly III related repositories, and they can be found in [the Firefly III documentation](https://docs.firefly-iii.org/explanation/contributing/).

View File

@@ -38,9 +38,11 @@ Example: Fixes #1234. See also #3456.
#### AI usage disclosure
<!--
If AI tools were involved in creating this PR, please check all boxes that apply
If AI tools were involved in creating this PR, please check all boxes that apply
below and make sure that you adhere to our Automated Contributions Policy:
https://docs.firefly-iii.org/explanation/support/#automated-contributions-policy
If you remove or skip this disclosure, your PR may be ignored.
-->
I used AI assistance for:
- [ ] Code generation (e.g., when writing an implementation or fixing a bug)

9
.github/security.md vendored
View File

@@ -3,6 +3,15 @@
Firefly III is an application to manage your personal finances. As such, the developer has adopted this security
disclosure and response policy to ensure that critical issues are responsibly handled.
## AI-generated security advisories
> [!WARNING]
> Due to a large number of irrelevant, noisy and uninformed AI-generated security advisories coming my way, reporting any the following security issues may result in a permanent ban from the Firefly III organization on GitHub.
1. Any SSRF in any user provided URL field (webhooks, ntfy, SimpleFIN, Slack). It's by design that users may set-up any URL they want, be it internal, private or non-existing.
2. Any XSS issue without a viable attack tree. If you can find a spot where Firefly III or the associated tools render unescaped data, it's not a security issue unless you can show me an actual attack that gets that data into the system.
3. Any issue that is not true. AI models have already *hallucinated* security issues in Firefly III. They've referred to **non-existing** functions, templates and files. Including line numbers and code excerpts. Validate your findings before you report them to me.
## Supported versions
Only the latest Firefly III release is maintained. Applicable fixes, including security fixes, will not be backported to

View File

@@ -13,4 +13,4 @@ jobs:
with:
fetch-depth: 0
- name: 'Dependency review'
uses: actions/dependency-review-action@v4
uses: actions/dependency-review-action@v5

View File

@@ -0,0 +1,61 @@
name: 'PRs - Check for AI disclosure'
# the workflow to execute on is comments that are newly created
on:
pull_request:
types: [ opened ]
# permissions needed for reacting to IssueOps commands on issues and PRs
permissions:
contents: read
pull-requests: write
issues: write
checks: read
jobs:
respond:
runs-on: ubuntu-latest
steps:
- run: |
BODY=$(gh pr view $NUMBER --json body)
AUTHOR=$(gh pr view $NUMBER --json author)
if [[ $AUTHOR == *"app/dependabot"* ]]; then
echo "Is dependabot, stop"
exit 0
fi
echo "Not dependabot!"
# $BODY must contain one of these four uses.
if [[ $BODY != *"Code generation"* &&
$BODY != *"Test/benchmark generation"* &&
$BODY != *"Documentation"* &&
$BODY != *"Research and understanding"* &&
$BODY != *"I used AI assistance for"* ]]; then
MESSAGE="Hi there!
This is an automated reply. \`Share and enjoy\`
You triggered an automated reply, because it seems you removed or changed the AI assistance disclosure from the PR template. Without a valid disclosure, your PR cannot be processed.
Even if you did not use AI, this disclosure must be present. Please reply to your PR and explain your use of AI in any or all of the following areas:
1. Code generation (e.g., when writing an implementation or fixing a bug)
2. Test/benchmark generation
3. Documentation (including examples)
4. Research and understanding
There cannot be interaction with your PR without this disclosure.
If the disclosure is present but the bot did not pick up on it, please accept my apologies for the intrusion. Contrary to other bots, this one is just a simple \`bash\` script and it may be wrong."
gh pr comment "$NUMBER" --body "$MESSAGE"
echo "Triggered on AI disclosure missing."
exit 0
fi
echo "It has the disclosure"
env:
NUMBER: ${{ github.event.pull_request.number }}
GH_TOKEN: ${{ github.token }}
GH_REPO: ${{ github.repository }}

3
.gitignore vendored
View File

@@ -28,3 +28,6 @@ public/v1/js/webhooks
resources/assets/v2/node_modules
resources/assets/v2/build
public/v2/i18n
# ignore v3 build files
resources/assets/v3/node_modules

View File

@@ -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.
## 2026
- iaohkut
- tasnim0tantawi
- Joe Longendyke
- Daniel Holøien

View File

@@ -87,7 +87,7 @@ final class PurgeController extends Controller
Rule::whereUserId($user->id)->onlyTrashed()->forceDelete();
// notes (this will actually purge EVERYBODY's deleted notes)
Note::onlyTrashed()->forceDelete();
Note::query()->onlyTrashed()->forceDelete();
// recurring transactions
Recurrence::whereUserId($user->id)->onlyTrashed()->forceDelete();

View File

@@ -158,10 +158,7 @@ final class TagController extends Controller
'currency_id' => (string) $foreignCurrencyId,
'currency_code' => $journal['foreign_currency_code'],
];
$response[$foreignKey]['difference'] = bcadd(
(string) $response[$foreignKey]['difference'],
Steam::positive($journal['foreign_amount'])
);
$response[$foreignKey]['difference'] = bcadd((string) $response[$foreignKey]['difference'], Steam::positive($journal['foreign_amount']));
$response[$foreignKey]['difference_float'] = (float) $response[$foreignKey]['difference'];
}
}

View File

@@ -155,10 +155,7 @@ final class TagController extends Controller
'currency_id' => (string) $foreignCurrencyId,
'currency_code' => $journal['foreign_currency_code'],
];
$response[$foreignKey]['difference'] = bcadd(
(string) $response[$foreignKey]['difference'],
Steam::positive($journal['foreign_amount'])
);
$response[$foreignKey]['difference'] = bcadd((string) $response[$foreignKey]['difference'], Steam::positive($journal['foreign_amount']));
$response[$foreignKey]['difference_float'] = (float) $response[$foreignKey]['difference']; // intentional float
}
}

View File

@@ -158,7 +158,7 @@ final class ConfigurationController extends Controller
$enableExternalRates = FireflyConfig::get('enable_external_rates', false);
$allowWebhooks = FireflyConfig::get('allow_webhooks', false);
$enableBatchProcessing = FireflyConfig::get('enable_batch_processing', false);
$validUrlProtocols = FireflyConfig::get('valid_url_protocols', 'http,https');
$validUrlProtocols = FireflyConfig::get('valid_url_protocols', config('firefly.valid_url_protocols'));
return [
'is_demo_site' => $isDemoSite?->data,
@@ -171,7 +171,7 @@ final class ConfigurationController extends Controller
'enable_external_rates' => $enableExternalRates?->data,
'allow_webhooks' => $allowWebhooks?->data,
'enable_batch_processing' => $enableBatchProcessing?->data,
'valid_url_protocols' => $validUrlProtocols->data ?? 'http,https',
'valid_url_protocols' => $validUrlProtocols->data ?? config('firefly.valid_url_protocols'),
];
}

View File

@@ -59,6 +59,6 @@ class AutocompleteRequest extends FormRequest
public function rules(): array
{
return ['date' => 'date|after:1970-01-02|before:2038-01-17'];
return ['date' => ['date', 'after:1970-01-02', 'before:2038-01-17']];
}
}

View File

@@ -60,11 +60,11 @@ class ChartRequest extends FormRequest
public function rules(): array
{
return [
'start' => 'required|date|after:1970-01-02|before:2038-01-17|before_or_equal:end',
'end' => 'required|date|after:1970-01-02|before:2038-01-17|after_or_equal:start',
'start' => ['required', 'date', 'after:1970-01-02', 'before:2038-01-17', 'before_or_equal:end'],
'end' => ['required', 'date', 'after:1970-01-02', 'before:2038-01-17', 'after_or_equal:start'],
'preselected' => sprintf('nullable|in:%s', implode(',', config('firefly.preselected_accounts'))),
'period' => sprintf('nullable|in:%s', implode(',', config('firefly.valid_view_ranges'))),
'accounts' => 'nullable|array',
'accounts' => ['nullable', 'array'],
'accounts.*' => 'exists:accounts,id',
];
}

View File

@@ -46,14 +46,11 @@ class MoveTransactionsRequest extends FormRequest
return ['original_account' => $this->convertInteger('original_account'), 'destination_account' => $this->convertInteger('destination_account')];
}
/**
* @return string[]
*/
public function rules(): array
{
return [
'original_account' => 'required|different:destination_account|belongsToUser:accounts,id',
'destination_account' => 'required|different:original_account|belongsToUser:accounts,id',
'original_account' => ['required', 'different:destination_account', 'belongsToUser:accounts,id'],
'destination_account' => ['required', 'different:original_account', 'belongsToUser:accounts,id'],
];
}

View File

@@ -72,6 +72,6 @@ class ExportRequest extends FormRequest
*/
public function rules(): array
{
return ['type' => 'in:csv', 'accounts' => 'min:1|max:32768', 'start' => 'date|before:end', 'end' => 'date|after:start'];
return ['type' => 'in:csv', 'accounts' => ['min:1', 'max:32768'], 'start' => ['date', 'before:end'], 'end' => ['date', 'after:start']];
}
}

View File

@@ -55,6 +55,6 @@ class SameDateRequest extends FormRequest
*/
public function rules(): array
{
return ['start' => 'required|date', 'end' => 'required|date|after_or_equal:start'];
return ['start' => ['required', 'date'], 'end' => ['required', 'date', 'after_or_equal:start']];
}
}

View File

@@ -56,6 +56,6 @@ class SingleDateRequest extends FormRequest
*/
public function rules(): array
{
return ['date' => 'required|date|after:1970-01-02|before:2038-01-17'];
return ['date' => ['required', 'date', 'after:1970-01-02', 'before:2038-01-17']];
}
}

View File

@@ -169,7 +169,7 @@ class GenericRequest extends FormRequest
$this->bills = new Collection();
$this->tags = new Collection();
return ['start' => 'required|date', 'end' => 'required|date|after_or_equal:start'];
return ['start' => ['required', 'date'], 'end' => ['required', 'date', 'after_or_equal:start']];
}
private function parseAccounts(): void

View File

@@ -99,29 +99,29 @@ class StoreRequest extends FormRequest
$ccPaymentTypes = implode(',', array_keys(config('firefly.ccTypes')));
$type = $this->convertString('type');
$rules = [
'name' => 'required|max:1024|min:1|uniqueAccountForUser',
'name' => ['required', 'max:1024', 'min:1', 'uniqueAccountForUser'],
'type' => sprintf('required|max:1024|min:1|in:%s', $types),
'iban' => ['iban', 'nullable', new UniqueIban(null, $type)],
'bic' => 'bic|nullable',
'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',
'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',
'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',
'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',
'notes' => ['min:0', 'max:32768'],
];
return Location::requestRules($rules);

View File

@@ -95,24 +95,24 @@ class UpdateRequest extends FormRequest
'name' => sprintf('min:1|max:1024|uniqueAccountForUser:%d', $account->id),
'type' => sprintf('in:%s', $types),
'iban' => ['iban', 'nullable', new UniqueIban($account, $this->convertString('type'))],
'bic' => 'bic|nullable',
'bic' => ['bic', 'nullable'],
'account_number' => ['min:1', 'max:255', 'nullable', new UniqueAccountNumber($account, $this->convertString('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:51|exists:transaction_currencies,code',
'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:51', 'exists:transaction_currencies,code'],
'active' => [new IsBoolean()],
'include_net_worth' => [new IsBoolean()],
'account_role' => sprintf('in:%s|nullable|required_if:type,asset', $accountRoles),
'credit_card_type' => sprintf('in:%s|nullable|required_if:account_role,ccAsset', $ccPaymentTypes),
'monthly_payment_date' => 'date|nullable|required_if:account_role,ccAsset|required_if:credit_card_type,monthlyFull',
'liability_type' => 'required_if:type,liability|in:loan,debt,mortgage',
'liability_direction' => 'required_if:type,liability|in:credit,debit',
'interest' => 'required_if:type,liability|min:0|max:100|numeric',
'interest_period' => 'required_if:type,liability|in:daily,monthly,yearly',
'notes' => 'min:0|max:32768',
'monthly_payment_date' => ['date', 'nullable', 'required_if:account_role,ccAsset', 'required_if:credit_card_type,monthlyFull'],
'liability_type' => ['required_if:type,liability', 'in:loan,debt,mortgage'],
'liability_direction' => ['required_if:type,liability', 'in:credit,debit'],
'interest' => ['required_if:type,liability', 'min:0', 'max:100', 'numeric'],
'interest_period' => ['required_if:type,liability', 'in:daily,monthly,yearly'],
'notes' => ['min:0', 'max:32768'],
];
return Location::requestRules($rules);

View File

@@ -64,9 +64,9 @@ class StoreRequest extends FormRequest
$model = $this->convertString('attachable_type');
return [
'filename' => 'required|min:1|max:255',
'filename' => ['required', 'min:1', 'max:255'],
'title' => ['min:1', 'max:255'],
'notes' => 'min:1|max:32768',
'notes' => ['min:1', 'max:32768'],
'attachable_type' => sprintf('required|in:%s', $models),
'attachable_id' => ['required', 'numeric', new IsValidAttachmentModel($model)],
];

View File

@@ -68,7 +68,7 @@ class UpdateRequest extends FormRequest
return [
'filename' => ['min:1', 'max:255'],
'title' => ['min:1', 'max:255'],
'notes' => 'min:1|max:32768',
'notes' => ['min:1', 'max:32768'],
'attachable_type' => sprintf('in:%s', $models),
'attachable_id' => ['numeric', new IsValidAttachmentModel($model)],
];

View File

@@ -65,11 +65,11 @@ class Request extends FormRequest
public function rules(): array
{
return [
'currency_id' => 'numeric|exists:transaction_currencies,id',
'currency_code' => 'min:3|max:51|exists:transaction_currencies,code',
'currency_id' => ['numeric', 'exists:transaction_currencies,id'],
'currency_code' => ['min:3', 'max:51', 'exists:transaction_currencies,code'],
'amount' => ['nullable', new IsValidPositiveAmount()],
'start' => 'date|after:1970-01-02|before:2038-01-17',
'end' => 'date|after:1970-01-02|before:2038-01-17',
'start' => ['date', 'after:1970-01-02', 'before:2038-01-17'],
'end' => ['date', 'after:1970-01-02', 'before:2038-01-17'],
];
}

View File

@@ -77,18 +77,18 @@ class StoreRequest extends FormRequest
public function rules(): array
{
return [
'name' => 'min:1|max:255|uniqueObjectForUser:bills,name',
'name' => ['min:1', 'max:255', 'uniqueObjectForUser:bills,name'],
'amount_min' => ['required', new IsValidPositiveAmount()],
'amount_max' => ['required', new IsValidPositiveAmount()],
'currency_id' => 'numeric|exists:transaction_currencies,id',
'currency_code' => 'min:3|max:51|exists:transaction_currencies,code',
'date' => 'date|required|after:1970-01-02|before:2038-01-17',
'end_date' => 'nullable|date|after:date|after:1970-01-02|before:2038-01-17',
'extension_date' => 'nullable|date|after:date|after:1970-01-02|before:2038-01-17',
'repeat_freq' => 'in:weekly,monthly,quarterly,half-year,yearly|required',
'skip' => 'min:0|max:31|numeric',
'currency_id' => ['numeric', 'exists:transaction_currencies,id'],
'currency_code' => ['min:3', 'max:51', 'exists:transaction_currencies,code'],
'date' => ['date', 'required', 'after:1970-01-02', 'before:2038-01-17'],
'end_date' => ['nullable', 'date', 'after:date', 'after:1970-01-02', 'before:2038-01-17'],
'extension_date' => ['nullable', 'date', 'after:date', 'after:1970-01-02', 'before:2038-01-17'],
'repeat_freq' => ['in:weekly,monthly,quarterly,half-year,yearly', 'required'],
'skip' => ['min:0', 'max:31', 'numeric'],
'active' => [new IsBoolean()],
'notes' => 'nullable|min:1|max:32768',
'notes' => ['nullable', 'min:1', 'max:32768'],
];
}

View File

@@ -81,15 +81,15 @@ class UpdateRequest extends FormRequest
'name' => sprintf('min:1|max:255|uniqueObjectForUser:bills,name,%d', $bill->id),
'amount_min' => ['nullable', new IsValidPositiveAmount()],
'amount_max' => ['nullable', new IsValidPositiveAmount()],
'currency_id' => 'numeric|exists:transaction_currencies,id',
'currency_code' => 'min:3|max:51|exists:transaction_currencies,code',
'date' => 'date|after:1970-01-02|before:2038-01-17',
'end_date' => 'date|after:date|after:1970-01-02|before:2038-01-17',
'extension_date' => 'date|after:date|after:1970-01-02|before:2038-01-17',
'currency_id' => ['numeric', 'exists:transaction_currencies,id'],
'currency_code' => ['min:3', 'max:51', 'exists:transaction_currencies,code'],
'date' => ['date', 'after:1970-01-02', 'before:2038-01-17'],
'end_date' => ['date', 'after:date', 'after:1970-01-02', 'before:2038-01-17'],
'extension_date' => ['date', 'after:date', 'after:1970-01-02', 'before:2038-01-17'],
'repeat_freq' => 'in:weekly,monthly,quarterly,half-year,yearly',
'skip' => 'min:0|max:31|numeric',
'skip' => ['min:0', 'max:31', 'numeric'],
'active' => [new IsBoolean()],
'notes' => 'min:1|max:32768',
'notes' => ['min:1', 'max:32768'],
];
}

View File

@@ -75,11 +75,11 @@ class StoreRequest extends FormRequest
public function rules(): array
{
return [
'name' => 'required|min:1|max:255|uniqueObjectForUser:budgets,name',
'name' => ['required', 'min:1', 'max:255', 'uniqueObjectForUser:budgets,name'],
'active' => [new IsBoolean()],
'currency_id' => 'exists:transaction_currencies,id',
'currency_code' => 'exists:transaction_currencies,code',
'notes' => 'nullable|min:1|max:32768',
'notes' => ['nullable', 'min:1', 'max:32768'],
// auto budget info
'auto_budget_type' => 'in:reset,rollover,adjusted,none',
'auto_budget_amount' => [
@@ -88,7 +88,12 @@ class StoreRequest extends FormRequest
'required_if:auto_budget_type,adjusted',
new IsValidPositiveAmount(),
],
'auto_budget_period' => 'in:daily,weekly,monthly,quarterly,half_year,yearly|required_if:auto_budget_type,reset|required_if:auto_budget_type,rollover|required_if:auto_budget_type,adjusted',
'auto_budget_period' => [
'in:daily,weekly,monthly,quarterly,half_year,yearly',
'required_if:auto_budget_type,reset',
'required_if:auto_budget_type,rollover',
'required_if:auto_budget_type,adjusted',
],
// webhooks
'fire_webhooks' => [new IsBoolean()],

View File

@@ -85,7 +85,7 @@ class UpdateRequest extends FormRequest
return [
'name' => sprintf('min:1|max:100|uniqueObjectForUser:budgets,name,%d', $budget->id),
'active' => [new IsBoolean()],
'notes' => 'nullable|min:1|max:32768',
'notes' => ['nullable', 'min:1', 'max:32768'],
'auto_budget_type' => 'in:reset,rollover,adjusted,none',
'auto_budget_currency_id' => 'exists:transaction_currencies,id',
'auto_budget_currency_code' => 'exists:transaction_currencies,code',

View File

@@ -71,12 +71,12 @@ class StoreRequest extends FormRequest
public function rules(): array
{
return [
'start' => 'required|before:end|date',
'end' => 'required|after:start|date',
'start' => ['required', 'before:end', 'date'],
'end' => ['required', 'after:start', 'date'],
'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',
'currency_id' => ['numeric', 'exists:transaction_currencies,id'],
'currency_code' => ['min:3', 'max:51', 'exists:transaction_currencies,code'],
'notes' => ['nullable', 'min:0', 'max:32768'],
// webhooks
'fire_webhooks' => [new IsBoolean()],

View File

@@ -73,12 +73,12 @@ class UpdateRequest extends FormRequest
public function rules(): array
{
return [
'start' => 'date|after:1970-01-02|before:2038-01-17',
'end' => 'date|after:1970-01-02|before:2038-01-17',
'start' => ['date', 'after:1970-01-02', 'before:2038-01-17'],
'end' => ['date', 'after:1970-01-02', 'before:2038-01-17'],
'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',
'currency_id' => ['numeric', 'exists:transaction_currencies,id'],
'currency_code' => ['min:3', 'max:51', 'exists:transaction_currencies,code'],
'notes' => ['nullable', 'min:0', 'max:32768'],
// webhooks
'fire_webhooks' => [new IsBoolean()],

View File

@@ -51,6 +51,6 @@ class StoreRequest extends FormRequest
*/
public function rules(): array
{
return ['name' => 'required|min:1|max:100|uniqueObjectForUser:categories,name'];
return ['name' => ['required', 'min:1', 'max:100', 'uniqueObjectForUser:categories,name']];
}
}

View File

@@ -48,7 +48,7 @@ class StoreByCurrenciesRequest extends FormRequest
*/
public function rules(): array
{
return ['*' => 'required|numeric|min:0.0000000001'];
return ['*' => ['required', 'numeric', 'min:0.0000000001']];
}
public function withValidator(Validator $validator): void

View File

@@ -54,12 +54,14 @@ class StoreByDateRequest extends FormRequest
/**
* The rules that the incoming request must be matched against.
*
* @return array<string, string>
*/
public function rules(): array
{
return ['from' => 'required|exists:transaction_currencies,code', 'rates' => 'required|array', 'rates.*' => 'required|numeric|min:0.0000000001'];
return [
'from' => ['required', 'exists:transaction_currencies,code'],
'rates' => ['required', 'array'],
'rates.*' => ['required', 'numeric', 'min:0.0000000001'],
];
}
public function withValidator(Validator $validator): void

View File

@@ -64,10 +64,10 @@ class StoreRequest extends FormRequest
public function rules(): array
{
return [
'date' => 'required|date|after:1970-01-02|before:2038-01-17',
'rate' => 'required|numeric|gt:0',
'from' => 'required|exists:transaction_currencies,code',
'to' => 'required|exists:transaction_currencies,code',
'date' => ['required', 'date', 'after:1970-01-02', 'before:2038-01-17'],
'rate' => ['required', 'numeric', 'gt:0'],
'from' => ['required', 'exists:transaction_currencies,code'],
'to' => ['required', 'exists:transaction_currencies,code'],
];
}
}

View File

@@ -52,10 +52,10 @@ class UpdateRequest extends FormRequest
public function rules(): array
{
return [
'date' => 'date|after:1970-01-02|before:2038-01-17',
'rate' => 'required|numeric|gt:0',
'from' => 'nullable|exists:transaction_currencies,code',
'to' => 'nullable|exists:transaction_currencies,code',
'date' => ['date', 'after:1970-01-02', 'before:2038-01-17'],
'rate' => ['required', 'numeric', 'gt:0'],
'from' => ['nullable', 'exists:transaction_currencies,code'],
'to' => ['nullable', 'exists:transaction_currencies,code'],
];
}
}

View File

@@ -71,18 +71,18 @@ class StoreRequest extends FormRequest
public function rules(): array
{
return [
'name' => 'required|min:1|max:255|uniquePiggyBankForUser',
'name' => ['required', 'min:1', 'max:255', 'uniquePiggyBankForUser'],
'accounts' => 'required',
'accounts.*' => 'array|required',
'accounts.*.account_id' => 'required|numeric|belongsToUser:accounts,id',
'accounts.*' => ['array', 'required'],
'accounts.*.account_id' => ['required', 'numeric', 'belongsToUser:accounts,id'],
'accounts.*.current_amount' => ['numeric', new IsValidZeroOrMoreAmount()],
'object_group_id' => 'numeric|belongsToUser:object_groups,id',
'object_group_id' => ['numeric', 'belongsToUser:object_groups,id'],
'object_group_title' => ['min:1', 'max:255'],
'target_amount' => ['required', new IsValidZeroOrMoreAmount()],
'start_date' => 'required|date|after:1970-01-01|before:2038-01-17',
'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',
'start_date' => ['required', 'date', 'after:1970-01-01', 'before:2038-01-17'],
'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',
];
}

View File

@@ -79,17 +79,17 @@ class UpdateRequest extends FormRequest
'name' => 'min:1|max:255|uniquePiggyBankForUser:'.$piggyBank->id,
'current_amount' => ['nullable', new LessThanPiggyTarget(), new IsValidPositiveAmount()],
'target_amount' => ['nullable', new IsValidZeroOrMoreAmount()],
'start_date' => 'date|nullable',
'target_date' => 'date|nullable|after:start_date',
'start_date' => ['date', 'nullable'],
'target_date' => ['date', 'nullable', 'after:start_date'],
'notes' => 'max:65000',
'accounts' => 'array',
'accounts.*' => 'array',
'accounts.*.account_id' => ['required', 'numeric', 'belongsToUser:accounts,id'],
'accounts.*.current_amount' => ['numeric', 'nullable', new IsValidZeroOrMoreAmount(true), new IsEnoughInAccounts($piggyBank, $this->getAll())],
'object_group_id' => 'numeric|belongsToUser:object_groups,id',
'object_group_id' => ['numeric', 'belongsToUser:object_groups,id'],
'object_group_title' => ['min:1', 'max:255'],
'transaction_currency_id' => 'exists:transaction_currencies,id|nullable',
'transaction_currency_code' => 'exists:transaction_currencies,code|nullable',
'transaction_currency_id' => ['exists:transaction_currencies,id', 'nullable'],
'transaction_currency_code' => ['exists:transaction_currencies,code', 'nullable'],
];
}
}

View File

@@ -78,40 +78,40 @@ class StoreRequest extends FormRequest
public function rules(): array
{
return [
'type' => 'required|in:withdrawal,transfer,deposit',
'title' => 'required|min:1|max:255|uniqueObjectForUser:recurrences,title',
'description' => 'min:1|max:32768',
'first_date' => 'required|date',
'type' => ['required', 'in:withdrawal,transfer,deposit'],
'title' => ['required', 'min:1', 'max:255', 'uniqueObjectForUser:recurrences,title'],
'description' => ['min:1', 'max:32768'],
'first_date' => ['required', 'date'],
'apply_rules' => [new IsBoolean()],
'active' => [new IsBoolean()],
'repeat_until' => 'nullable|date',
'nr_of_repetitions' => 'nullable|numeric|min:1|max:31',
'repeat_until' => ['nullable', 'date'],
'nr_of_repetitions' => ['nullable', 'numeric', 'min:1', 'max:31'],
'repetitions.*.type' => 'required|in:daily,weekly,ndom,monthly,yearly',
'repetitions.*.moment' => 'min:0|max:10',
'repetitions.*.skip' => 'nullable|numeric|min:0|max:31',
'repetitions.*.weekend' => 'numeric|min:1|max:4',
'repetitions.*.type' => ['required', 'in:daily,weekly,ndom,monthly,yearly'],
'repetitions.*.moment' => ['min:0', 'max:10'],
'repetitions.*.skip' => ['nullable', 'numeric', 'min:0', 'max:31'],
'repetitions.*.weekend' => ['numeric', 'min:1', 'max:4'],
'transactions.*.description' => 'required|min:1|max:255',
'transactions.*.description' => ['required', 'min:1', 'max:255'],
'transactions.*.amount' => ['required', new IsValidPositiveAmount()],
'transactions.*.foreign_amount' => ['nullable', new IsValidPositiveAmount()],
'transactions.*.currency_id' => 'nullable|numeric|exists:transaction_currencies,id',
'transactions.*.currency_code' => 'nullable|min:3|max:51|exists:transaction_currencies,code',
'transactions.*.foreign_currency_id' => 'nullable|numeric|exists:transaction_currencies,id',
'transactions.*.foreign_currency_code' => 'nullable|min:3|max:51|exists:transaction_currencies,code',
'transactions.*.currency_id' => ['nullable', 'numeric', 'exists:transaction_currencies,id'],
'transactions.*.currency_code' => ['nullable', 'min:3', 'max:51', 'exists:transaction_currencies,code'],
'transactions.*.foreign_currency_id' => ['nullable', 'numeric', 'exists:transaction_currencies,id'],
'transactions.*.foreign_currency_code' => ['nullable', 'min:3', 'max:51', 'exists:transaction_currencies,code'],
'transactions.*.source_id' => ['numeric', 'nullable', new BelongsUser()],
'transactions.*.source_name' => 'min:1|max:255|nullable',
'transactions.*.source_name' => ['min:1', 'max:255', 'nullable'],
'transactions.*.destination_id' => ['numeric', 'nullable', new BelongsUser()],
'transactions.*.destination_name' => 'min:1|max:255|nullable',
'transactions.*.destination_name' => ['min:1', 'max:255', 'nullable'],
// new and updated fields:
'transactions.*.budget_id' => ['nullable', 'mustExist:budgets,id', new BelongsUser()],
'transactions.*.budget_name' => ['min:1', 'max:255', 'nullable', new BelongsUser()],
'transactions.*.category_id' => ['nullable', 'mustExist:categories,id', new BelongsUser()],
'transactions.*.category_name' => 'min:1|max:255|nullable',
'transactions.*.category_name' => ['min:1', 'max:255', 'nullable'],
'transactions.*.piggy_bank_id' => ['nullable', 'numeric', 'mustExist:piggy_banks,id', new BelongsUser()],
'transactions.*.piggy_bank_name' => ['min:1', 'max:255', 'nullable', new BelongsUser()],
'transactions.*.tags' => 'nullable|min:1|max:255',
'transactions.*.tags' => ['nullable', 'min:1', 'max:255'],
];
}

View File

@@ -89,38 +89,38 @@ class UpdateRequest extends FormRequest
return [
'title' => sprintf('min:1|max:255|uniqueObjectForUser:recurrences,title,%d', $recurrence->id),
'description' => 'min:1|max:32768',
'first_date' => 'date|after:1970-01-02|before:2038-01-17',
'description' => ['min:1', 'max:32768'],
'first_date' => ['date', 'after:1970-01-02', 'before:2038-01-17'],
'apply_rules' => [new IsBoolean()],
'active' => [new IsBoolean()],
'repeat_until' => 'nullable|date',
'nr_of_repetitions' => 'nullable|numeric|min:1|max:31',
'repeat_until' => ['nullable', 'date'],
'nr_of_repetitions' => ['nullable', 'numeric', 'min:1', 'max:31'],
'repetitions.*.type' => 'in:daily,weekly,ndom,monthly,yearly',
'repetitions.*.moment' => 'min:0|max:10|numeric',
'repetitions.*.skip' => 'nullable|numeric|min:0|max:31',
'repetitions.*.weekend' => 'nullable|numeric|min:1|max:4',
'repetitions.*.moment' => ['min:0', 'max:10', 'numeric'],
'repetitions.*.skip' => ['nullable', 'numeric', 'min:0', 'max:31'],
'repetitions.*.weekend' => ['nullable', 'numeric', 'min:1', 'max:4'],
'transactions.*.description' => ['min:1', 'max:255'],
'transactions.*.amount' => [new IsValidPositiveAmount()],
'transactions.*.foreign_amount' => ['nullable', new IsValidPositiveAmount()],
'transactions.*.currency_id' => 'nullable|numeric|exists:transaction_currencies,id',
'transactions.*.currency_code' => 'nullable|min:3|max:51|exists:transaction_currencies,code',
'transactions.*.foreign_currency_id' => 'nullable|numeric|exists:transaction_currencies,id',
'transactions.*.foreign_currency_code' => 'nullable|min:3|max:51|exists:transaction_currencies,code',
'transactions.*.currency_id' => ['nullable', 'numeric', 'exists:transaction_currencies,id'],
'transactions.*.currency_code' => ['nullable', 'min:3', 'max:51', 'exists:transaction_currencies,code'],
'transactions.*.foreign_currency_id' => ['nullable', 'numeric', 'exists:transaction_currencies,id'],
'transactions.*.foreign_currency_code' => ['nullable', 'min:3', 'max:51', 'exists:transaction_currencies,code'],
'transactions.*.source_id' => ['numeric', 'nullable', new BelongsUser()],
'transactions.*.source_name' => 'min:1|max:255|nullable',
'transactions.*.source_name' => ['min:1', 'max:255', 'nullable'],
'transactions.*.destination_id' => ['numeric', 'nullable', new BelongsUser()],
'transactions.*.destination_name' => 'min:1|max:255|nullable',
'transactions.*.destination_name' => ['min:1', 'max:255', 'nullable'],
// new and updated fields:
'transactions.*.budget_id' => ['nullable', 'mustExist:budgets,id', new BelongsUser()],
'transactions.*.budget_name' => ['min:1', 'max:255', 'nullable', new BelongsUser()],
'transactions.*.category_id' => ['nullable', 'mustExist:categories,id', new BelongsUser()],
'transactions.*.category_name' => 'min:1|max:255|nullable',
'transactions.*.category_name' => ['min:1', 'max:255', 'nullable'],
'transactions.*.piggy_bank_id' => ['nullable', 'numeric', 'mustExist:piggy_banks,id', new BelongsUser()],
'transactions.*.piggy_bank_name' => ['min:1', 'max:255', 'nullable', new BelongsUser()],
'transactions.*.tags' => 'nullable|min:1|max:255',
'transactions.*.tags' => ['nullable', 'min:1', 'max:255'],
];
}

View File

@@ -80,11 +80,11 @@ class StoreRequest extends FormRequest
$contextActions = implode(',', config('firefly.context-rule-actions'));
return [
'title' => 'required|min:1|max:100|uniqueObjectForUser:rules,title',
'description' => 'min:1|max:32768|nullable',
'rule_group_id' => 'belongsToUser:rule_groups|required_without:rule_group_title',
'rule_group_title' => 'nullable|min:1|max:255|required_without:rule_group_id|belongsToUser:rule_groups,title',
'trigger' => 'required|in:store-journal,update-journal,manual-activation',
'title' => ['required', 'min:1', 'max:100', 'uniqueObjectForUser:rules,title'],
'description' => ['min:1', 'max:32768', 'nullable'],
'rule_group_id' => ['belongsToUser:rule_groups', 'required_without:rule_group_title'],
'rule_group_title' => ['nullable', 'min:1', 'max:255', 'required_without:rule_group_id', 'belongsToUser:rule_groups,title'],
'trigger' => ['required', 'in:store-journal,update-journal,manual-activation'],
'triggers.*.type' => 'required|in:'.implode(',', $validTriggers),
'triggers.*.value' => 'required_if:actions.*.type,'.$contextTriggers.'|min:1|ruleTriggerValue|max:1024',
'triggers.*.stop_processing' => [new IsBoolean()],

View File

@@ -47,10 +47,10 @@ class TestRequest extends FormRequest
public function rules(): array
{
return [
'start' => 'date|after:1970-01-02|before:2038-01-17',
'end' => 'date|after_or_equal:start|after:1970-01-02|before:2038-01-17',
'start' => ['date', 'after:1970-01-02', 'before:2038-01-17'],
'end' => ['date', 'after_or_equal:start', 'after:1970-01-02', 'before:2038-01-17'],
'accounts' => '',
'accounts.*' => 'required|exists:accounts,id|belongsToUser:accounts',
'accounts.*' => ['required', 'exists:accounts,id', 'belongsToUser:accounts'],
];
}

View File

@@ -47,10 +47,10 @@ class TriggerRequest extends FormRequest
public function rules(): array
{
return [
'start' => 'date|after:1970-01-02|before:2038-01-17',
'end' => 'date|after_or_equal:start|after:1970-01-02|before:2038-01-17',
'start' => ['date', 'after:1970-01-02', 'before:2038-01-17'],
'end' => ['date', 'after_or_equal:start', 'after:1970-01-02', 'before:2038-01-17'],
'accounts' => '',
'accounts.*' => 'exists:accounts,id|belongsToUser:accounts',
'accounts.*' => ['exists:accounts,id', 'belongsToUser:accounts'],
];
}

View File

@@ -91,9 +91,9 @@ class UpdateRequest extends FormRequest
return [
'title' => sprintf('min:1|max:100|uniqueObjectForUser:rules,title,%d', $rule->id),
'description' => 'min:1|max:32768|nullable',
'description' => ['min:1', 'max:32768', 'nullable'],
'rule_group_id' => 'belongsToUser:rule_groups',
'rule_group_title' => 'nullable|min:1|max:255|belongsToUser:rule_groups,title',
'rule_group_title' => ['nullable', 'min:1', 'max:255', 'belongsToUser:rule_groups,title'],
'trigger' => 'in:store-journal,update-journal,manual-activation',
'triggers.*.type' => 'required|in:'.implode(',', $validTriggers),
'triggers.*.value' => 'required_if:actions.*.type,'.$contextTriggers.'|min:1|ruleTriggerValue|max:1024',
@@ -106,7 +106,7 @@ class UpdateRequest extends FormRequest
'strict' => [new IsBoolean()],
'stop_processing' => [new IsBoolean()],
'active' => [new IsBoolean()],
'order' => 'numeric|min:1|max:2048',
'order' => ['numeric', 'min:1', 'max:2048'],
];
}

View File

@@ -67,8 +67,8 @@ class StoreRequest extends FormRequest
public function rules(): array
{
return [
'title' => 'required|min:1|max:100|uniqueObjectForUser:rule_groups,title',
'description' => 'min:1|max:32768|nullable',
'title' => ['required', 'min:1', 'max:100', 'uniqueObjectForUser:rule_groups,title'],
'description' => ['min:1', 'max:32768', 'nullable'],
'active' => [new IsBoolean()],
];
}

View File

@@ -47,10 +47,10 @@ class TestRequest extends FormRequest
public function rules(): array
{
return [
'start' => 'date|after:1970-01-02|before:2038-01-17',
'end' => 'date|after_or_equal:start|after:1970-01-02|before:2038-01-17',
'start' => ['date', 'after:1970-01-02', 'before:2038-01-17'],
'end' => ['date', 'after_or_equal:start', 'after:1970-01-02', 'before:2038-01-17'],
'accounts' => '',
'accounts.*' => 'exists:accounts,id|belongsToUser:accounts',
'accounts.*' => ['exists:accounts,id', 'belongsToUser:accounts'],
];
}

View File

@@ -46,7 +46,10 @@ class TriggerRequest extends FormRequest
public function rules(): array
{
return ['start' => 'date|after:1970-01-02|before:2038-01-17', 'end' => 'date|after_or_equal:start|after:1970-01-02|before:2038-01-17'];
return [
'start' => ['date', 'after:1970-01-02', 'before:2038-01-17'],
'end' => ['date', 'after_or_equal:start', 'after:1970-01-02', 'before:2038-01-17'],
];
}
private function getAccounts(): array

View File

@@ -66,7 +66,7 @@ class UpdateRequest extends FormRequest
return [
'title' => 'min:1|max:100|uniqueObjectForUser:rule_groups,title,'.$ruleGroup->id,
'description' => 'min:1|max:32768|nullable',
'description' => ['min:1', 'max:32768', 'nullable'],
'active' => [new IsBoolean()],
];
}

View File

@@ -62,9 +62,9 @@ class StoreRequest extends FormRequest
public function rules(): array
{
$rules = [
'tag' => 'required|min:1|uniqueObjectForUser:tags,tag|max:1024',
'description' => 'min:1|nullable|max:32768',
'date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'tag' => ['required', 'min:1', 'uniqueObjectForUser:tags,tag', 'max:1024'],
'description' => ['min:1', 'nullable', 'max:32768'],
'date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
];
return Location::requestRules($rules);

View File

@@ -63,8 +63,8 @@ class UpdateRequest extends FormRequest
$tag = $this->route()->parameter('tagOrId');
$rules = [
'tag' => 'min:1|max:1024|uniqueObjectForUser:tags,tag,'.$tag->id,
'description' => 'min:1|nullable|max:32768',
'date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'description' => ['min:1', 'nullable', 'max:32768'],
'date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
];
return Location::requestRules($rules);

View File

@@ -86,7 +86,7 @@ class StoreRequest extends FormRequest
return [
// basic fields for group:
'group_title' => 'min:1|max:1000|nullable',
'group_title' => ['min:1', 'max:1000', 'nullable'],
'error_if_duplicate_hash' => [new IsBoolean()],
'fire_webhooks' => [new IsBoolean()],
'apply_rules' => [new IsBoolean()],
@@ -97,42 +97,42 @@ class StoreRequest extends FormRequest
'transactions.*.zoom_level' => $locationRules['zoom_level'],
// transaction rules (in array for splits):
'transactions.*.type' => 'required|in:withdrawal,deposit,transfer,opening-balance,reconciliation',
'transactions.*.type' => ['required', 'in:withdrawal,deposit,transfer,opening-balance,reconciliation'],
'transactions.*.date' => ['required', new IsDateOrTime()],
'transactions.*.order' => 'numeric|min:0',
'transactions.*.order' => ['numeric', 'min:0'],
// currency info
'transactions.*.currency_id' => 'numeric|exists:transaction_currencies,id|nullable',
'transactions.*.currency_code' => 'min:3|max:51|exists:transaction_currencies,code|nullable',
'transactions.*.foreign_currency_id' => 'numeric|exists:transaction_currencies,id|nullable',
'transactions.*.foreign_currency_code' => 'min:3|max:51|exists:transaction_currencies,code|nullable',
'transactions.*.currency_id' => ['numeric', 'exists:transaction_currencies,id', 'nullable'],
'transactions.*.currency_code' => ['min:3', 'max:51', 'exists:transaction_currencies,code', 'nullable'],
'transactions.*.foreign_currency_id' => ['numeric', 'exists:transaction_currencies,id', 'nullable'],
'transactions.*.foreign_currency_code' => ['min:3', 'max:51', 'exists:transaction_currencies,code', 'nullable'],
// amount
'transactions.*.amount' => ['required', new IsValidPositiveAmount()],
'transactions.*.foreign_amount' => ['nullable', new IsValidZeroOrMoreAmount()],
// description
'transactions.*.description' => 'nullable|min:1|max:1000',
'transactions.*.description' => ['nullable', 'min:1', 'max:1000'],
// source of transaction
'transactions.*.source_id' => ['numeric', 'nullable', new BelongsUser()],
'transactions.*.source_name' => 'min:1|max:255|nullable',
'transactions.*.source_iban' => 'min:1|max:255|nullable|iban',
'transactions.*.source_number' => 'min:1|max:255|nullable',
'transactions.*.source_bic' => 'min:1|max:255|nullable|bic',
'transactions.*.source_name' => ['min:1', 'max:255', 'nullable'],
'transactions.*.source_iban' => ['min:1', 'max:255', 'nullable', 'iban'],
'transactions.*.source_number' => ['min:1', 'max:255', 'nullable'],
'transactions.*.source_bic' => ['min:1', 'max:255', 'nullable', 'bic'],
// destination of transaction
'transactions.*.destination_id' => ['numeric', 'nullable', new BelongsUser()],
'transactions.*.destination_name' => 'min:1|max:255|nullable',
'transactions.*.destination_iban' => 'min:1|max:255|nullable|iban',
'transactions.*.destination_number' => 'min:1|max:255|nullable',
'transactions.*.destination_bic' => 'min:1|max:255|nullable|bic',
'transactions.*.destination_name' => ['min:1', 'max:255', 'nullable'],
'transactions.*.destination_iban' => ['min:1', 'max:255', 'nullable', 'iban'],
'transactions.*.destination_number' => ['min:1', 'max:255', 'nullable'],
'transactions.*.destination_bic' => ['min:1', 'max:255', 'nullable', 'bic'],
// budget, category, bill and piggy
'transactions.*.budget_id' => ['mustExist:budgets,id', new BelongsUser()],
'transactions.*.budget_name' => ['min:1', 'max:255', 'nullable', new BelongsUser()],
'transactions.*.category_id' => ['mustExist:categories,id', new BelongsUser(), 'nullable'],
'transactions.*.category_name' => 'min:1|max:255|nullable',
'transactions.*.category_name' => ['min:1', 'max:255', 'nullable'],
'transactions.*.bill_id' => ['numeric', 'nullable', 'mustExist:bills,id', new BelongsUser()],
'transactions.*.bill_name' => ['min:1', 'max:255', 'nullable', new BelongsUser()],
'transactions.*.piggy_bank_id' => ['numeric', 'nullable', 'mustExist:piggy_banks,id', new BelongsUser()],
@@ -140,34 +140,34 @@ class StoreRequest extends FormRequest
// other interesting fields
'transactions.*.reconciled' => [new IsBoolean()],
'transactions.*.notes' => 'min:1|max:32768|nullable',
'transactions.*.tags' => 'min:0|max:255',
'transactions.*.tags.*' => 'min:0|max:255',
'transactions.*.notes' => ['min:1', 'max:32768', 'nullable'],
'transactions.*.tags' => ['min:0', 'max:255'],
'transactions.*.tags.*' => ['min:0', 'max:255'],
// meta info fields
'transactions.*.internal_reference' => 'min:1|max:255|nullable',
'transactions.*.external_id' => 'min:1|max:255|nullable',
'transactions.*.recurrence_id' => 'min:1|max:255|nullable',
'transactions.*.bunq_payment_id' => 'min:1|max:255|nullable',
'transactions.*.internal_reference' => ['min:1', 'max:255', 'nullable'],
'transactions.*.external_id' => ['min:1', 'max:255', 'nullable'],
'transactions.*.recurrence_id' => ['min:1', 'max:255', 'nullable'],
'transactions.*.bunq_payment_id' => ['min:1', 'max:255', 'nullable'],
'transactions.*.external_url' => sprintf('min:1|max:255|nullable|url:%s', $validProtocols),
// SEPA fields:
'transactions.*.sepa_cc' => 'min:1|max:255|nullable',
'transactions.*.sepa_ct_op' => 'min:1|max:255|nullable',
'transactions.*.sepa_ct_id' => 'min:1|max:255|nullable',
'transactions.*.sepa_db' => 'min:1|max:255|nullable',
'transactions.*.sepa_country' => 'min:1|max:255|nullable',
'transactions.*.sepa_ep' => 'min:1|max:255|nullable',
'transactions.*.sepa_ci' => 'min:1|max:255|nullable',
'transactions.*.sepa_batch_id' => 'min:1|max:255|nullable',
'transactions.*.sepa_cc' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_ct_op' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_ct_id' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_db' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_country' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_ep' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_ci' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_batch_id' => ['min:1', 'max:255', 'nullable'],
// dates
'transactions.*.interest_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.book_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.process_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.due_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.payment_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.invoice_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.interest_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
'transactions.*.book_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
'transactions.*.process_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
'transactions.*.due_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
'transactions.*.payment_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
'transactions.*.invoice_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
];
}

View File

@@ -145,76 +145,76 @@ class UpdateRequest extends FormRequest
return [
// basic fields for group:
'group_title' => 'min:1|max:1000|nullable',
'group_title' => ['min:1', 'max:1000', 'nullable'],
'apply_rules' => [new IsBoolean()],
// transaction rules (in array for splits):
'transactions.*.type' => 'in:withdrawal,deposit,transfer,opening-balance,reconciliation',
'transactions.*.date' => [new IsDateOrTime()],
'transactions.*.order' => 'numeric|min:0',
'transactions.*.order' => ['numeric', 'min:0'],
// group id:
'transactions.*.transaction_journal_id' => ['nullable', 'numeric', new BelongsUser()],
// currency info
'transactions.*.currency_id' => 'numeric|exists:transaction_currencies,id|nullable',
'transactions.*.currency_code' => 'min:3|max:51|exists:transaction_currencies,code|nullable',
'transactions.*.foreign_currency_id' => 'nullable|numeric|exists:transaction_currencies,id',
'transactions.*.foreign_currency_code' => 'nullable|min:3|max:51|exists:transaction_currencies,code',
'transactions.*.currency_id' => ['numeric', 'exists:transaction_currencies,id', 'nullable'],
'transactions.*.currency_code' => ['min:3', 'max:51', 'exists:transaction_currencies,code', 'nullable'],
'transactions.*.foreign_currency_id' => ['nullable', 'numeric', 'exists:transaction_currencies,id'],
'transactions.*.foreign_currency_code' => ['nullable', 'min:3', 'max:51', 'exists:transaction_currencies,code'],
// amount
'transactions.*.amount' => [new IsValidPositiveAmount()],
'transactions.*.foreign_amount' => ['nullable', new IsValidZeroOrMoreAmount()],
// description
'transactions.*.description' => 'nullable|min:1|max:1000',
'transactions.*.description' => ['nullable', 'min:1', 'max:1000'],
// source of transaction
'transactions.*.source_id' => ['numeric', 'nullable', new BelongsUser()],
'transactions.*.source_name' => 'min:1|max:255|nullable',
'transactions.*.source_name' => ['min:1', 'max:255', 'nullable'],
// destination of transaction
'transactions.*.destination_id' => ['numeric', 'nullable', new BelongsUser()],
'transactions.*.destination_name' => 'min:1|max:255|nullable',
'transactions.*.destination_name' => ['min:1', 'max:255', 'nullable'],
// budget, category, bill and piggy
'transactions.*.budget_id' => ['mustExist:budgets,id', new BelongsUser(), 'nullable'],
'transactions.*.budget_name' => ['min:1', 'max:255', 'nullable', new BelongsUser()],
'transactions.*.category_id' => ['mustExist:categories,id', new BelongsUser(), 'nullable'],
'transactions.*.category_name' => 'min:1|max:255|nullable',
'transactions.*.category_name' => ['min:1', 'max:255', 'nullable'],
'transactions.*.bill_id' => ['numeric', 'nullable', 'mustExist:bills,id', new BelongsUser()],
'transactions.*.bill_name' => ['min:1', 'max:255', 'nullable', new BelongsUser()],
// other interesting fields
'transactions.*.reconciled' => [new IsBoolean()],
'transactions.*.notes' => 'min:1|max:32768|nullable',
'transactions.*.tags' => 'min:0|max:255|nullable',
'transactions.*.tags.*' => 'min:0|max:255',
'transactions.*.notes' => ['min:1', 'max:32768', 'nullable'],
'transactions.*.tags' => ['min:0', 'max:255', 'nullable'],
'transactions.*.tags.*' => ['min:0', 'max:255'],
// meta info fields
'transactions.*.internal_reference' => 'min:1|max:255|nullable',
'transactions.*.external_id' => 'min:1|max:255|nullable',
'transactions.*.recurrence_id' => 'min:1|max:255|nullable',
'transactions.*.bunq_payment_id' => 'min:1|max:255|nullable',
'transactions.*.internal_reference' => ['min:1', 'max:255', 'nullable'],
'transactions.*.external_id' => ['min:1', 'max:255', 'nullable'],
'transactions.*.recurrence_id' => ['min:1', 'max:255', 'nullable'],
'transactions.*.bunq_payment_id' => ['min:1', 'max:255', 'nullable'],
'transactions.*.external_url' => sprintf('min:1|max:255|nullable|url:%s', $validProtocols),
// SEPA fields:
'transactions.*.sepa_cc' => 'min:1|max:255|nullable',
'transactions.*.sepa_ct_op' => 'min:1|max:255|nullable',
'transactions.*.sepa_ct_id' => 'min:1|max:255|nullable',
'transactions.*.sepa_db' => 'min:1|max:255|nullable',
'transactions.*.sepa_country' => 'min:1|max:255|nullable',
'transactions.*.sepa_ep' => 'min:1|max:255|nullable',
'transactions.*.sepa_ci' => 'min:1|max:255|nullable',
'transactions.*.sepa_batch_id' => 'min:1|max:255|nullable',
'transactions.*.sepa_cc' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_ct_op' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_ct_id' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_db' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_country' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_ep' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_ci' => ['min:1', 'max:255', 'nullable'],
'transactions.*.sepa_batch_id' => ['min:1', 'max:255', 'nullable'],
// dates
'transactions.*.interest_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.book_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.process_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.due_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.payment_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.invoice_date' => 'date|nullable|after:1970-01-02|before:2038-01-17',
'transactions.*.interest_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
'transactions.*.book_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
'transactions.*.process_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
'transactions.*.due_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
'transactions.*.payment_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
'transactions.*.invoice_date' => ['date', 'nullable', 'after:1970-01-02', 'before:2038-01-17'],
];
}

View File

@@ -69,10 +69,10 @@ class StoreRequest extends FormRequest
public function rules(): array
{
return [
'name' => 'required|min:1|max:255|unique:transaction_currencies,name',
'code' => 'required|min:3|max:32|unique:transaction_currencies,code',
'symbol' => 'required|min:1|max:32|unique:transaction_currencies,symbol',
'decimal_places' => 'numeric|min:0|max:12',
'name' => ['required', 'min:1', 'max:255', 'unique:transaction_currencies,name'],
'code' => ['required', 'min:3', 'max:32', 'unique:transaction_currencies,code'],
'symbol' => ['required', 'min:1', 'max:32', 'unique:transaction_currencies,symbol'],
'decimal_places' => ['numeric', 'min:0', 'max:12'],
'enabled' => [new IsBoolean()],
'default' => [new IsBoolean()],
];

View File

@@ -82,7 +82,7 @@ class UpdateRequest extends FormRequest
'name' => sprintf('min:1|max:255|unique:transaction_currencies,name,%d', $currency->id),
'code' => sprintf('min:3|max:32|unique:transaction_currencies,code,%d', $currency->id),
'symbol' => sprintf('min:1|max:32|unique:transaction_currencies,symbol,%d', $currency->id),
'decimal_places' => 'numeric|min:0|max:12',
'decimal_places' => ['numeric', 'min:0', 'max:12'],
'enabled' => [new IsBoolean()],
'default' => [new IsBoolean()],
];

View File

@@ -63,11 +63,11 @@ class StoreRequest extends FormRequest
public function rules(): array
{
return [
'link_type_id' => 'exists:link_types,id|required_without:link_type_name',
'link_type_name' => 'exists:link_types,name|required_without:link_type_id',
'inward_id' => 'required|belongsToUser:transaction_journals,id|different:outward_id',
'outward_id' => 'required|belongsToUser:transaction_journals,id|different:inward_id',
'notes' => 'min:1|max:32768|nullable',
'link_type_id' => ['exists:link_types,id', 'required_without:link_type_name'],
'link_type_name' => ['exists:link_types,name', 'required_without:link_type_id'],
'inward_id' => ['required', 'belongsToUser:transaction_journals,id', 'different:outward_id'],
'outward_id' => ['required', 'belongsToUser:transaction_journals,id', 'different:inward_id'],
'notes' => ['min:1', 'max:32768', 'nullable'],
];
}

View File

@@ -65,9 +65,9 @@ class UpdateRequest extends FormRequest
return [
'link_type_id' => 'exists:link_types,id',
'link_type_name' => 'exists:link_types,name',
'inward_id' => 'belongsToUser:transaction_journals,id|different:outward_id',
'outward_id' => 'belongsToUser:transaction_journals,id|different:inward_id',
'notes' => 'min:1|max:32768|nullable',
'inward_id' => ['belongsToUser:transaction_journals,id', 'different:outward_id'],
'outward_id' => ['belongsToUser:transaction_journals,id', 'different:inward_id'],
'notes' => ['min:1', 'max:32768', 'nullable'],
];
}

View File

@@ -52,9 +52,9 @@ class StoreRequest extends FormRequest
public function rules(): array
{
return [
'name' => 'required|unique:link_types,name|min:1|max:1024',
'outward' => 'required|unique:link_types,outward|min:1|different:inward|max:1024',
'inward' => 'required|unique:link_types,inward|min:1|different:outward|max:1024',
'name' => ['required', 'unique:link_types,name', 'min:1', 'max:1024'],
'outward' => ['required', 'unique:link_types,outward', 'min:1', 'different:inward', 'max:1024'],
'inward' => ['required', 'unique:link_types,inward', 'min:1', 'different:outward', 'max:1024'],
];
}
}

View File

@@ -75,16 +75,16 @@ class CreateRequest extends FormRequest
$validProtocols = FireflyConfig::get('valid_url_protocols', config('firefly.valid_url_protocols'))->data;
return [
'title' => 'required|min:1|max:255|uniqueObjectForUser:webhooks,title',
'title' => ['required', 'min:1', 'max:255', 'uniqueObjectForUser:webhooks,title'],
'active' => [new IsBoolean()],
'trigger' => 'prohibited',
'triggers' => 'required|array|min:1|max:10',
'triggers' => ['required', 'array', 'min:1', 'max:10'],
'triggers.*' => sprintf('required|in:%s', $triggers),
'response' => 'prohibited',
'responses' => 'required|array|min:1|max:1',
'responses' => ['required', 'array', 'min:1', 'max:1'],
'responses.*' => sprintf('required|in:%s', $responses),
'delivery' => 'prohibited',
'deliveries' => 'required|array|min:1|max:1',
'deliveries' => ['required', 'array', 'min:1', 'max:1'],
'deliveries.*' => sprintf('required|in:%s', $deliveries),
'url' => ['required', sprintf('url:%s', $validProtocols), new IsValidWebhookUrl()],
];

View File

@@ -82,13 +82,13 @@ class UpdateRequest extends FormRequest
'title' => sprintf('min:1|max:255|uniqueObjectForUser:webhooks,title,%d', $webhook->id),
'active' => [new IsBoolean()],
'trigger' => 'prohibited',
'triggers' => 'required|array|min:1|max:10',
'triggers' => ['required', 'array', 'min:1', 'max:10'],
'triggers.*' => sprintf('required|in:%s', $triggers),
'response' => 'prohibited',
'responses' => 'required|array|min:1|max:1',
'responses' => ['required', 'array', 'min:1', 'max:1'],
'responses.*' => sprintf('required|in:%s', $responses),
'delivery' => 'prohibited',
'deliveries' => 'required|array|min:1|max:1',
'deliveries' => ['required', 'array', 'min:1', 'max:1'],
'deliveries.*' => sprintf('required|in:%s', $deliveries),
'url' => [sprintf('url:%s', $validProtocols), sprintf('uniqueExistingWebhook:%d', $webhook->id), new IsValidWebhookUrl()],
];

View File

@@ -50,8 +50,8 @@ class PaginationRequest extends ApiRequest
{
return [
'sort' => ['nullable', new IsValidSortInstruction((string) $this->sortClass)],
'limit' => 'numeric|min:1|max:131337',
'page' => 'numeric|min:1|max:131337',
'limit' => ['numeric', 'min:1', 'max:131337'],
'page' => ['numeric', 'min:1', 'max:131337'],
];
}

View File

@@ -34,10 +34,10 @@ class CountRequest extends AggregateFormRequest
public function rules(): array
{
return [
'notes' => 'string|min:1|max:255',
'external_identifier' => 'string|min:1|max:255',
'description' => 'string|min:1|max:255',
'internal_reference' => 'string|min:1|max:255',
'notes' => ['string', 'min:1', 'max:255'],
'external_identifier' => ['string', 'min:1', 'max:255'],
'description' => ['string', 'min:1', 'max:255'],
'internal_reference' => ['string', 'min:1', 'max:255'],
'include_deleted' => new IsBoolean(),
];
}

View File

@@ -68,6 +68,6 @@ class CronRequest extends FormRequest
*/
public function rules(): array
{
return ['force' => 'in:true,false', 'date' => 'nullable|date|after:1970-01-02|before:2038-01-17'];
return ['force' => 'in:true,false', 'date' => ['nullable', 'date', 'after:1970-01-02', 'before:2038-01-17']];
}
}

View File

@@ -77,10 +77,10 @@ class UpdateRequest extends FormRequest
return ['value' => ['required', new IsBoolean()]];
}
if ('configuration.permission_update_check' === $name) {
return ['value' => 'required|numeric|min:-1|max:1'];
return ['value' => ['required', 'numeric', 'min:-1', 'max:1']];
}
if (in_array($name, $this->integers, strict: true)) {
return ['value' => 'required|numeric|min:464272080'];
return ['value' => ['required', 'numeric', 'min:464272080']];
}
return ['value' => 'required'];

View File

@@ -71,7 +71,7 @@ class UserStoreRequest extends FormRequest
public function rules(): array
{
return [
'email' => 'required|email|unique:users,email',
'email' => ['required', 'email', 'unique:users,email'],
'blocked' => [new IsBoolean()],
'blocked_code' => 'in:email_changed',
'role' => 'in:owner,demo',

View File

@@ -52,15 +52,15 @@ class ClearsEmptyForeignAmounts extends Command
public function handle(): int
{
// transaction: has no amount, but reference to currency.
$count = Transaction::whereNull('foreign_amount')->whereNotNull('foreign_currency_id')->count();
$count = Transaction::query()->whereNull('foreign_amount')->whereNotNull('foreign_currency_id')->count();
if ($count > 0) {
Transaction::whereNull('foreign_amount')->whereNotNull('foreign_currency_id')->update(['foreign_currency_id' => null]);
Transaction::query()->whereNull('foreign_amount')->whereNotNull('foreign_currency_id')->update(['foreign_currency_id' => null]);
$this->friendlyInfo(sprintf('Corrected %d invalid foreign amount reference(s)', $count));
}
// transaction: has amount, but no currency.
$count = Transaction::whereNull('foreign_currency_id')->whereNotNull('foreign_amount')->count();
$count = Transaction::query()->whereNull('foreign_currency_id')->whereNotNull('foreign_amount')->count();
if ($count > 0) {
Transaction::whereNull('foreign_currency_id')->whereNotNull('foreign_amount')->update(['foreign_amount' => null]);
Transaction::query()->whereNull('foreign_currency_id')->whereNotNull('foreign_amount')->update(['foreign_amount' => null]);
$this->friendlyInfo(sprintf('Corrected %d invalid foreign amount reference(s)', $count));
}

View File

@@ -88,7 +88,7 @@ class CorrectsAmounts extends Command
/** @var AccountRepositoryInterface $repository */
$repository = app(AccountRepositoryInterface::class);
$type = TransactionType::where('type', TransactionTypeEnum::TRANSFER->value)->first();
$type = TransactionType::query()->where('type', TransactionTypeEnum::TRANSFER->value)->first();
$journals = TransactionJournal::leftJoin('transactions', 'transactions.transaction_journal_id', '=', 'transaction_journals.id')
->whereNotNull('transactions.foreign_amount')
->where('transaction_journals.transaction_type_id', $type->id)
@@ -188,7 +188,10 @@ class CorrectsAmounts extends Command
private function fixAutoBudgets(): void
{
$count = AutoBudget::where('amount', '<', 0)->update(['amount' => DB::raw('amount * -1')]);
$count = AutoBudget::query()
->where('amount', '<', 0)
->update(['amount' => DB::raw('amount * -1')])
;
if (0 === $count) {
return;
}
@@ -197,7 +200,10 @@ class CorrectsAmounts extends Command
private function fixAvailableBudgets(): void
{
$count = AvailableBudget::where('amount', '<', 0)->update(['amount' => DB::raw('amount * -1')]);
$count = AvailableBudget::query()
->where('amount', '<', 0)
->update(['amount' => DB::raw('amount * -1')])
;
if (0 === $count) {
return;
}
@@ -207,8 +213,14 @@ class CorrectsAmounts extends Command
private function fixBills(): void
{
$count = 0;
$count += Bill::where('amount_max', '<', 0)->update(['amount_max' => DB::raw('amount_max * -1')]);
$count += Bill::where('amount_min', '<', 0)->update(['amount_min' => DB::raw('amount_min * -1')]);
$count += Bill::query()
->where('amount_max', '<', 0)
->update(['amount_max' => DB::raw('amount_max * -1')])
;
$count += Bill::query()
->where('amount_min', '<', 0)
->update(['amount_min' => DB::raw('amount_min * -1')])
;
if (0 === $count) {
return;
}
@@ -217,7 +229,10 @@ class CorrectsAmounts extends Command
private function fixBudgetLimits(): void
{
$count = BudgetLimit::where('amount', '<', 0)->update(['amount' => DB::raw('amount * -1')]);
$count = BudgetLimit::query()
->where('amount', '<', 0)
->update(['amount' => DB::raw('amount * -1')])
;
if (0 === $count) {
return;
}
@@ -226,7 +241,10 @@ class CorrectsAmounts extends Command
private function fixExchangeRates(): void
{
$count = CurrencyExchangeRate::where('rate', '<', 0)->update(['rate' => DB::raw('rate * -1')]);
$count = CurrencyExchangeRate::query()
->where('rate', '<', 0)
->update(['rate' => DB::raw('rate * -1')])
;
if (0 === $count) {
return;
}
@@ -235,7 +253,10 @@ class CorrectsAmounts extends Command
private function fixPiggyBanks(): void
{
$count = PiggyBank::where('target_amount', '<', 0)->update(['target_amount' => DB::raw('target_amount * -1')]);
$count = PiggyBank::query()
->where('target_amount', '<', 0)
->update(['target_amount' => DB::raw('target_amount * -1')])
;
if (0 === $count) {
return;
}
@@ -245,8 +266,14 @@ class CorrectsAmounts extends Command
private function fixRecurrences(): void
{
$count = 0;
$count += RecurrenceTransaction::where('amount', '<', 0)->update(['amount' => DB::raw('amount * -1')]);
$count += RecurrenceTransaction::where('foreign_amount', '<', 0)->update(['foreign_amount' => DB::raw('foreign_amount * -1')]);
$count += RecurrenceTransaction::query()
->where('amount', '<', 0)
->update(['amount' => DB::raw('amount * -1')])
;
$count += RecurrenceTransaction::query()
->where('foreign_amount', '<', 0)
->update(['foreign_amount' => DB::raw('foreign_amount * -1')])
;
if (0 === $count) {
return;
}
@@ -285,7 +312,7 @@ class CorrectsAmounts extends Command
*/
private function fixRuleTriggers(): void
{
$set = RuleTrigger::whereIn('trigger_type', ['amount_less', 'amount_more', 'amount_is'])->get();
$set = RuleTrigger::query()->whereIn('trigger_type', ['amount_less', 'amount_more', 'amount_is'])->get();
$fixed = 0;
/** @var RuleTrigger $item */

View File

@@ -81,7 +81,7 @@ class CorrectsCurrencies extends Command
}
// get all from journals:
$journals = TransactionJournal::where('user_group_id', $userGroup->id)->groupBy('transaction_currency_id')->get(['transaction_currency_id']);
$journals = TransactionJournal::query()->where('user_group_id', $userGroup->id)->groupBy('transaction_currency_id')->get(['transaction_currency_id']);
foreach ($journals as $entry) {
$found[] = (int) $entry->transaction_currency_id;
}

View File

@@ -49,7 +49,10 @@ class CorrectsGroupAccounts extends Command
{
Log::debug('Start of correction:group-accounts');
$groups = [];
$res = TransactionJournal::groupBy('transaction_group_id')->get(['transaction_group_id', DB::raw('COUNT(transaction_group_id) as the_count')]);
$res = TransactionJournal::query()->groupBy('transaction_group_id')->get([
'transaction_group_id',
DB::raw('COUNT(transaction_group_id) as the_count'),
]);
/** @var TransactionJournal $journal */
foreach ($res as $journal) {

View File

@@ -44,7 +44,7 @@ class CorrectsIbans extends Command
*/
public function handle(): int
{
$accounts = Account::with('accountMeta')->get();
$accounts = Account::query()->with('accountMeta')->get();
$this->filterIbans($accounts);
$this->countAndCorrectIbans($accounts);

View File

@@ -53,7 +53,7 @@ class CorrectsInvertedBudgetLimits extends Command
*/
public function handle(): int
{
$set = BudgetLimit::where('start_date', '>', DB::raw('end_date'))->get();
$set = BudgetLimit::query()->where('start_date', '>', DB::raw('end_date'))->get();
if (0 === $set->count()) {
Log::debug('No inverted budget limits found.');

View File

@@ -44,7 +44,7 @@ class CorrectsLongDescriptions extends Command
*/
public function handle(): int
{
$journals = TransactionJournal::where(DB::raw('LENGTH(description)'), '>', self::MAX_LENGTH)->get(['id', 'description']);
$journals = TransactionJournal::query()->where(DB::raw('LENGTH(description)'), '>', self::MAX_LENGTH)->get(['id', 'description']);
$count = 0;
/** @var TransactionJournal $journal */
@@ -57,7 +57,7 @@ class CorrectsLongDescriptions extends Command
}
}
$groups = TransactionGroup::where(DB::raw('LENGTH(title)'), '>', self::MAX_LENGTH)->get(['id', 'title']);
$groups = TransactionGroup::query()->where(DB::raw('LENGTH(title)'), '>', self::MAX_LENGTH)->get(['id', 'title']);
/** @var TransactionGroup $group */
foreach ($groups as $group) {

View File

@@ -42,7 +42,7 @@ class CorrectsPiggyBanks extends Command
public function handle(): int
{
$count = 0;
$set = PiggyBankEvent::with(['PiggyBank', 'TransactionJournal'])->get();
$set = PiggyBankEvent::query()->with(['PiggyBank', 'TransactionJournal'])->get();
/** @var PiggyBankEvent $event */
foreach ($set as $event) {

View File

@@ -47,7 +47,7 @@ class CorrectsPreferences extends Command
foreach ($users as $user) {
$count = 0;
foreach ($items as $item) {
$preference = Preference::where('name', $item)->where('user_id', $user->id)->first();
$preference = Preference::query()->where('name', $item)->where('user_id', $user->id)->first();
if (null === $preference) {
continue;
}

View File

@@ -81,7 +81,7 @@ class CorrectsTransactionTypes extends Command
*/
private function collectJournals(): Collection
{
return TransactionJournal::with(['transactionType', 'transactions', 'transactions.account', 'transactions.account.accountType'])->get();
return TransactionJournal::query()->with(['transactionType', 'transactions', 'transactions.account', 'transactions.account.accountType'])->get();
}
private function fixJournal(TransactionJournal $journal): bool

View File

@@ -42,7 +42,8 @@ class CorrectsTransferBudgets extends Command
*/
public function handle(): int
{
$set = TransactionJournal::distinct()
$set = TransactionJournal::query()
->distinct()
->leftJoin('transaction_types', 'transaction_types.id', '=', 'transaction_journals.transaction_type_id')
->leftJoin('budget_transaction_journal', 'transaction_journals.id', '=', 'budget_transaction_journal.transaction_journal_id')
->whereNotIn('transaction_types.type', [TransactionTypeEnum::WITHDRAWAL->value])

View File

@@ -76,7 +76,8 @@ class CorrectsUnevenAmount extends Command
$repository = app(AccountRepositoryInterface::class);
Log::debug('convertOldStyleTransactions()');
$count = 0;
$transactions = Transaction::distinct()
$transactions = Transaction::query()
->distinct()
->leftJoin('transaction_journals', 'transaction_journals.id', 'transactions.transaction_journal_id')
->leftJoin('transaction_types', 'transaction_types.id', 'transaction_journals.transaction_type_id')
->leftJoin('accounts', 'accounts.id', 'transactions.account_id')
@@ -188,7 +189,8 @@ class CorrectsUnevenAmount extends Command
{
Log::debug('convertOldStyleTransfers()');
// select transactions with a foreign amount and a foreign currency. and it's a transfer. and they are different.
$transactions = Transaction::distinct()
$transactions = Transaction::query()
->distinct()
->leftJoin('transaction_journals', 'transaction_journals.id', 'transactions.transaction_journal_id')
->leftJoin('transaction_types', 'transaction_types.id', 'transaction_journals.transaction_type_id')
->where('transaction_types.type', TransactionTypeEnum::TRANSFER->value)
@@ -262,8 +264,14 @@ class CorrectsUnevenAmount extends Command
$journal->id ?? 0,
$journal->description ?? ''
));
Transaction::where('transaction_journal_id', $journal->id ?? 0)->forceDelete();
TransactionJournal::where('id', $journal->id ?? 0)->forceDelete();
Transaction::query()
->where('transaction_journal_id', $journal->id ?? 0)
->forceDelete()
;
TransactionJournal::query()
->where('id', $journal->id ?? 0)
->forceDelete()
;
++$this->count;
return;
@@ -282,8 +290,14 @@ class CorrectsUnevenAmount extends Command
$journal->description ?? ''
));
Transaction::where('transaction_journal_id', $journal->id ?? 0)->forceDelete();
TransactionJournal::where('id', $journal->id ?? 0)->forceDelete();
Transaction::query()
->where('transaction_journal_id', $journal->id ?? 0)
->forceDelete()
;
TransactionJournal::query()
->where('id', $journal->id ?? 0)
->forceDelete()
;
++$this->count;
return;
@@ -430,7 +444,7 @@ class CorrectsUnevenAmount extends Command
/** @var TransactionJournal $journal */
foreach ($journals as $journal) {
if (!$this->isForeignCurrencyTransfer($journal) && !$this->isBetweenAssetAndLiability($journal)) {
Transaction::where('transaction_journal_id', $journal->id)->update(['transaction_currency_id' => $journal->transaction_currency_id]);
Transaction::query()->where('transaction_journal_id', $journal->id)->update(['transaction_currency_id' => $journal->transaction_currency_id]);
++$count;
continue;

View File

@@ -50,17 +50,22 @@ class CreatesGroupMemberships extends Command
public static function createGroupMembership(User $user): void
{
// check if membership exists
$userGroup = UserGroup::where('title', $user->email)->first();
$userGroup = UserGroup::query()->where('title', $user->email)->first();
if (null === $userGroup) {
$userGroup = UserGroup::create(['title' => $user->email]);
}
$userRole = UserRole::where('title', UserRoleEnum::OWNER->value)->first();
$userRole = UserRole::query()->where('title', UserRoleEnum::OWNER->value)->first();
if (null === $userRole) {
throw new FireflyException('Firefly III could not find a user role. Please make sure all migrations have run.');
}
$membership = GroupMembership::where('user_id', $user->id)->where('user_group_id', $userGroup->id)->where('user_role_id', $userRole->id)->first();
$membership = GroupMembership::query()
->where('user_id', $user->id)
->where('user_group_id', $userGroup->id)
->where('user_role_id', $userRole->id)
->first()
;
if (null === $membership) {
GroupMembership::create(['user_id' => $user->id, 'user_role_id' => $userRole->id, 'user_group_id' => $userGroup->id]);
}

View File

@@ -49,7 +49,7 @@ class CreatesLinkTypes extends Command
'Reimbursement' => ['(partially) reimburses', 'is (partially) reimbursed by'],
];
foreach ($set as $name => $values) {
$link = LinkType::where('name', $name)->first();
$link = LinkType::query()->where('name', $name)->first();
if (null === $link) {
$link = new LinkType();
$link->name = $name;

View File

@@ -43,11 +43,11 @@ class RemovesBills extends Command
public function handle(): int
{
/** @var null|TransactionType $withdrawal */
$withdrawal = TransactionType::where('type', TransactionTypeEnum::WITHDRAWAL->value)->first();
$withdrawal = TransactionType::query()->where('type', TransactionTypeEnum::WITHDRAWAL->value)->first();
if (null === $withdrawal) {
return 0;
}
$journals = TransactionJournal::whereNotNull('bill_id')->where('transaction_type_id', '!=', $withdrawal->id)->get();
$journals = TransactionJournal::query()->whereNotNull('bill_id')->where('transaction_type_id', '!=', $withdrawal->id)->get();
/** @var TransactionJournal $journal */
foreach ($journals as $journal) {

View File

@@ -57,7 +57,7 @@ class RemovesEmptyGroups extends Command
// again, chunks for SQLite.
$chunks = array_chunk($groupIds, 500);
foreach ($chunks as $chunk) {
TransactionGroup::whereNull('deleted_at')->whereIn('id', $chunk)->delete();
TransactionGroup::query()->whereNull('deleted_at')->whereIn('id', $chunk)->delete();
}
}

View File

@@ -80,10 +80,14 @@ class RemovesEmptyJournals extends Command
*/
private function deleteUnevenJournals(): void
{
$set = Transaction::whereNull('deleted_at')->groupBy('transactions.transaction_journal_id')->get([
DB::raw('COUNT(transactions.transaction_journal_id) as the_count'),
'transaction_journal_id',
]);
$set = Transaction::query()
->whereNull('deleted_at')
->groupBy('transactions.transaction_journal_id')
->get([
DB::raw('COUNT(transactions.transaction_journal_id) as the_count'),
'transaction_journal_id',
])
;
$total = 0;
/** @var Transaction $row */
@@ -100,7 +104,7 @@ class RemovesEmptyJournals extends Command
Log::error($e->getTraceAsString());
}
Transaction::where('transaction_journal_id', $row->transaction_journal_id)->delete();
Transaction::query()->where('transaction_journal_id', $row->transaction_journal_id)->delete();
$this->friendlyWarning(sprintf(
'Deleted transaction journal #%d because it had an uneven number of transactions.',
$row->transaction_journal_id

View File

@@ -57,10 +57,34 @@ class RemovesLinksToDeletedObjects extends Command
*/
public function handle(): void
{
$deletedTags = Tag::withTrashed()->whereNotNull('deleted_at')->get('tags.id')->pluck('id')->toArray();
$deletedJournals = TransactionJournal::withTrashed()->whereNotNull('deleted_at')->get('transaction_journals.id')->pluck('id')->toArray();
$deletedBudgets = Budget::withTrashed()->whereNotNull('deleted_at')->get('budgets.id')->pluck('id')->toArray();
$deletedCategories = Category::withTrashed()->whereNotNull('deleted_at')->get('categories.id')->pluck('id')->toArray();
$deletedTags = Tag::query()
->withTrashed()
->whereNotNull('deleted_at')
->get('tags.id')
->pluck('id')
->toArray()
;
$deletedJournals = TransactionJournal::query()
->withTrashed()
->whereNotNull('deleted_at')
->get('transaction_journals.id')
->pluck('id')
->toArray()
;
$deletedBudgets = Budget::query()
->withTrashed()
->whereNotNull('deleted_at')
->get('budgets.id')
->pluck('id')
->toArray()
;
$deletedCategories = Category::query()
->withTrashed()
->whereNotNull('deleted_at')
->get('categories.id')
->pluck('id')
->toArray()
;
if (count($deletedTags) > 0) {
$this->cleanupTags($deletedTags);

View File

@@ -67,7 +67,7 @@ class RemovesOrphanedTransactions extends Command
/** @var null|TransactionJournal $journal */
$journal = TransactionJournal::find($transaction->transaction_journal_id);
$journal?->delete();
Transaction::where('transaction_journal_id', $transaction->transaction_journal_id)->delete();
Transaction::query()->where('transaction_journal_id', $transaction->transaction_journal_id)->delete();
$this->friendlyWarning(sprintf(
'Deleted transaction journal #%d because account #%d was already deleted.',
$transaction->transaction_journal_id,
@@ -93,7 +93,7 @@ class RemovesOrphanedTransactions extends Command
$this->friendlyInfo(sprintf('Found %d orphaned journal(s).', $count));
foreach ($set as $entry) {
/** @var null|TransactionJournal $journal */
$journal = TransactionJournal::withTrashed()->find($entry->id);
$journal = TransactionJournal::query()->withTrashed()->find($entry->id);
if (null !== $journal) {
$journal->delete();
$this->friendlyWarning(sprintf(

View File

@@ -42,16 +42,16 @@ class RemovesZeroAmount extends Command
*/
public function handle(): int
{
$set = Transaction::where('amount', 0)->get(['transaction_journal_id'])->pluck('transaction_journal_id')->toArray();
$set = Transaction::query()->where('amount', 0)->get(['transaction_journal_id'])->pluck('transaction_journal_id')->toArray();
$set = array_unique($set);
$journals = TransactionJournal::whereIn('id', $set)->get();
$journals = TransactionJournal::query()->whereIn('id', $set)->get();
/** @var TransactionJournal $journal */
foreach ($journals as $journal) {
$this->friendlyWarning(sprintf('Deleted transaction journal #%d because the amount is zero (0.00).', $journal->id));
$journal->delete();
Transaction::where('transaction_journal_id', $journal->id)->delete();
Transaction::query()->where('transaction_journal_id', $journal->id)->delete();
}
return 0;

View File

@@ -490,11 +490,14 @@ class ForcesDecimalSize extends Command
{
// select all transactions with this currency and issue.
/** @var Builder $query */
$query = Transaction::where('transaction_currency_id', $currency->id)->where(
DB::raw(sprintf('CAST(amount as %s)', $this->cast)),
$this->operator,
DB::raw(sprintf($this->regularExpression, $currency->decimal_places))
);
$query = Transaction::query()
->where('transaction_currency_id', $currency->id)
->where(
DB::raw(sprintf('CAST(amount as %s)', $this->cast)),
$this->operator,
DB::raw(sprintf($this->regularExpression, $currency->decimal_places))
)
;
$result = $query->get(['transactions.*']);
if (0 === $result->count()) {
@@ -519,11 +522,14 @@ class ForcesDecimalSize extends Command
// select all transactions with this FOREIGN currency and issue.
/** @var Builder $query */
$query = Transaction::where('foreign_currency_id', $currency->id)->where(
DB::raw(sprintf('CAST(foreign_amount as %s)', $this->cast)),
$this->operator,
DB::raw(sprintf($this->regularExpression, $currency->decimal_places))
);
$query = Transaction::query()
->where('foreign_currency_id', $currency->id)
->where(
DB::raw(sprintf('CAST(foreign_amount as %s)', $this->cast)),
$this->operator,
DB::raw(sprintf($this->regularExpression, $currency->decimal_places))
)
;
$result = $query->get();
if (0 === $result->count()) {

View File

@@ -93,7 +93,8 @@ class AddsTransactionIdentifiers extends Command
try {
/** @var Transaction $opposing */
$opposing = Transaction::where('transaction_journal_id', $transaction->transaction_journal_id)
$opposing = Transaction::query()
->where('transaction_journal_id', $transaction->transaction_journal_id)
->where('amount', $amount)
->where('identifier', '=', 0)
->whereNotIn('id', $exclude)

View File

@@ -106,7 +106,7 @@ class UpgradesAccountCurrencies extends Command
// both 0? set to default currency:
if (0 === $accountCurrency && 0 === $obCurrency) {
AccountMeta::where('account_id', $account->id)->where('name', 'currency_id')->forceDelete();
AccountMeta::query()->where('account_id', $account->id)->where('name', 'currency_id')->forceDelete();
AccountMeta::create(['account_id' => $account->id, 'name' => 'currency_id', 'data' => $currency->id]);
$this->friendlyInfo(sprintf('Account #%d ("%s") now has a currency setting (%s).', $account->id, $account->name, $currency->code));
++$this->count;

View File

@@ -66,10 +66,10 @@ class UpgradesAccountMetaData extends Command
* @var string $new
*/
foreach ($array as $old => $new) {
$count += AccountMeta::where('name', $old)->update(['name' => $new]);
$count += AccountMeta::query()->where('name', $old)->update(['name' => $new]);
// delete empty entries while we're at it.
AccountMeta::where('name', $new)->where('data', '""')->delete();
AccountMeta::query()->where('name', $new)->where('data', '""')->delete();
}
$this->markAsExecuted();

View File

@@ -152,7 +152,7 @@ class UpgradesBudgetLimitPeriods extends Command
private function theresNoLimit(): void
{
$limits = BudgetLimit::whereNull('period')->get();
$limits = BudgetLimit::query()->whereNull('period')->get();
/** @var BudgetLimit $limit */
foreach ($limits as $limit) {

View File

@@ -55,8 +55,8 @@ class UpgradesCreditCardLiabilities extends Command
return 0;
}
$ccType = AccountType::where('type', AccountTypeEnum::CREDITCARD->value)->first();
$debtType = AccountType::where('type', AccountTypeEnum::DEBT->value)->first();
$ccType = AccountType::query()->where('type', AccountTypeEnum::CREDITCARD->value)->first();
$debtType = AccountType::query()->where('type', AccountTypeEnum::DEBT->value)->first();
if (null === $ccType || null === $debtType) {
$this->markAsExecuted();
@@ -64,7 +64,7 @@ class UpgradesCreditCardLiabilities extends Command
}
/** @var Collection $accounts */
$accounts = Account::where('account_type_id', $ccType->id)->get();
$accounts = Account::query()->where('account_type_id', $ccType->id)->get();
foreach ($accounts as $account) {
$account->account_type_id = $debtType->id;
$account->save();

View File

@@ -66,7 +66,8 @@ class UpgradesCurrencyPreferences extends Command
private function getPreference(User $user): string
{
$preference = Preference::where('user_id', $user->id)
$preference = Preference::query()
->where('user_id', $user->id)
->where('name', 'currencyPreference')
->first(['id', 'user_id', 'name', 'data', 'updated_at', 'created_at'])
;
@@ -144,7 +145,7 @@ class UpgradesCurrencyPreferences extends Command
try {
$primaryCurrency = Amount::getTransactionCurrencyByCode($preference);
} catch (FireflyException) {
$primaryCurrency = TransactionCurrency::where('code', 'EUR')->first();
$primaryCurrency = TransactionCurrency::query()->where('code', 'EUR')->first();
}
$user->currencies()->updateExistingPivot($primaryCurrency->id, ['user_default' => true]);
$user->userGroup->currencies()->updateExistingPivot($primaryCurrency->id, ['group_default' => true]);

View File

@@ -131,7 +131,7 @@ class UpgradesJournalMetaData extends Command
$allIds = $this->getIdsForBudgets();
$chunks = array_chunk($allIds, 500);
foreach ($chunks as $journalIds) {
$collected = TransactionJournal::whereIn('id', $journalIds)->with(['transactions', 'budgets', 'transactions.budgets'])->get();
$collected = TransactionJournal::query()->whereIn('id', $journalIds)->with(['transactions', 'budgets', 'transactions.budgets'])->get();
$journals = $journals->merge($collected);
}
@@ -180,7 +180,7 @@ class UpgradesJournalMetaData extends Command
$chunks = array_chunk($allIds, 500);
foreach ($chunks as $chunk) {
$collected = TransactionJournal::whereIn('id', $chunk)->with(['transactions', 'categories', 'transactions.categories'])->get();
$collected = TransactionJournal::query()->whereIn('id', $chunk)->with(['transactions', 'categories', 'transactions.categories'])->get();
$journals = $journals->merge($collected);
}

View File

@@ -105,7 +105,7 @@ class UpgradesMultiPiggyBanks extends Command
{
$this->repository = app(PiggyBankRepositoryInterface::class);
$this->accountRepository = app(AccountRepositoryInterface::class);
$set = PiggyBank::whereNotNull('account_id')->get();
$set = PiggyBank::query()->whereNotNull('account_id')->get();
Log::debug(sprintf('Will update %d piggy banks(s).', $set->count()));
/** @var PiggyBank $piggyBank */

View File

@@ -104,7 +104,7 @@ class UpgradesRecurrenceMetaData extends Command
{
$count = 0;
// get all recurrence meta data:
$collection = RecurrenceMeta::with('recurrence')->get();
$collection = RecurrenceMeta::query()->with('recurrence')->get();
/** @var RecurrenceMeta $meta */
foreach ($collection as $meta) {

View File

@@ -106,7 +106,7 @@ class UpgradesRuleActions extends Command
'move_descr_to_notes',
'move_notes_to_descr',
];
$actions = RuleAction::whereIn('action_type', $obsolete)->get();
$actions = RuleAction::query()->whereIn('action_type', $obsolete)->get();
/** @var RuleAction $action */
foreach ($actions as $action) {

View File

@@ -84,9 +84,9 @@ class UpgradesWebhooks extends Command
return;
}
$deliveryModel = WebhookDeliveryModel::where('key', $delivery->value)->first();
$responseModel = WebhookResponseModel::where('key', $response->value)->first();
$triggerModel = WebhookTriggerModel::where('key', $trigger->value)->first();
$deliveryModel = WebhookDeliveryModel::query()->where('key', $delivery->value)->first();
$responseModel = WebhookResponseModel::query()->where('key', $response->value)->first();
$triggerModel = WebhookTriggerModel::query()->where('key', $trigger->value)->first();
if (in_array(null, [$deliveryModel, $responseModel, $triggerModel], true)) {
$this->friendlyError(sprintf('[b] Webhook #%d has an invalid delivery, response or trigger model. Will not upgrade.', $webhook->id));
@@ -104,7 +104,7 @@ class UpgradesWebhooks extends Command
private function upgradeWebhooks(): void
{
$set = Webhook::where('delivery', '>', 1)->orWhere('trigger', '>', 1)->orWhere('response', '>', 1)->get();
$set = Webhook::query()->where('delivery', '>', 1)->orWhere('trigger', '>', 1)->orWhere('response', '>', 1)->get();
/** @var Webhook $webhook */
foreach ($set as $webhook) {

View File

@@ -157,7 +157,7 @@ class AccountFactory
if (null === $result) {
$types = config(sprintf('firefly.accountTypeByIdentifier.%s', $accountTypeName)) ?? [];
if (0 !== count($types)) {
$result = AccountType::whereIn('type', $types)->first();
$result = AccountType::query()->whereIn('type', $types)->first();
}
}
if (null === $result) {

View File

@@ -245,7 +245,10 @@ class PiggyBankFactory
);
// validate amount:
if (array_key_exists('target_amount', $piggyBankData) && '' === (string) $piggyBankData['target_amount']) {
if (array_key_exists('target_amount', $piggyBankData) && '' === trim((string) $piggyBankData['target_amount'])) {
$piggyBankData['target_amount'] = '0';
}
if (!array_key_exists('target_amount', $piggyBankData)) {
$piggyBankData['target_amount'] = '0';
}

View File

@@ -46,9 +46,9 @@ class TransactionCurrencyFactory
$data['decimal_places'] = (int) $data['decimal_places'];
// if the code already exists (deleted)
// force delete it and then create the transaction:
$count = TransactionCurrency::withTrashed()->whereCode($data['code'])->count();
$count = TransactionCurrency::query()->withTrashed()->whereCode($data['code'])->count();
if (1 === $count) {
$old = TransactionCurrency::withTrashed()->whereCode($data['code'])->first();
$old = TransactionCurrency::query()->withTrashed()->whereCode($data['code'])->first();
$old->forceDelete();
Log::warning(sprintf('Force deleted old currency with ID #%d and code "%s".', $old->id, $data['code']));
}

View File

@@ -425,7 +425,8 @@ class TransactionJournalFactory
Log::debug('Will verify duplicate!');
/** @var null|TransactionJournalMeta $result */
$result = TransactionJournalMeta::withTrashed()
$result = TransactionJournalMeta::query()
->withTrashed()
->leftJoin('transaction_journals', 'transaction_journals.id', '=', 'journal_meta.transaction_journal_id')
->whereNotNull('transaction_journals.id')
->where('transaction_journals.user_id', $this->user->id)

View File

@@ -49,18 +49,23 @@ class DeletedAccountObserver
$repository->destroy($attachment);
}
$journalIds = Transaction::where('account_id', $account->id)->get(['transactions.transaction_journal_id'])->pluck('transaction_journal_id')->toArray();
$journalIds = Transaction::query()
->where('account_id', $account->id)
->get(['transactions.transaction_journal_id'])
->pluck('transaction_journal_id')
->toArray()
;
$groupIds = array_map(function (array $item) {
return $item['transaction_group_id'];
}, TransactionJournal::whereIn('id', $journalIds)->get(['transaction_journals.transaction_group_id'])->toArray());
}, TransactionJournal::query()->whereIn('id', $journalIds)->get(['transaction_journals.transaction_group_id'])->toArray());
if (count($journalIds) > 0) {
Transaction::whereIn('transaction_journal_id', $journalIds)->delete();
TransactionJournal::whereIn('id', $journalIds)->delete();
Transaction::query()->whereIn('transaction_journal_id', $journalIds)->delete();
TransactionJournal::query()->whereIn('id', $journalIds)->delete();
}
if (count($groupIds) > 0) {
TransactionGroup::whereIn('id', $groupIds)->delete();
TransactionGroup::query()->whereIn('id', $groupIds)->delete();
}
Log::debug(sprintf('Delete %d journal(s)', count($journalIds)));

Some files were not shown because too many files have changed in this diff Show More