mirror of
https://github.com/firefly-iii/firefly-iii.git
synced 2026-05-05 05:33:36 +00:00
Compare commits
71 Commits
develop-20
...
develop-20
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
5b80a5bdbe | ||
|
|
0202f4abd9 | ||
|
|
615d568479 | ||
|
|
2ace0d3f23 | ||
|
|
42204f8dc1 | ||
|
|
cfac8fa569 | ||
|
|
04704392f3 | ||
|
|
4b9bbc9d6a | ||
|
|
f24f535d39 | ||
|
|
3a9ac03358 | ||
|
|
4ac7fec5f6 | ||
|
|
b6759c3fa0 | ||
|
|
4a83b1e3e5 | ||
|
|
4b701dfc4c | ||
|
|
b2997d0a5a | ||
|
|
fd8722e401 | ||
|
|
e46153330a | ||
|
|
525f0c752a | ||
|
|
13e4160e85 | ||
|
|
7806d63f91 | ||
|
|
8c620b6536 | ||
|
|
e47ce30579 | ||
|
|
7e6eadc047 | ||
|
|
dae4f6f351 | ||
|
|
8c8af51bc4 | ||
|
|
a5e1cba39c | ||
|
|
96d56ad723 | ||
|
|
e4b1c3045e | ||
|
|
e974594fe3 | ||
|
|
c93a2dc23a | ||
|
|
639efee78a | ||
|
|
eb4971fec6 | ||
|
|
0c63a3380d | ||
|
|
edd30b2d42 | ||
|
|
a4f6c2b748 | ||
|
|
5fc90e0f76 | ||
|
|
e8ab7d8a93 | ||
|
|
e73d04bc0f | ||
|
|
c0eca4298a | ||
|
|
dafb43393a | ||
|
|
ba8155a391 | ||
|
|
9e4329ebfc | ||
|
|
60e2645e54 | ||
|
|
33a9e5b3f0 | ||
|
|
cd0290475b | ||
|
|
45528cf7d3 | ||
|
|
7cfd21362a | ||
|
|
f91063c88b | ||
|
|
30c1f4c13d | ||
|
|
39be5075eb | ||
|
|
714133dad5 | ||
|
|
1caf639b85 | ||
|
|
33ad34a719 | ||
|
|
dca1d962af | ||
|
|
1ebff22785 | ||
|
|
8b14a11969 | ||
|
|
7b0e40543b | ||
|
|
ea57a0a8c8 | ||
|
|
62ee37f631 | ||
|
|
c96cc8d941 | ||
|
|
0e97b4a6b8 | ||
|
|
3de7cfd3bf | ||
|
|
a6fd805202 | ||
|
|
541e1ac7b4 | ||
|
|
1c6b8af3a3 | ||
|
|
b33b22e0b3 | ||
|
|
30cce327e8 | ||
|
|
994e3dae18 | ||
|
|
b065150968 | ||
|
|
d18e9ffad0 | ||
|
|
fad5438909 |
72
.ci/php-cs-fixer/composer.lock
generated
72
.ci/php-cs-fixer/composer.lock
generated
@@ -1334,16 +1334,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/console",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/console.git",
|
||||
"reference": "5b66d385dc58f69652e56f78a4184615e3f2b7f7"
|
||||
"reference": "7113778e2e91f4709cb3194a75dfa9c0d028d94d"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/console/zipball/5b66d385dc58f69652e56f78a4184615e3f2b7f7",
|
||||
"reference": "5b66d385dc58f69652e56f78a4184615e3f2b7f7",
|
||||
"url": "https://api.github.com/repos/symfony/console/zipball/7113778e2e91f4709cb3194a75dfa9c0d028d94d",
|
||||
"reference": "7113778e2e91f4709cb3194a75dfa9c0d028d94d",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -1400,7 +1400,7 @@
|
||||
"terminal"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/console/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/console/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -1420,7 +1420,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:14:47+00:00"
|
||||
"time": "2026-04-29T15:02:55+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/deprecation-contracts",
|
||||
@@ -1491,16 +1491,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/event-dispatcher",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/event-dispatcher.git",
|
||||
"reference": "f662acc6ab22a3d6d716dcb44c381c6002940df6"
|
||||
"reference": "0c3c1a17604c4dbbec4b93fe162c538482096e1f"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/f662acc6ab22a3d6d716dcb44c381c6002940df6",
|
||||
"reference": "f662acc6ab22a3d6d716dcb44c381c6002940df6",
|
||||
"url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/0c3c1a17604c4dbbec4b93fe162c538482096e1f",
|
||||
"reference": "0c3c1a17604c4dbbec4b93fe162c538482096e1f",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -1552,7 +1552,7 @@
|
||||
"description": "Provides tools that allow your application components to communicate with each other by dispatching events and listening to them",
|
||||
"homepage": "https://symfony.com",
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/event-dispatcher/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/event-dispatcher/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -1572,7 +1572,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:14:47+00:00"
|
||||
"time": "2026-04-18T13:51:42+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/event-dispatcher-contracts",
|
||||
@@ -1652,16 +1652,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/filesystem",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/filesystem.git",
|
||||
"reference": "66b769ae743ce2d13e435528fbef4af03d623e5a"
|
||||
"reference": "d1ec4543d5c6c2dac78503c2fae5ea0b3608ce40"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/filesystem/zipball/66b769ae743ce2d13e435528fbef4af03d623e5a",
|
||||
"reference": "66b769ae743ce2d13e435528fbef4af03d623e5a",
|
||||
"url": "https://api.github.com/repos/symfony/filesystem/zipball/d1ec4543d5c6c2dac78503c2fae5ea0b3608ce40",
|
||||
"reference": "d1ec4543d5c6c2dac78503c2fae5ea0b3608ce40",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -1698,7 +1698,7 @@
|
||||
"description": "Provides basic utilities for the filesystem",
|
||||
"homepage": "https://symfony.com",
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/filesystem/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/filesystem/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -1718,7 +1718,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:14:47+00:00"
|
||||
"time": "2026-04-18T13:51:42+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/finder",
|
||||
@@ -1861,7 +1861,7 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-ctype",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-ctype.git",
|
||||
@@ -1920,7 +1920,7 @@
|
||||
"portable"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-ctype/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-ctype/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -1944,16 +1944,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-intl-grapheme",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-intl-grapheme.git",
|
||||
"reference": "ad1b7b9092976d6c948b8a187cec9faaea9ec1df"
|
||||
"reference": "4864388bfbd3001ce88e234fab652acd91fdc57e"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/polyfill-intl-grapheme/zipball/ad1b7b9092976d6c948b8a187cec9faaea9ec1df",
|
||||
"reference": "ad1b7b9092976d6c948b8a187cec9faaea9ec1df",
|
||||
"url": "https://api.github.com/repos/symfony/polyfill-intl-grapheme/zipball/4864388bfbd3001ce88e234fab652acd91fdc57e",
|
||||
"reference": "4864388bfbd3001ce88e234fab652acd91fdc57e",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -2002,7 +2002,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-intl-grapheme/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-intl-grapheme/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -2022,11 +2022,11 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-04-10T16:19:22+00:00"
|
||||
"time": "2026-04-26T13:13:48+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-intl-normalizer",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-intl-normalizer.git",
|
||||
@@ -2087,7 +2087,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-intl-normalizer/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-intl-normalizer/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -2111,7 +2111,7 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-mbstring",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-mbstring.git",
|
||||
@@ -2172,7 +2172,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-mbstring/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-mbstring/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -2196,7 +2196,7 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-php80",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-php80.git",
|
||||
@@ -2256,7 +2256,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-php80/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-php80/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -2280,7 +2280,7 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-php81",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-php81.git",
|
||||
@@ -2336,7 +2336,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-php81/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-php81/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -2360,7 +2360,7 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-php84",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-php84.git",
|
||||
@@ -2416,7 +2416,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-php84/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-php84/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
|
||||
8
.github/ISSUE_TEMPLATE/fr.yml
vendored
8
.github/ISSUE_TEMPLATE/fr.yml
vendored
@@ -12,6 +12,14 @@ body:
|
||||
required: true
|
||||
- label: I've used [the search](https://github.com/firefly-iii/firefly-iii/issues?q=is%3Aissue) and this has not been requested before.
|
||||
required: true
|
||||
- type: checkboxes
|
||||
attributes:
|
||||
label: Use of AI
|
||||
description: AI agents like Claude and CoPilot are not reliable tools. Do not use them.
|
||||
options:
|
||||
- label: I'm a real person and wrote this bug without assistance from AI.
|
||||
required: true
|
||||
|
||||
|
||||
- type: textarea
|
||||
attributes:
|
||||
|
||||
2
.github/security.md
vendored
2
.github/security.md
vendored
@@ -5,7 +5,7 @@ disclosure and response policy to ensure that critical issues are responsibly ha
|
||||
|
||||
## Supported versions
|
||||
|
||||
Only the latest Firefly III release is maintained. Applicable fixes, including security fixes, will not backported to
|
||||
Only the latest Firefly III release is maintained. Applicable fixes, including security fixes, will not be backported to
|
||||
older release branches. Please refer to [releases.md](https://github.com/firefly-iii/firefly-iii/blob/main/releases.md) for details.
|
||||
|
||||
## Reporting a vulnerability - private disclosure process
|
||||
|
||||
11
.github/workflows/release.yml
vendored
11
.github/workflows/release.yml
vendored
@@ -99,11 +99,6 @@ jobs:
|
||||
env:
|
||||
FIREFLY_III_ROOT: /github/workspace
|
||||
GH_TOKEN: ''
|
||||
- name: Setup Mago
|
||||
uses: nhedger/setup-mago@v1
|
||||
with:
|
||||
version: "latest"
|
||||
working-directory: "."
|
||||
- name: Run CI
|
||||
run: |
|
||||
cp .env.example .env
|
||||
@@ -113,17 +108,19 @@ jobs:
|
||||
|
||||
# format code.
|
||||
echo "Will now run Mago Format"
|
||||
mago format
|
||||
./vendor/bin/mago format
|
||||
sudo chown -R runner:docker resources/lang
|
||||
echo "Will now run PHPCS"
|
||||
.ci/phpcs.sh
|
||||
|
||||
# lint and check
|
||||
echo "Will now run Mago Lint"
|
||||
mago lint
|
||||
./vendor/bin/mago lint
|
||||
echo "Will now run PHPstan"
|
||||
.ci/phpstan.sh
|
||||
rm .env
|
||||
env:
|
||||
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
|
||||
- name: Crowdin action
|
||||
uses: crowdin/github-action@v2
|
||||
with:
|
||||
|
||||
@@ -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
|
||||
- tasnim0tantawi
|
||||
- Joe Longendyke
|
||||
- Daniel Holøien
|
||||
- Matthew Grove
|
||||
|
||||
@@ -179,9 +179,9 @@ final class CategoryController extends Controller
|
||||
|
||||
// order by amount
|
||||
usort($return, static fn (array $a, array $b): int => ((float) $a['entries']['spent'] + (float) $a['entries']['earned'])
|
||||
< ((float) $b['entries']['spent'] + (float) $b['entries']['earned'])
|
||||
? 1
|
||||
: -1);
|
||||
< ((float) $b['entries']['spent'] + (float) $b['entries']['earned'])
|
||||
? 1
|
||||
: -1);
|
||||
|
||||
return response()->json($this->clean($return));
|
||||
}
|
||||
|
||||
@@ -59,8 +59,9 @@ final class DestroyController extends Controller
|
||||
|
||||
public function destroy(DestroyRequest $request, TransactionCurrency $from, TransactionCurrency $to): JsonResponse
|
||||
{
|
||||
$first = Carbon::create(1970, 1, 1);
|
||||
$this->repository->deleteRates($from, $to);
|
||||
event(new DestroyedCurrencyExchangeRate($from, $to, $this->validateUserGroup($request)));
|
||||
event(new DestroyedCurrencyExchangeRate($from, $to, $this->validateUserGroup($request), $first));
|
||||
|
||||
return response()->json([], 204);
|
||||
}
|
||||
@@ -74,7 +75,7 @@ final class DestroyController extends Controller
|
||||
if (!$exchangeRate instanceof CurrencyExchangeRate) {
|
||||
throw new FireflyException('Bla');
|
||||
}
|
||||
event(new DestroyedCurrencyExchangeRate($from, $to, $this->validateUserGroup($request)));
|
||||
event(new DestroyedCurrencyExchangeRate($from, $to, $this->validateUserGroup($request), $date));
|
||||
|
||||
return response()->json([], 204);
|
||||
}
|
||||
@@ -85,7 +86,7 @@ final class DestroyController extends Controller
|
||||
$to = $exchangeRate->toCurrency;
|
||||
$this->repository->deleteRate($exchangeRate);
|
||||
|
||||
event(new DestroyedCurrencyExchangeRate($from, $to, $this->validateUserGroup($request)));
|
||||
event(new DestroyedCurrencyExchangeRate($from, $to, $this->validateUserGroup($request), $exchangeRate->date));
|
||||
|
||||
return response()->json([], 204);
|
||||
}
|
||||
|
||||
@@ -95,7 +95,9 @@ final class StoreController extends Controller
|
||||
$transactionGroup = $this->groupRepository->store($data);
|
||||
} catch (DuplicateTransactionException $e) {
|
||||
Log::warning('Caught a duplicate transaction. Return error message.');
|
||||
$validator = Validator::make(['transactions' => [['description' => $e->getMessage()]]], ['transactions.0.description' => new IsDuplicateTransaction()]);
|
||||
$validator = Validator::make(['transactions' => [['description' => $e->getMessage()]]], [
|
||||
'transactions.0.description' => new IsDuplicateTransaction(),
|
||||
]);
|
||||
|
||||
throw new ValidationException($validator);
|
||||
} catch (FireflyException $e) {
|
||||
|
||||
@@ -162,12 +162,12 @@ class StoreRequest extends FormRequest
|
||||
'transactions.*.sepa_batch_id' => 'min:1|max:255|nullable',
|
||||
|
||||
// dates
|
||||
'transactions.*.interest_date' => 'date|nullable',
|
||||
'transactions.*.book_date' => 'date|nullable',
|
||||
'transactions.*.process_date' => 'date|nullable',
|
||||
'transactions.*.due_date' => 'date|nullable',
|
||||
'transactions.*.payment_date' => 'date|nullable',
|
||||
'transactions.*.invoice_date' => 'date|nullable',
|
||||
'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',
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
@@ -209,12 +209,12 @@ class UpdateRequest extends FormRequest
|
||||
'transactions.*.sepa_batch_id' => 'min:1|max:255|nullable',
|
||||
|
||||
// dates
|
||||
'transactions.*.interest_date' => 'date|nullable',
|
||||
'transactions.*.book_date' => 'date|nullable',
|
||||
'transactions.*.process_date' => 'date|nullable',
|
||||
'transactions.*.due_date' => 'date|nullable',
|
||||
'transactions.*.payment_date' => 'date|nullable',
|
||||
'transactions.*.invoice_date' => 'date|nullable',
|
||||
'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',
|
||||
];
|
||||
}
|
||||
|
||||
|
||||
@@ -24,6 +24,7 @@ declare(strict_types=1);
|
||||
|
||||
namespace FireflyIII\Events\Model\CurrencyExchangeRate;
|
||||
|
||||
use Carbon\Carbon;
|
||||
use FireflyIII\Events\Event;
|
||||
use FireflyIII\Models\TransactionCurrency;
|
||||
use FireflyIII\Models\UserGroup;
|
||||
@@ -37,7 +38,8 @@ class DestroyedCurrencyExchangeRate extends Event
|
||||
public function __construct(
|
||||
public TransactionCurrency $from,
|
||||
public TransactionCurrency $to,
|
||||
public UserGroup $userGroup
|
||||
public UserGroup $userGroup,
|
||||
public Carbon $date
|
||||
) {
|
||||
Log::debug(sprintf('DestroyedCurrencyExchangeRate(%s, %s) Event', $from->code, $to->code));
|
||||
}
|
||||
|
||||
@@ -79,7 +79,7 @@ class PiggyBankObserver
|
||||
}
|
||||
|
||||
$params = new ConversionParameters();
|
||||
$params->user = $piggyBank->accounts()->first()?->user;
|
||||
$params->user = $piggyBank->accounts()->first()->user;
|
||||
$params->model = $piggyBank;
|
||||
$params->originalCurrency = $piggyBank->transactionCurrency;
|
||||
$params->amountField = 'target_amount';
|
||||
|
||||
105
app/Helpers/Functions/helpers.php
Normal file
105
app/Helpers/Functions/helpers.php
Normal file
@@ -0,0 +1,105 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
* helpers.php
|
||||
* Copyright (c) 2026 james@firefly-iii.org
|
||||
*
|
||||
* This file is part of Firefly III (https://github.com/firefly-iii).
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
declare(strict_types=1);
|
||||
|
||||
use FireflyIII\Exceptions\FireflyException;
|
||||
|
||||
use function Safe\mb_ord;
|
||||
use function Safe\preg_match;
|
||||
use function Safe\preg_replace_callback;
|
||||
|
||||
if (!function_exists('env_default_when_empty')) {
|
||||
/**
|
||||
* @return null|mixed
|
||||
*/
|
||||
function env_default_when_empty(mixed $value, bool|int|string|null $default = null): mixed
|
||||
{
|
||||
if (null === $value) {
|
||||
return $default;
|
||||
}
|
||||
if ('' === $value) {
|
||||
return $default;
|
||||
}
|
||||
|
||||
return $value;
|
||||
}
|
||||
}
|
||||
|
||||
if (!function_exists('string_is_equal')) {
|
||||
function string_is_equal(string $left, string $right): bool
|
||||
{
|
||||
return $left === $right;
|
||||
}
|
||||
}
|
||||
|
||||
if (!function_exists('blade_escape_js')) {
|
||||
function blade_escape_js(string $string): string
|
||||
{
|
||||
// escape all non-alphanumeric characters
|
||||
// into their \x or \uHHHH representations
|
||||
if (0 === preg_match('//u', $string)) {
|
||||
throw new FireflyException('The string to escape is not a valid UTF-8 string.');
|
||||
}
|
||||
|
||||
return preg_replace_callback(
|
||||
'#[^a-zA-Z0-9,\._]#Su',
|
||||
static function ($matches) {
|
||||
$char = $matches[0];
|
||||
|
||||
/*
|
||||
* A few characters have short escape sequences in JSON and JavaScript.
|
||||
* Escape sequences supported only by JavaScript, not JSON, are omitted.
|
||||
* \" is also supported but omitted, because the resulting string is not HTML safe.
|
||||
*/
|
||||
$short = match ($char) {
|
||||
'\\' => '\\\\',
|
||||
'/' => '\/',
|
||||
"\x08" => '\b',
|
||||
"\x0C" => '\f',
|
||||
"\x0A" => '\n',
|
||||
"\x0D" => '\r',
|
||||
"\x09" => '\t',
|
||||
default => false
|
||||
};
|
||||
|
||||
if ($short) {
|
||||
return $short;
|
||||
}
|
||||
|
||||
$codepoint = mb_ord($char, 'UTF-8');
|
||||
if (0x10_000 > $codepoint) {
|
||||
return \sprintf('\u%04X', $codepoint);
|
||||
}
|
||||
|
||||
// Split characters outside the BMP into surrogate pairs
|
||||
// https://tools.ietf.org/html/rfc2781.html#section-2.1
|
||||
$u = $codepoint - 0x10_000;
|
||||
$high = 0xD800 | ($u >> 10);
|
||||
$low = 0xDC00 | ($u & 0x3FF);
|
||||
|
||||
return \sprintf('\u%04X\u%04X', $high, $low);
|
||||
},
|
||||
$string
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -40,8 +40,7 @@ class ReportHelper implements ReportHelperInterface
|
||||
/**
|
||||
* ReportHelper constructor.
|
||||
*/
|
||||
public function __construct(
|
||||
/** @var BudgetRepositoryInterface The budget repository */
|
||||
public function __construct(/** @var BudgetRepositoryInterface The budget repository */
|
||||
protected BudgetRepositoryInterface $budgetRepository
|
||||
) {}
|
||||
|
||||
|
||||
@@ -245,13 +245,8 @@ final class IndexController extends Controller
|
||||
$inPast = $limitPeriod->startsBefore(now()) && $limitPeriod->endsBefore(now());
|
||||
$currency = $limit->transactionCurrency ?? $primaryCurrency;
|
||||
$amount = Steam::bcround($limit->amount, $currency->decimal_places);
|
||||
$spent = $this->opsRepository->sumExpenses(
|
||||
$limit->start_date,
|
||||
$limit->end_date,
|
||||
null,
|
||||
new Collection()->push($budget),
|
||||
$currency
|
||||
);
|
||||
$spent = $this->opsRepository->sumExpenses($limit->start_date, $limit->end_date, null, new Collection()->push($budget), $currency);
|
||||
|
||||
$spentAmount = $spent[$currency->id]['sum'] ?? '0';
|
||||
$array['budgeted'][] = [
|
||||
'id' => $limit->id,
|
||||
@@ -289,7 +284,7 @@ final class IndexController extends Controller
|
||||
|
||||
if (array_key_exists($currency->id, $spentArr) && array_key_exists('sum', $spentArr[$currency->id])) {
|
||||
$array['spent'][$currency->id]['spent'] = $spentArr[$currency->id]['sum'];
|
||||
$array['spent'][$currency->id]['spent_outside'] = bcmul(bcsub($spentInLimits[$currency->id], $spentArr[$currency->id]['sum']), '-1');
|
||||
$array['spent'][$currency->id]['spent_outside'] = Steam::negative(bcsub($spentInLimits[$currency->id], $spentArr[$currency->id]['sum']));
|
||||
$array['spent'][$currency->id]['currency_id'] = $currency->id;
|
||||
$array['spent'][$currency->id]['currency_symbol'] = $currency->symbol;
|
||||
$array['spent'][$currency->id]['currency_decimal_places'] = $currency->decimal_places;
|
||||
|
||||
@@ -589,7 +589,6 @@ final class AccountController extends Controller
|
||||
Log::debug('End of chart loop.');
|
||||
// second loop (yes) to create nice array with info! Yay!
|
||||
$chartData = [];
|
||||
|
||||
foreach ($return as $key => $info) {
|
||||
if ('balance' !== $key && 'pc_balance' !== $key) {
|
||||
// assume it's a currency:
|
||||
@@ -608,6 +607,11 @@ final class AccountController extends Controller
|
||||
$info['currency_code'] = $this->primaryCurrency->code;
|
||||
$info['label'] = sprintf('%s (%s) (%s)', $account->name, (string) trans('firefly.sum'), $this->primaryCurrency->symbol);
|
||||
}
|
||||
// do not add pc_balance to the array if the account is in the primary currency anyway,
|
||||
// and it has no currency balances.
|
||||
if (2 === count(array_keys($return)) && 'pc_balance' === $key && $accountCurrency->id === $this->primaryCurrency->id) {
|
||||
continue;
|
||||
}
|
||||
$chartData[] = $info;
|
||||
}
|
||||
|
||||
|
||||
@@ -115,6 +115,9 @@ final class OAuthController extends Controller
|
||||
|
||||
public function listClients(): JsonResponse
|
||||
{
|
||||
if (!auth()->check()) {
|
||||
return response()->json([]);
|
||||
}
|
||||
Log::debug('Now in listClients()');
|
||||
// Retrieving all the OAuth app clients that belong to the user...
|
||||
$clients = auth()->user()->oauthApps()->where('revoked', false)->get();
|
||||
|
||||
@@ -40,10 +40,9 @@ class Authenticate
|
||||
/**
|
||||
* Create a new middleware instance.
|
||||
*/
|
||||
public function __construct(
|
||||
/**
|
||||
* The authentication factory instance.
|
||||
*/
|
||||
public function __construct(/**
|
||||
* The authentication factory instance.
|
||||
*/
|
||||
protected Auth $auth
|
||||
) {}
|
||||
|
||||
|
||||
@@ -42,10 +42,9 @@ class Binder
|
||||
/**
|
||||
* Binder constructor.
|
||||
*/
|
||||
public function __construct(
|
||||
/**
|
||||
* The authentication factory instance.
|
||||
*/
|
||||
public function __construct(/**
|
||||
* The authentication factory instance.
|
||||
*/
|
||||
protected Auth $auth
|
||||
) {
|
||||
$this->binders = Domain::getBindables();
|
||||
|
||||
@@ -63,7 +63,7 @@ class SecureHeaders
|
||||
"base-uri 'self'",
|
||||
// "form-action 'self'", // safe
|
||||
"font-src 'self' data:",
|
||||
sprintf("connect-src 'self' %s", $trackingScriptSrc),
|
||||
sprintf("connect-src 'self' https://api.pwnedpasswords.com %s", $trackingScriptSrc),
|
||||
sprintf("img-src 'self' data: 'nonce-%1s' ", $nonce),
|
||||
"manifest-src 'self'",
|
||||
];
|
||||
|
||||
@@ -24,6 +24,7 @@ declare(strict_types=1);
|
||||
|
||||
namespace FireflyIII\Listeners\Model\CurrencyExchangeRate;
|
||||
|
||||
use Carbon\Carbon;
|
||||
use FireflyIII\Events\Model\CurrencyExchangeRate\CreatedCurrencyExchangeRate;
|
||||
use FireflyIII\Events\Model\CurrencyExchangeRate\DestroyedCurrencyExchangeRate;
|
||||
use FireflyIII\Events\Model\CurrencyExchangeRate\UpdatedCurrencyExchangeRate;
|
||||
@@ -42,20 +43,22 @@ class ProcessesExchangeRates
|
||||
Preferences::mark();
|
||||
Cache::clear();
|
||||
if ($event instanceof DestroyedCurrencyExchangeRate) {
|
||||
$this->handleCurrency($event->userGroup, $event->from);
|
||||
$this->handleCurrency($event->userGroup, $event->to);
|
||||
$this->handleCurrency($event->userGroup, $event->from, $event->date);
|
||||
$this->handleCurrency($event->userGroup, $event->to, $event->date);
|
||||
|
||||
return;
|
||||
}
|
||||
$this->handleCurrency($event->rate->userGroup, $event->rate->fromCurrency);
|
||||
$this->handleCurrency($event->rate->userGroup, $event->rate->toCurrency);
|
||||
$this->handleCurrency($event->rate->userGroup, $event->rate->fromCurrency, $event->rate->date);
|
||||
$this->handleCurrency($event->rate->userGroup, $event->rate->toCurrency, $event->rate->date);
|
||||
}
|
||||
|
||||
private function handleCurrency(UserGroup $userGroup, TransactionCurrency $currency): void
|
||||
private function handleCurrency(UserGroup $userGroup, TransactionCurrency $currency, Carbon $date): void
|
||||
{
|
||||
$calculator = new PrimaryAmountRecalculationService();
|
||||
$calculator->setDate($date);
|
||||
if (Amount::convertToPrimary()) {
|
||||
Log::debug(sprintf('Will now convert amounts to primary currency for currency %s.', $currency->code));
|
||||
$date->startOfDay();
|
||||
Log::debug(sprintf('Will now convert amounts to primary currency for currency %s after %s.', $currency->code, $date->format('Y-m-d')));
|
||||
|
||||
$calculator->recalculateForGroupAndCurrency($userGroup, $currency);
|
||||
// $calculator->recalculateForGroup($userGroup);
|
||||
|
||||
@@ -335,7 +335,9 @@ class BudgetLimitRepository implements BudgetLimitRepositoryInterface, UserGroup
|
||||
$limit = new BudgetLimit();
|
||||
$limit->budget()->associate($budget);
|
||||
$limit->start_date = $data['start_date']->format('Y-m-d');
|
||||
$limit->start_date_tz = $data['start_date']->format('e');
|
||||
$limit->end_date = $data['end_date']->format('Y-m-d');
|
||||
$limit->end_date_tz = $data['end_date']->format('e');
|
||||
$limit->amount = $data['amount'];
|
||||
$limit->generated = $data['generated'] ?? false;
|
||||
$limit->period = $data['period'] ?? '';
|
||||
|
||||
@@ -98,7 +98,7 @@ trait ModifiesPiggyBanks
|
||||
$maxAmount = $leftOnAccount;
|
||||
|
||||
Log::debug(sprintf('Left on account: %s on %s', $leftOnAccount, $today->format('Y-m-d H:i:s')));
|
||||
Log::debug(sprintf('Saved so far: %s', $savedSoFar));
|
||||
Log::debug(sprintf('Saved so far : %s', $savedSoFar));
|
||||
|
||||
if (0 !== bccomp($piggyBank->target_amount, '0')) {
|
||||
$leftToSave = bcsub($piggyBank->target_amount, (string) $savedSoFar);
|
||||
@@ -110,7 +110,7 @@ trait ModifiesPiggyBanks
|
||||
$compare = bccomp($amount, (string) $maxAmount);
|
||||
$result = $compare <= 0;
|
||||
|
||||
Log::debug(sprintf('Compare <= 0? %d, so canAddAmount is %s', $compare, var_export($result, true)));
|
||||
Log::debug(sprintf('Compare %s to %s <= 0? %d, so canAddAmount is %s', $amount, $maxAmount, $compare, var_export($result, true)));
|
||||
|
||||
return $result;
|
||||
}
|
||||
@@ -385,9 +385,9 @@ trait ModifiesPiggyBanks
|
||||
$piggyBank->target_date = $data['target_date'];
|
||||
$piggyBank->target_date_tz = $data['target_date']?->format('e');
|
||||
}
|
||||
if (array_key_exists('start_date', $data)) {
|
||||
if (array_key_exists('start_date', $data) && '' !== $data['start_date']) {
|
||||
$piggyBank->start_date = $data['start_date'];
|
||||
$piggyBank->start_date_tz = $data['target_date']?->format('e');
|
||||
$piggyBank->start_date_tz = $data['start_date']?->format('e');
|
||||
}
|
||||
$piggyBank->save();
|
||||
|
||||
|
||||
@@ -342,33 +342,6 @@ class PiggyBankRepository implements PiggyBankRepositoryInterface, UserGroupInte
|
||||
return $piggyBank->piggyBankRepetitions()->first();
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns the suggested amount the user should save per month, or "".
|
||||
*/
|
||||
public function getSuggestedMonthlyAmount(PiggyBank $piggyBank): string
|
||||
{
|
||||
$savePerMonth = '0';
|
||||
$currentAmount = $this->getCurrentAmount($piggyBank);
|
||||
if (null !== $piggyBank->target_date && $currentAmount < $piggyBank->target_amount) {
|
||||
$now = today(config('app.timezone'));
|
||||
$startDate = null !== $piggyBank->start_date && $piggyBank->start_date->gte($now) ? $piggyBank->start_date : $now;
|
||||
$diffInMonths = (int) $startDate->diffInMonths($piggyBank->target_date);
|
||||
$remainingAmount = bcsub((string) $piggyBank->target_amount, $currentAmount);
|
||||
|
||||
// more than 1 month to go and still need money to save:
|
||||
if ($diffInMonths > 0 && 1 === bccomp($remainingAmount, '0')) {
|
||||
$savePerMonth = bcdiv($remainingAmount, (string) $diffInMonths);
|
||||
}
|
||||
|
||||
// less than 1 month to go but still need money to save:
|
||||
if (0 === $diffInMonths && 1 === bccomp($remainingAmount, '0')) {
|
||||
$savePerMonth = $remainingAmount;
|
||||
}
|
||||
}
|
||||
|
||||
return $savePerMonth;
|
||||
}
|
||||
|
||||
/**
|
||||
* Get for piggy account what is left to put in piggies.
|
||||
*/
|
||||
|
||||
@@ -111,11 +111,6 @@ interface PiggyBankRepositoryInterface
|
||||
|
||||
public function getRepetition(PiggyBank $piggyBank, bool $overrule = false): ?PiggyBankRepetition;
|
||||
|
||||
/**
|
||||
* Returns the suggested amount the user should save per month, or "".
|
||||
*/
|
||||
public function getSuggestedMonthlyAmount(PiggyBank $piggyBank): string;
|
||||
|
||||
/**
|
||||
* Get for piggy account what is left to put in piggies.
|
||||
*/
|
||||
|
||||
@@ -166,7 +166,7 @@ class TransactionGroupRepository implements TransactionGroupRepositoryInterface,
|
||||
$set = TransactionJournalLink::where(static function (Builder $q) use ($journals): void {
|
||||
$q->whereIn('source_id', $journals);
|
||||
$q->orWhereIn('destination_id', $journals);
|
||||
})->with(['source', 'destination', 'source.transactions'])->leftJoin('link_types', 'link_types.id', '=', 'journal_links.link_type_id')->get([
|
||||
})->with(['source', 'notes', 'destination', 'source.transactions'])->leftJoin('link_types', 'link_types.id', '=', 'journal_links.link_type_id')->get([
|
||||
'journal_links.*',
|
||||
'link_types.inward',
|
||||
'link_types.outward',
|
||||
@@ -191,6 +191,7 @@ class TransactionGroupRepository implements TransactionGroupRepositoryInterface,
|
||||
'editable' => 1 === (int) $entry->editable,
|
||||
'amount' => $amount,
|
||||
'foreign_amount' => $foreignAmount,
|
||||
'notes' => null === $entry->notes->first() ? '' : $entry->notes->first()->text,
|
||||
];
|
||||
}
|
||||
if ($journalId === $entry->destination_id) {
|
||||
@@ -204,6 +205,7 @@ class TransactionGroupRepository implements TransactionGroupRepositoryInterface,
|
||||
'editable' => 1 === (int) $entry->editable,
|
||||
'amount' => $amount,
|
||||
'foreign_amount' => $foreignAmount,
|
||||
'notes' => null === $entry->notes->first() ? '' : $entry->notes->first()->text,
|
||||
];
|
||||
}
|
||||
}
|
||||
|
||||
@@ -50,7 +50,7 @@ class IsDateOrTime implements ValidationRule
|
||||
if (10 === strlen($value)) {
|
||||
// probably a date format.
|
||||
try {
|
||||
Carbon::createFromFormat('Y-m-d', $value);
|
||||
$object = Carbon::createFromFormat('Y-m-d', $value);
|
||||
} catch (InvalidDateException $e) {
|
||||
Log::error(sprintf('"%s" is not a valid date: %s', $value, $e->getMessage()));
|
||||
|
||||
@@ -64,13 +64,18 @@ class IsDateOrTime implements ValidationRule
|
||||
|
||||
return;
|
||||
}
|
||||
if ($object->year < 1970) {
|
||||
$fail('validation.date_or_time')->translate();
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
return;
|
||||
}
|
||||
|
||||
// is an atom string, I hope?
|
||||
try {
|
||||
Carbon::parse($value);
|
||||
$object = Carbon::parse($value);
|
||||
} catch (InvalidDateException $e) {
|
||||
Log::error(sprintf('"%s" is not a valid date or time: %s', $value, $e->getMessage()));
|
||||
|
||||
@@ -82,6 +87,11 @@ class IsDateOrTime implements ValidationRule
|
||||
|
||||
$fail('validation.date_or_time')->translate();
|
||||
|
||||
return;
|
||||
}
|
||||
if ($object->year < 1970) {
|
||||
$fail('validation.date_or_time')->translate();
|
||||
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -54,8 +54,9 @@ class IsEnoughInAccounts implements ValidationRule
|
||||
|
||||
$accounts = $this->data['accounts'];
|
||||
foreach ($accounts as $info) {
|
||||
$account = $repository->find((int) $info['account_id']);
|
||||
$amount = $info['current_amount'] ?? '0';
|
||||
$account = $repository->find((int) $info['account_id']);
|
||||
$amount = $info['current_amount'] ?? '0';
|
||||
$savedSoFar = $piggyRepos->getCurrentAmount($this->piggyBank, $account);
|
||||
if (null === $account) {
|
||||
$fail('validation.no_asset_account')->translate();
|
||||
|
||||
@@ -64,8 +65,8 @@ class IsEnoughInAccounts implements ValidationRule
|
||||
if ('' === $amount || 0 === bccomp($amount, '0')) {
|
||||
continue;
|
||||
}
|
||||
$diff = bcsub($amount, $piggyRepos->getCurrentAmount($this->piggyBank, $account));
|
||||
if (1 === bccomp($diff, '0') && !$piggyRepos->canAddAmount($this->piggyBank, $account, $amount)) {
|
||||
$diff = bcsub($amount, $savedSoFar);
|
||||
if (1 === bccomp($diff, '0') && !$piggyRepos->canAddAmount($this->piggyBank, $account, $diff)) {
|
||||
$fail('validation.cannot_add_piggy_amount')->translate();
|
||||
}
|
||||
}
|
||||
|
||||
@@ -24,6 +24,7 @@ declare(strict_types=1);
|
||||
|
||||
namespace FireflyIII\Services\Internal\Recalculate;
|
||||
|
||||
use Carbon\Carbon;
|
||||
use FireflyIII\Events\Model\Account\UpdatedExistingAccount;
|
||||
use FireflyIII\Handlers\Observer\TransactionObserver;
|
||||
use FireflyIII\Models\Account;
|
||||
@@ -52,6 +53,13 @@ use Illuminate\Support\Facades\Log;
|
||||
|
||||
class PrimaryAmountRecalculationService
|
||||
{
|
||||
private Carbon $date;
|
||||
|
||||
public function __construct()
|
||||
{
|
||||
$this->date = Carbon::createFromDate(1970, 1, 1);
|
||||
}
|
||||
|
||||
public function recalculate(): void
|
||||
{
|
||||
if (false === FireflyConfig::get('enable_exchange_rates', config('cer.enabled'))->data) {
|
||||
@@ -106,12 +114,18 @@ class PrimaryAmountRecalculationService
|
||||
$this->calculateTransactionsForCurrency($userGroup, $currency, $limitCurrency);
|
||||
}
|
||||
|
||||
public function setDate(?Carbon $date): void
|
||||
{
|
||||
$this->date = $date;
|
||||
}
|
||||
|
||||
private function calculateTransactions(UserGroup $userGroup, TransactionCurrency $currency): void
|
||||
{
|
||||
// custom query because of the potential size of this update.
|
||||
$set = DB::table('transactions')
|
||||
->join('transaction_journals', 'transaction_journals.id', '=', 'transactions.transaction_journal_id')
|
||||
->where('transaction_journals.user_group_id', $userGroup->id)
|
||||
->where('transaction_journals.date', '>=', $this->date)
|
||||
->where(static function (DatabaseBuilder $q1) use ($currency): void {
|
||||
$q1->where(static function (DatabaseBuilder $q2) use ($currency): void {
|
||||
$q2->whereNot('transactions.transaction_currency_id', $currency->id)->whereNull('transactions.foreign_currency_id');
|
||||
@@ -147,6 +161,7 @@ class PrimaryAmountRecalculationService
|
||||
$set = DB::table('transactions')
|
||||
->join('transaction_journals', 'transaction_journals.id', '=', 'transactions.transaction_journal_id')
|
||||
->where('transaction_journals.user_group_id', $userGroup->id)
|
||||
->where('transaction_journals.date', '>=', $this->date)
|
||||
->where(static function (DatabaseBuilder $q1) use ($currency): void {
|
||||
$q1->where(static function (DatabaseBuilder $q2) use ($currency): void {
|
||||
$q2->whereNot('transactions.transaction_currency_id', $currency->id)->whereNull('transactions.foreign_currency_id');
|
||||
@@ -279,7 +294,15 @@ class PrimaryAmountRecalculationService
|
||||
|
||||
private function recalculateBudgetLimits(Budget $budget, TransactionCurrency $currency): void
|
||||
{
|
||||
$set = $budget->budgetlimits()->where('transaction_currency_id', '!=', $currency->id)->get();
|
||||
$set = $budget
|
||||
->budgetlimits()
|
||||
->where(function (EloquentBuilder $q): void {
|
||||
$q->where('budget_limits.start_date', '>=', $this->date);
|
||||
$q->orWhere('budget_limits.end_date', '<=', $this->date);
|
||||
})
|
||||
->where('transaction_currency_id', '!=', $currency->id)
|
||||
->get()
|
||||
;
|
||||
|
||||
/** @var BudgetLimit $limit */
|
||||
foreach ($set as $limit) {
|
||||
@@ -436,6 +459,7 @@ class PrimaryAmountRecalculationService
|
||||
$success = DB::table('transactions')
|
||||
->join('transaction_journals', 'transaction_journals.id', '=', 'transactions.transaction_journal_id')
|
||||
->where('transaction_journals.user_group_id', $userGroup->id)
|
||||
->where('transaction_journals.date', '>=', $this->date)
|
||||
->where(static function (Builder $q): void {
|
||||
$q->whereNotNull('native_amount')->orWhereNotNull('native_foreign_amount');
|
||||
})
|
||||
|
||||
@@ -741,12 +741,12 @@ class JournalUpdateService
|
||||
if (null === $group || null === $this->transactionJournal) {
|
||||
return;
|
||||
}
|
||||
if (0 === bccomp($source->foreign_amount, $foreignAmount)) {
|
||||
if (0 === bccomp(Steam::positive($originalSourceAmount), Steam::positive($foreignAmount))) {
|
||||
Log::debug('Amount was not actually changed, return.');
|
||||
|
||||
return;
|
||||
}
|
||||
Log::debug('Amount was changed, needs audit log entry.');
|
||||
Log::debug(sprintf('Amount was changed (%s -> %s), needs audit log entry.', $originalSourceAmount, $foreignAmount));
|
||||
$transfer = TransactionTypeEnum::TRANSFER->value === $this->transactionJournal->transactionType->type;
|
||||
// $withdrawal = TransactionTypeEnum::WITHDRAWAL->value === $this->transactionJournal->transactionType->type;
|
||||
$deposit = TransactionTypeEnum::DEPOSIT->value === $this->transactionJournal->transactionType->type;
|
||||
|
||||
@@ -163,6 +163,7 @@ class PiggyBankEnrichment implements EnrichmentInterface
|
||||
}
|
||||
|
||||
// get suggested per month.
|
||||
|
||||
$meta['save_per_month'] = Steam::bcround(
|
||||
$this->getSuggestedMonthlyAmount($this->date, $item->target_date, $meta['target_amount'], $meta['current_amount']),
|
||||
$currency->decimal_places
|
||||
@@ -301,23 +302,21 @@ class PiggyBankEnrichment implements EnrichmentInterface
|
||||
if (null === $targetAmount || !$targetDate instanceof Carbon || !$startDate instanceof Carbon) {
|
||||
return '0';
|
||||
}
|
||||
$savePerMonth = '0';
|
||||
if (1 === bccomp($targetAmount, $currentAmount)) {
|
||||
$now = today(config('app.timezone'));
|
||||
$diffInMonths = (int) $startDate->diffInMonths($targetDate);
|
||||
$diffInMonths = ceil($startDate->diffInMonths($targetDate));
|
||||
$remainingAmount = bcsub($targetAmount, $currentAmount);
|
||||
|
||||
// more than 1 month to go and still need money to save:
|
||||
if ($diffInMonths > 0 && 1 === bccomp($remainingAmount, '0')) {
|
||||
$savePerMonth = bcdiv($remainingAmount, (string) $diffInMonths);
|
||||
return bcdiv($remainingAmount, (string) $diffInMonths);
|
||||
}
|
||||
|
||||
// less than 1 month to go but still need money to save:
|
||||
if (0 === $diffInMonths && 1 === bccomp($remainingAmount, '0')) {
|
||||
$savePerMonth = $remainingAmount;
|
||||
if (1 === bccomp($remainingAmount, '0')) {
|
||||
return $remainingAmount;
|
||||
}
|
||||
}
|
||||
|
||||
return $savePerMonth;
|
||||
return '0';
|
||||
}
|
||||
}
|
||||
|
||||
@@ -522,7 +522,7 @@ class OperatorQuerySearch implements SearchInterface
|
||||
$stringMethod = 'str_contains';
|
||||
}
|
||||
if (StringPosition::IS === $stringPosition) {
|
||||
$stringMethod = 'stringIsEqual';
|
||||
$stringMethod = 'string_is_equal';
|
||||
}
|
||||
|
||||
// get accounts:
|
||||
@@ -619,7 +619,7 @@ class OperatorQuerySearch implements SearchInterface
|
||||
$stringMethod = 'str_contains';
|
||||
}
|
||||
if (StringPosition::IS === $stringPosition) {
|
||||
$stringMethod = 'stringIsEqual';
|
||||
$stringMethod = 'string_is_equal';
|
||||
}
|
||||
|
||||
// search for accounts:
|
||||
|
||||
@@ -63,29 +63,7 @@ use PragmaRX\Google2FALaravel\Middleware as MFAMiddleware;
|
||||
|
||||
bcscale(12);
|
||||
|
||||
if (!function_exists('envDefaultWhenEmpty')) {
|
||||
/**
|
||||
*
|
||||
* @return mixed|null
|
||||
*/
|
||||
function envDefaultWhenEmpty(mixed $value, string | int | bool | null $default = null): mixed
|
||||
{
|
||||
if(null === $value) {
|
||||
return $default;
|
||||
}
|
||||
if('' === $value) {
|
||||
return $default;
|
||||
}
|
||||
return $value;
|
||||
}
|
||||
}
|
||||
|
||||
if (!function_exists('stringIsEqual')) {
|
||||
function stringIsEqual(string $left, string $right): bool
|
||||
{
|
||||
return $left === $right;
|
||||
}
|
||||
}
|
||||
|
||||
$app = Application::configure(basePath: dirname(__DIR__))
|
||||
->withRouting(
|
||||
|
||||
18
changelog.md
18
changelog.md
@@ -3,6 +3,24 @@
|
||||
All notable changes to this project will be documented in this file.
|
||||
This project adheres to [Semantic Versioning](http://semver.org/).
|
||||
|
||||
## v6.6.2 - 2026-04-28
|
||||
|
||||
<!-- summary: This releases fixes a security issue and some small UI issues. Please upgrade at your earliest convenience. -->
|
||||
|
||||
### Added
|
||||
|
||||
- [PR 12179](https://github.com/firefly-iii/firefly-iii/pull/12179) (implement password validation JS script) reported by @tasnim0tantawi
|
||||
- [PR 12182](https://github.com/firefly-iii/firefly-iii/pull/12182) (fix shrinked sidebar expanding when navigating by clicking on icons) reported by @tasnim0tantawi
|
||||
|
||||
### Fixed
|
||||
|
||||
- [Issue 12169](https://github.com/firefly-iii/firefly-iii/issues/12169) (The 'Running balance' column is not showing the respective calculation instantly for new records that use 'Rules') reported by @jgmm81
|
||||
- [Issue 12186](https://github.com/firefly-iii/firefly-iii/issues/12186) (Set a year validator accepted by the system when saving or editing a transaction) reported by @jgmm81
|
||||
|
||||
### Security
|
||||
|
||||
- Fixed an issue where oAuth tokens could be generated before you confirmed your 2FA state. This would allow access to your data when your password was stolen, despite you having MFA enabled.
|
||||
|
||||
## v6.6.1 - 2026-04-19
|
||||
|
||||
<!-- summary: This releases upgrades many dependencies and will invalidate all of your OAuth-tokens and clients. -->
|
||||
|
||||
@@ -111,7 +111,9 @@
|
||||
},
|
||||
"require-dev": {
|
||||
"barryvdh/laravel-ide-helper": "^3",
|
||||
"carthage-software/mago": "^1.24.0",
|
||||
"driftingly/rector-laravel": "^2.0",
|
||||
"ergebnis/phpstan-rules": "^2",
|
||||
"fakerphp/faker": "1.*",
|
||||
"filp/whoops": "2.*",
|
||||
"fruitcake/laravel-debugbar": "^4.0",
|
||||
@@ -124,8 +126,7 @@
|
||||
"phpstan/phpstan-strict-rules": "^2",
|
||||
"phpunit/phpunit": "^13",
|
||||
"rector/rector": "^2.3",
|
||||
"thecodingmachine/phpstan-safe-rule": "^1.4",
|
||||
"ergebnis/phpstan-rules": "^2"
|
||||
"thecodingmachine/phpstan-safe-rule": "^1.4"
|
||||
},
|
||||
"replace": {
|
||||
"symfony/polyfill-php54": "*",
|
||||
@@ -135,6 +136,9 @@
|
||||
|
||||
"suggest": {},
|
||||
"autoload": {
|
||||
"files": [
|
||||
"app/Helpers/Functions/helpers.php"
|
||||
],
|
||||
"psr-4": {
|
||||
"FireflyIII\\": "app/",
|
||||
"Domain\\": "domain/",
|
||||
|
||||
398
composer.lock
generated
398
composer.lock
generated
@@ -4,7 +4,7 @@
|
||||
"Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
|
||||
"This file is @generated automatically"
|
||||
],
|
||||
"content-hash": "4f1f0dcde32d2f02333bd7af2cbc90eb",
|
||||
"content-hash": "7f960fa15bddd432267fb2bb9b730195",
|
||||
"packages": [
|
||||
{
|
||||
"name": "bacon/bacon-qr-code",
|
||||
@@ -1879,16 +1879,16 @@
|
||||
},
|
||||
{
|
||||
"name": "laravel/framework",
|
||||
"version": "v13.6.0",
|
||||
"version": "v13.7.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/laravel/framework.git",
|
||||
"reference": "416a93ea9c53161e0d4b8a44045f447b65a7d2f1"
|
||||
"reference": "f13b85b2cce7ef5e8f3bcdf2b6c6364bbdedae0b"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/laravel/framework/zipball/416a93ea9c53161e0d4b8a44045f447b65a7d2f1",
|
||||
"reference": "416a93ea9c53161e0d4b8a44045f447b65a7d2f1",
|
||||
"url": "https://api.github.com/repos/laravel/framework/zipball/f13b85b2cce7ef5e8f3bcdf2b6c6364bbdedae0b",
|
||||
"reference": "f13b85b2cce7ef5e8f3bcdf2b6c6364bbdedae0b",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -1931,6 +1931,7 @@
|
||||
"symfony/mime": "^7.4.0 || ^8.0.0",
|
||||
"symfony/polyfill-php84": "^1.33",
|
||||
"symfony/polyfill-php85": "^1.33",
|
||||
"symfony/polyfill-php86": "^1.36",
|
||||
"symfony/process": "^7.4.5 || ^8.0.5",
|
||||
"symfony/routing": "^7.4.0 || ^8.0.0",
|
||||
"symfony/uid": "^7.4.0 || ^8.0.0",
|
||||
@@ -2098,7 +2099,7 @@
|
||||
"issues": "https://github.com/laravel/framework/issues",
|
||||
"source": "https://github.com/laravel/framework"
|
||||
},
|
||||
"time": "2026-04-21T13:32:11+00:00"
|
||||
"time": "2026-04-28T17:18:25+00:00"
|
||||
},
|
||||
{
|
||||
"name": "laravel/passport",
|
||||
@@ -2236,16 +2237,16 @@
|
||||
},
|
||||
{
|
||||
"name": "laravel/serializable-closure",
|
||||
"version": "v2.0.12",
|
||||
"version": "v2.0.13",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/laravel/serializable-closure.git",
|
||||
"reference": "a6abb4e54f6fcd3138120b9ad497f0bd146f9919"
|
||||
"reference": "b566ee0dd251f3c4078bed003a7ce015f5ea6dce"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/laravel/serializable-closure/zipball/a6abb4e54f6fcd3138120b9ad497f0bd146f9919",
|
||||
"reference": "a6abb4e54f6fcd3138120b9ad497f0bd146f9919",
|
||||
"url": "https://api.github.com/repos/laravel/serializable-closure/zipball/b566ee0dd251f3c4078bed003a7ce015f5ea6dce",
|
||||
"reference": "b566ee0dd251f3c4078bed003a7ce015f5ea6dce",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -2293,7 +2294,7 @@
|
||||
"issues": "https://github.com/laravel/serializable-closure/issues",
|
||||
"source": "https://github.com/laravel/serializable-closure"
|
||||
},
|
||||
"time": "2026-04-14T13:33:34+00:00"
|
||||
"time": "2026-04-16T14:03:50+00:00"
|
||||
},
|
||||
{
|
||||
"name": "laravel/slack-notification-channel",
|
||||
@@ -4776,16 +4777,16 @@
|
||||
},
|
||||
{
|
||||
"name": "phpseclib/phpseclib",
|
||||
"version": "3.0.51",
|
||||
"version": "3.0.52",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/phpseclib/phpseclib.git",
|
||||
"reference": "d59c94077f9c9915abb51ddb52ce85188ece1748"
|
||||
"reference": "2adaefc83df2ec548558307690f376dd7d4f4fce"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/phpseclib/phpseclib/zipball/d59c94077f9c9915abb51ddb52ce85188ece1748",
|
||||
"reference": "d59c94077f9c9915abb51ddb52ce85188ece1748",
|
||||
"url": "https://api.github.com/repos/phpseclib/phpseclib/zipball/2adaefc83df2ec548558307690f376dd7d4f4fce",
|
||||
"reference": "2adaefc83df2ec548558307690f376dd7d4f4fce",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -4866,7 +4867,7 @@
|
||||
],
|
||||
"support": {
|
||||
"issues": "https://github.com/phpseclib/phpseclib/issues",
|
||||
"source": "https://github.com/phpseclib/phpseclib/tree/3.0.51"
|
||||
"source": "https://github.com/phpseclib/phpseclib/tree/3.0.52"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -4882,7 +4883,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-04-10T01:33:53+00:00"
|
||||
"time": "2026-04-27T07:02:15+00:00"
|
||||
},
|
||||
{
|
||||
"name": "pragmarx/google2fa",
|
||||
@@ -6496,16 +6497,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/cache",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/cache.git",
|
||||
"reference": "8abf3ccbeae9d3071b81a3ae7ee11b209f9e1e78"
|
||||
"reference": "2866a183cd942bbaa81e9fdbd1ef1ea902c5ee2d"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/cache/zipball/8abf3ccbeae9d3071b81a3ae7ee11b209f9e1e78",
|
||||
"reference": "8abf3ccbeae9d3071b81a3ae7ee11b209f9e1e78",
|
||||
"url": "https://api.github.com/repos/symfony/cache/zipball/2866a183cd942bbaa81e9fdbd1ef1ea902c5ee2d",
|
||||
"reference": "2866a183cd942bbaa81e9fdbd1ef1ea902c5ee2d",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -6572,7 +6573,7 @@
|
||||
"psr6"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/cache/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/cache/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -6592,7 +6593,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:18:51+00:00"
|
||||
"time": "2026-04-29T15:02:55+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/cache-contracts",
|
||||
@@ -6749,16 +6750,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/console",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/console.git",
|
||||
"reference": "5b66d385dc58f69652e56f78a4184615e3f2b7f7"
|
||||
"reference": "7113778e2e91f4709cb3194a75dfa9c0d028d94d"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/console/zipball/5b66d385dc58f69652e56f78a4184615e3f2b7f7",
|
||||
"reference": "5b66d385dc58f69652e56f78a4184615e3f2b7f7",
|
||||
"url": "https://api.github.com/repos/symfony/console/zipball/7113778e2e91f4709cb3194a75dfa9c0d028d94d",
|
||||
"reference": "7113778e2e91f4709cb3194a75dfa9c0d028d94d",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -6815,7 +6816,7 @@
|
||||
"terminal"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/console/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/console/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -6835,20 +6836,20 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:14:47+00:00"
|
||||
"time": "2026-04-29T15:02:55+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/css-selector",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/css-selector.git",
|
||||
"reference": "8db1c00226a94d8ab6aa89d9224eeee91e2ea2ed"
|
||||
"reference": "3665cfade90565430909b906394c73c8739e57d0"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/css-selector/zipball/8db1c00226a94d8ab6aa89d9224eeee91e2ea2ed",
|
||||
"reference": "8db1c00226a94d8ab6aa89d9224eeee91e2ea2ed",
|
||||
"url": "https://api.github.com/repos/symfony/css-selector/zipball/3665cfade90565430909b906394c73c8739e57d0",
|
||||
"reference": "3665cfade90565430909b906394c73c8739e57d0",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -6884,7 +6885,7 @@
|
||||
"description": "Converts CSS selectors to XPath expressions",
|
||||
"homepage": "https://symfony.com",
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/css-selector/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/css-selector/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -6904,7 +6905,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:14:47+00:00"
|
||||
"time": "2026-04-18T13:51:42+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/deprecation-contracts",
|
||||
@@ -7056,16 +7057,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/event-dispatcher",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/event-dispatcher.git",
|
||||
"reference": "f662acc6ab22a3d6d716dcb44c381c6002940df6"
|
||||
"reference": "0c3c1a17604c4dbbec4b93fe162c538482096e1f"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/f662acc6ab22a3d6d716dcb44c381c6002940df6",
|
||||
"reference": "f662acc6ab22a3d6d716dcb44c381c6002940df6",
|
||||
"url": "https://api.github.com/repos/symfony/event-dispatcher/zipball/0c3c1a17604c4dbbec4b93fe162c538482096e1f",
|
||||
"reference": "0c3c1a17604c4dbbec4b93fe162c538482096e1f",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -7117,7 +7118,7 @@
|
||||
"description": "Provides tools that allow your application components to communicate with each other by dispatching events and listening to them",
|
||||
"homepage": "https://symfony.com",
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/event-dispatcher/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/event-dispatcher/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -7137,7 +7138,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:14:47+00:00"
|
||||
"time": "2026-04-18T13:51:42+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/event-dispatcher-contracts",
|
||||
@@ -7352,16 +7353,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/http-client",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/http-client.git",
|
||||
"reference": "356e43d6994ae9d7761fd404d40f78691deabe0e"
|
||||
"reference": "537c7f164078975b800f3f1c56810791024e4c77"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/http-client/zipball/356e43d6994ae9d7761fd404d40f78691deabe0e",
|
||||
"reference": "356e43d6994ae9d7761fd404d40f78691deabe0e",
|
||||
"url": "https://api.github.com/repos/symfony/http-client/zipball/537c7f164078975b800f3f1c56810791024e4c77",
|
||||
"reference": "537c7f164078975b800f3f1c56810791024e4c77",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -7424,7 +7425,7 @@
|
||||
"http"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/http-client/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/http-client/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -7444,7 +7445,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:14:47+00:00"
|
||||
"time": "2026-04-29T15:02:55+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/http-client-contracts",
|
||||
@@ -7860,16 +7861,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/mime",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/mime.git",
|
||||
"reference": "ddff21f14c7ce04b98101b399a9463dce8b0ce66"
|
||||
"reference": "a9fcb293650c054b62a5b406f4e92e7b711ea333"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/mime/zipball/ddff21f14c7ce04b98101b399a9463dce8b0ce66",
|
||||
"reference": "ddff21f14c7ce04b98101b399a9463dce8b0ce66",
|
||||
"url": "https://api.github.com/repos/symfony/mime/zipball/a9fcb293650c054b62a5b406f4e92e7b711ea333",
|
||||
"reference": "a9fcb293650c054b62a5b406f4e92e7b711ea333",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -7922,7 +7923,7 @@
|
||||
"mime-type"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/mime/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/mime/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -7942,7 +7943,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:14:47+00:00"
|
||||
"time": "2026-04-29T15:02:55+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/options-resolver",
|
||||
@@ -8017,7 +8018,7 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-ctype",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-ctype.git",
|
||||
@@ -8076,7 +8077,7 @@
|
||||
"portable"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-ctype/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-ctype/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -8100,16 +8101,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-intl-grapheme",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-intl-grapheme.git",
|
||||
"reference": "ad1b7b9092976d6c948b8a187cec9faaea9ec1df"
|
||||
"reference": "4864388bfbd3001ce88e234fab652acd91fdc57e"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/polyfill-intl-grapheme/zipball/ad1b7b9092976d6c948b8a187cec9faaea9ec1df",
|
||||
"reference": "ad1b7b9092976d6c948b8a187cec9faaea9ec1df",
|
||||
"url": "https://api.github.com/repos/symfony/polyfill-intl-grapheme/zipball/4864388bfbd3001ce88e234fab652acd91fdc57e",
|
||||
"reference": "4864388bfbd3001ce88e234fab652acd91fdc57e",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -8158,7 +8159,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-intl-grapheme/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-intl-grapheme/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -8178,11 +8179,11 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-04-10T16:19:22+00:00"
|
||||
"time": "2026-04-26T13:13:48+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-intl-idn",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-intl-idn.git",
|
||||
@@ -8245,7 +8246,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-intl-idn/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-intl-idn/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -8269,7 +8270,7 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-intl-normalizer",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-intl-normalizer.git",
|
||||
@@ -8330,7 +8331,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-intl-normalizer/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-intl-normalizer/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -8354,7 +8355,7 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-php80",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-php80.git",
|
||||
@@ -8414,7 +8415,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-php80/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-php80/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -8438,7 +8439,7 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-php84",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-php84.git",
|
||||
@@ -8494,7 +8495,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-php84/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-php84/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -8518,16 +8519,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-php85",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-php85.git",
|
||||
"reference": "2c408a6bb0313e6001a83628dc5506100474254e"
|
||||
"reference": "fcfa4973a9917cef23f2e38774da74a2b7d115ee"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/polyfill-php85/zipball/2c408a6bb0313e6001a83628dc5506100474254e",
|
||||
"reference": "2c408a6bb0313e6001a83628dc5506100474254e",
|
||||
"url": "https://api.github.com/repos/symfony/polyfill-php85/zipball/fcfa4973a9917cef23f2e38774da74a2b7d115ee",
|
||||
"reference": "fcfa4973a9917cef23f2e38774da74a2b7d115ee",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -8574,7 +8575,7 @@
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-php85/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-php85/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -8594,11 +8595,91 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-04-10T16:50:15+00:00"
|
||||
"time": "2026-04-26T13:10:57+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-php86",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-php86.git",
|
||||
"reference": "33d8fc5a705481e21fe3a81212b26f9b1f61749c"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/polyfill-php86/zipball/33d8fc5a705481e21fe3a81212b26f9b1f61749c",
|
||||
"reference": "33d8fc5a705481e21fe3a81212b26f9b1f61749c",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": ">=7.2"
|
||||
},
|
||||
"type": "library",
|
||||
"extra": {
|
||||
"thanks": {
|
||||
"url": "https://github.com/symfony/polyfill",
|
||||
"name": "symfony/polyfill"
|
||||
}
|
||||
},
|
||||
"autoload": {
|
||||
"files": [
|
||||
"bootstrap.php"
|
||||
],
|
||||
"psr-4": {
|
||||
"Symfony\\Polyfill\\Php86\\": ""
|
||||
},
|
||||
"classmap": [
|
||||
"Resources/stubs"
|
||||
]
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Nicolas Grekas",
|
||||
"email": "p@tchwork.com"
|
||||
},
|
||||
{
|
||||
"name": "Symfony Community",
|
||||
"homepage": "https://symfony.com/contributors"
|
||||
}
|
||||
],
|
||||
"description": "Symfony polyfill backporting some PHP 8.6+ features to lower PHP versions",
|
||||
"homepage": "https://symfony.com",
|
||||
"keywords": [
|
||||
"compatibility",
|
||||
"polyfill",
|
||||
"portable",
|
||||
"shim"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-php86/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
"url": "https://symfony.com/sponsor",
|
||||
"type": "custom"
|
||||
},
|
||||
{
|
||||
"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": "2026-04-26T13:13:48+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/polyfill-uuid",
|
||||
"version": "v1.36.0",
|
||||
"version": "v1.37.0",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/polyfill-uuid.git",
|
||||
@@ -8657,7 +8738,7 @@
|
||||
"uuid"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/polyfill-uuid/tree/v1.36.0"
|
||||
"source": "https://github.com/symfony/polyfill-uuid/tree/v1.37.0"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -8833,16 +8914,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/routing",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/routing.git",
|
||||
"reference": "0de330ec2ea922a7b08ec45615bd51179de7fda4"
|
||||
"reference": "75d1bd8e5da3424e4db2fc3ff0222cb4d0c73038"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/routing/zipball/0de330ec2ea922a7b08ec45615bd51179de7fda4",
|
||||
"reference": "0de330ec2ea922a7b08ec45615bd51179de7fda4",
|
||||
"url": "https://api.github.com/repos/symfony/routing/zipball/75d1bd8e5da3424e4db2fc3ff0222cb4d0c73038",
|
||||
"reference": "75d1bd8e5da3424e4db2fc3ff0222cb4d0c73038",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -8889,7 +8970,7 @@
|
||||
"url"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/routing/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/routing/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -8909,7 +8990,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:14:47+00:00"
|
||||
"time": "2026-04-29T15:02:55+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/service-contracts",
|
||||
@@ -9265,16 +9346,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/uid",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/uid.git",
|
||||
"reference": "f63fa6096a24147283bce4d29327d285326438e0"
|
||||
"reference": "4d9d6510bbe88ebb4608b7200d18606cdf80825c"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/uid/zipball/f63fa6096a24147283bce4d29327d285326438e0",
|
||||
"reference": "f63fa6096a24147283bce4d29327d285326438e0",
|
||||
"url": "https://api.github.com/repos/symfony/uid/zipball/4d9d6510bbe88ebb4608b7200d18606cdf80825c",
|
||||
"reference": "4d9d6510bbe88ebb4608b7200d18606cdf80825c",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -9319,7 +9400,7 @@
|
||||
"uuid"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/uid/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/uid/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -9339,7 +9420,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:14:47+00:00"
|
||||
"time": "2026-04-30T16:10:06+00:00"
|
||||
},
|
||||
{
|
||||
"name": "symfony/var-dumper",
|
||||
@@ -9430,16 +9511,16 @@
|
||||
},
|
||||
{
|
||||
"name": "symfony/var-exporter",
|
||||
"version": "v8.0.8",
|
||||
"version": "v8.0.9",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/symfony/var-exporter.git",
|
||||
"reference": "15776bb07a91b089037da89f8832fa41d5fa6ec6"
|
||||
"reference": "24cf67be4dd0926e4413635418682f4fff831412"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/symfony/var-exporter/zipball/15776bb07a91b089037da89f8832fa41d5fa6ec6",
|
||||
"reference": "15776bb07a91b089037da89f8832fa41d5fa6ec6",
|
||||
"url": "https://api.github.com/repos/symfony/var-exporter/zipball/24cf67be4dd0926e4413635418682f4fff831412",
|
||||
"reference": "24cf67be4dd0926e4413635418682f4fff831412",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -9486,7 +9567,7 @@
|
||||
"serialize"
|
||||
],
|
||||
"support": {
|
||||
"source": "https://github.com/symfony/var-exporter/tree/v8.0.8"
|
||||
"source": "https://github.com/symfony/var-exporter/tree/v8.0.9"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -9506,7 +9587,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-03-30T15:14:47+00:00"
|
||||
"time": "2026-04-18T13:51:42+00:00"
|
||||
},
|
||||
{
|
||||
"name": "thecodingmachine/safe",
|
||||
@@ -9872,16 +9953,16 @@
|
||||
},
|
||||
{
|
||||
"name": "voku/portable-ascii",
|
||||
"version": "2.1.0",
|
||||
"version": "2.1.1",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/voku/portable-ascii.git",
|
||||
"reference": "d870a33f0f79d2b4579740b0620200221ee44aeb"
|
||||
"reference": "8e1051fe39379367aecf014f41744ce7539a856f"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/voku/portable-ascii/zipball/d870a33f0f79d2b4579740b0620200221ee44aeb",
|
||||
"reference": "d870a33f0f79d2b4579740b0620200221ee44aeb",
|
||||
"url": "https://api.github.com/repos/voku/portable-ascii/zipball/8e1051fe39379367aecf014f41744ce7539a856f",
|
||||
"reference": "8e1051fe39379367aecf014f41744ce7539a856f",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -9918,7 +9999,7 @@
|
||||
],
|
||||
"support": {
|
||||
"issues": "https://github.com/voku/portable-ascii/issues",
|
||||
"source": "https://github.com/voku/portable-ascii/tree/2.1.0"
|
||||
"source": "https://github.com/voku/portable-ascii/tree/2.1.1"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -9942,7 +10023,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-04-16T23:10:39+00:00"
|
||||
"time": "2026-04-26T05:33:54+00:00"
|
||||
}
|
||||
],
|
||||
"packages-dev": [
|
||||
@@ -10093,6 +10174,62 @@
|
||||
},
|
||||
"time": "2026-03-05T20:09:01+00:00"
|
||||
},
|
||||
{
|
||||
"name": "carthage-software/mago",
|
||||
"version": "1.25.2",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/carthage-software/mago.git",
|
||||
"reference": "54e9645d15381aa78bf7113e01dcd1734ec43737"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/carthage-software/mago/zipball/54e9645d15381aa78bf7113e01dcd1734ec43737",
|
||||
"reference": "54e9645d15381aa78bf7113e01dcd1734ec43737",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"php": "~8.1 || ~8.2 || ~8.3 || ~8.4 || ~8.5 || ~8.6"
|
||||
},
|
||||
"suggest": {
|
||||
"ext-curl": "To show binary download progress"
|
||||
},
|
||||
"bin": [
|
||||
"composer/bin/mago"
|
||||
],
|
||||
"type": "library",
|
||||
"autoload": {
|
||||
"files": [
|
||||
"composer/functions.php",
|
||||
"composer/internal.php"
|
||||
]
|
||||
},
|
||||
"notification-url": "https://packagist.org/downloads/",
|
||||
"license": [
|
||||
"MIT OR Apache-2.0"
|
||||
],
|
||||
"authors": [
|
||||
{
|
||||
"name": "Saif Eddin Gmati",
|
||||
"email": "azjezz@carthage.software"
|
||||
}
|
||||
],
|
||||
"description": "Mago is a toolchain for PHP that aims to provide a set of tools to help developers write better code.",
|
||||
"keywords": [
|
||||
"dev"
|
||||
],
|
||||
"support": {
|
||||
"issues": "https://github.com/carthage-software/mago/issues",
|
||||
"source": "https://github.com/carthage-software/mago/tree/1.25.2"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
"url": "https://github.com/azjezz",
|
||||
"type": "github"
|
||||
}
|
||||
],
|
||||
"time": "2026-05-02T23:21:31+00:00"
|
||||
},
|
||||
{
|
||||
"name": "cloudcreativity/json-api-testing",
|
||||
"version": "v6.4.0",
|
||||
@@ -11141,16 +11278,16 @@
|
||||
},
|
||||
{
|
||||
"name": "php-debugbar/php-debugbar",
|
||||
"version": "v3.7.5",
|
||||
"version": "v3.7.6",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/php-debugbar/php-debugbar.git",
|
||||
"reference": "dbf77f48fa6e6b57ed57ae67aa047b2535697788"
|
||||
"reference": "1690ee1728827f9deb4b60457fa387cf44672c56"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/php-debugbar/php-debugbar/zipball/dbf77f48fa6e6b57ed57ae67aa047b2535697788",
|
||||
"reference": "dbf77f48fa6e6b57ed57ae67aa047b2535697788",
|
||||
"url": "https://api.github.com/repos/php-debugbar/php-debugbar/zipball/1690ee1728827f9deb4b60457fa387cf44672c56",
|
||||
"reference": "1690ee1728827f9deb4b60457fa387cf44672c56",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -11227,7 +11364,7 @@
|
||||
],
|
||||
"support": {
|
||||
"issues": "https://github.com/php-debugbar/php-debugbar/issues",
|
||||
"source": "https://github.com/php-debugbar/php-debugbar/tree/v3.7.5"
|
||||
"source": "https://github.com/php-debugbar/php-debugbar/tree/v3.7.6"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -11239,7 +11376,7 @@
|
||||
"type": "github"
|
||||
}
|
||||
],
|
||||
"time": "2026-04-15T11:58:43+00:00"
|
||||
"time": "2026-04-30T07:31:44+00:00"
|
||||
},
|
||||
{
|
||||
"name": "php-debugbar/symfony-bridge",
|
||||
@@ -11357,11 +11494,11 @@
|
||||
},
|
||||
{
|
||||
"name": "phpstan/phpstan",
|
||||
"version": "2.1.51",
|
||||
"version": "2.1.54",
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/phpstan/phpstan/zipball/dc3b523c45e714c70de2ac5113b958223b55dc59",
|
||||
"reference": "dc3b523c45e714c70de2ac5113b958223b55dc59",
|
||||
"url": "https://api.github.com/repos/phpstan/phpstan/zipball/8be50c3992107dc837b17da4d140fbbdf9a5c5bd",
|
||||
"reference": "8be50c3992107dc837b17da4d140fbbdf9a5c5bd",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -11406,7 +11543,7 @@
|
||||
"type": "github"
|
||||
}
|
||||
],
|
||||
"time": "2026-04-21T18:22:01+00:00"
|
||||
"time": "2026-04-29T13:31:09+00:00"
|
||||
},
|
||||
{
|
||||
"name": "phpstan/phpstan-deprecation-rules",
|
||||
@@ -11460,16 +11597,16 @@
|
||||
},
|
||||
{
|
||||
"name": "phpstan/phpstan-strict-rules",
|
||||
"version": "2.0.10",
|
||||
"version": "2.0.11",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/phpstan/phpstan-strict-rules.git",
|
||||
"reference": "1aba28b697c1e3b6bbec8a1725f8b11b6d3e5a5f"
|
||||
"reference": "9b000a578b85b32945b358b172c7b20e91189024"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/phpstan/phpstan-strict-rules/zipball/1aba28b697c1e3b6bbec8a1725f8b11b6d3e5a5f",
|
||||
"reference": "1aba28b697c1e3b6bbec8a1725f8b11b6d3e5a5f",
|
||||
"url": "https://api.github.com/repos/phpstan/phpstan-strict-rules/zipball/9b000a578b85b32945b358b172c7b20e91189024",
|
||||
"reference": "9b000a578b85b32945b358b172c7b20e91189024",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -11505,27 +11642,28 @@
|
||||
],
|
||||
"support": {
|
||||
"issues": "https://github.com/phpstan/phpstan-strict-rules/issues",
|
||||
"source": "https://github.com/phpstan/phpstan-strict-rules/tree/2.0.10"
|
||||
"source": "https://github.com/phpstan/phpstan-strict-rules/tree/2.0.11"
|
||||
},
|
||||
"time": "2026-02-11T14:17:32+00:00"
|
||||
"time": "2026-05-02T06:54:10+00:00"
|
||||
},
|
||||
{
|
||||
"name": "phpunit/php-code-coverage",
|
||||
"version": "14.1.3",
|
||||
"version": "14.1.6",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/sebastianbergmann/php-code-coverage.git",
|
||||
"reference": "24dc6fcf9f2a983de5b3f1199fb01e88d68e7474"
|
||||
"reference": "4991e47adce8e31e554aee8fdaabfc3b1d60707d"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/sebastianbergmann/php-code-coverage/zipball/24dc6fcf9f2a983de5b3f1199fb01e88d68e7474",
|
||||
"reference": "24dc6fcf9f2a983de5b3f1199fb01e88d68e7474",
|
||||
"url": "https://api.github.com/repos/sebastianbergmann/php-code-coverage/zipball/4991e47adce8e31e554aee8fdaabfc3b1d60707d",
|
||||
"reference": "4991e47adce8e31e554aee8fdaabfc3b1d60707d",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
"ext-dom": "*",
|
||||
"ext-libxml": "*",
|
||||
"ext-mbstring": "*",
|
||||
"ext-xmlwriter": "*",
|
||||
"nikic/php-parser": "^5.7.0",
|
||||
"php": ">=8.4",
|
||||
@@ -11576,7 +11714,7 @@
|
||||
"support": {
|
||||
"issues": "https://github.com/sebastianbergmann/php-code-coverage/issues",
|
||||
"security": "https://github.com/sebastianbergmann/php-code-coverage/security/policy",
|
||||
"source": "https://github.com/sebastianbergmann/php-code-coverage/tree/14.1.3"
|
||||
"source": "https://github.com/sebastianbergmann/php-code-coverage/tree/14.1.6"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -11596,7 +11734,7 @@
|
||||
"type": "tidelift"
|
||||
}
|
||||
],
|
||||
"time": "2026-04-18T05:41:54+00:00"
|
||||
"time": "2026-04-24T13:10:08+00:00"
|
||||
},
|
||||
{
|
||||
"name": "phpunit/php-file-iterator",
|
||||
@@ -11893,16 +12031,16 @@
|
||||
},
|
||||
{
|
||||
"name": "phpunit/phpunit",
|
||||
"version": "13.1.7",
|
||||
"version": "13.1.8",
|
||||
"source": {
|
||||
"type": "git",
|
||||
"url": "https://github.com/sebastianbergmann/phpunit.git",
|
||||
"reference": "ddd6401641861cdef94b922ef10d484f436e8dcd"
|
||||
"reference": "f49a2b5e51ffb33421745368cc099cf66830d71b"
|
||||
},
|
||||
"dist": {
|
||||
"type": "zip",
|
||||
"url": "https://api.github.com/repos/sebastianbergmann/phpunit/zipball/ddd6401641861cdef94b922ef10d484f436e8dcd",
|
||||
"reference": "ddd6401641861cdef94b922ef10d484f436e8dcd",
|
||||
"url": "https://api.github.com/repos/sebastianbergmann/phpunit/zipball/f49a2b5e51ffb33421745368cc099cf66830d71b",
|
||||
"reference": "f49a2b5e51ffb33421745368cc099cf66830d71b",
|
||||
"shasum": ""
|
||||
},
|
||||
"require": {
|
||||
@@ -11916,7 +12054,7 @@
|
||||
"phar-io/manifest": "^2.0.4",
|
||||
"phar-io/version": "^3.2.1",
|
||||
"php": ">=8.4.1",
|
||||
"phpunit/php-code-coverage": "^14.1.3",
|
||||
"phpunit/php-code-coverage": "^14.1.6",
|
||||
"phpunit/php-file-iterator": "^7.0.0",
|
||||
"phpunit/php-invoker": "^7.0.0",
|
||||
"phpunit/php-text-template": "^6.0.0",
|
||||
@@ -11972,7 +12110,7 @@
|
||||
"support": {
|
||||
"issues": "https://github.com/sebastianbergmann/phpunit/issues",
|
||||
"security": "https://github.com/sebastianbergmann/phpunit/security/policy",
|
||||
"source": "https://github.com/sebastianbergmann/phpunit/tree/13.1.7"
|
||||
"source": "https://github.com/sebastianbergmann/phpunit/tree/13.1.8"
|
||||
},
|
||||
"funding": [
|
||||
{
|
||||
@@ -11980,7 +12118,7 @@
|
||||
"type": "other"
|
||||
}
|
||||
],
|
||||
"time": "2026-04-18T06:14:52+00:00"
|
||||
"time": "2026-05-01T04:22:45+00:00"
|
||||
},
|
||||
{
|
||||
"name": "rector/rector",
|
||||
|
||||
@@ -36,12 +36,12 @@ use Illuminate\Support\Facades\URL;
|
||||
use Spatie\Html\Facades\Html;
|
||||
|
||||
return [
|
||||
'name' => envDefaultWhenEmpty(env('APP_NAME'), 'Firefly III'),
|
||||
'env' => envDefaultWhenEmpty(env('APP_ENV'), 'production'),
|
||||
'name' => env_default_when_empty(env('APP_NAME'), 'Firefly III'),
|
||||
'env' => env_default_when_empty(env('APP_ENV'), 'production'),
|
||||
'debug' => env('APP_DEBUG', false),
|
||||
'url' => envDefaultWhenEmpty(env('APP_URL'), 'http://localhost'),
|
||||
'timezone' => envDefaultWhenEmpty(env('TZ'), 'UTC'),
|
||||
'locale' => envDefaultWhenEmpty(env('DEFAULT_LANGUAGE'), 'en_US'),
|
||||
'url' => env_default_when_empty(env('APP_URL'), 'http://localhost'),
|
||||
'timezone' => env_default_when_empty(env('TZ'), 'UTC'),
|
||||
'locale' => env_default_when_empty(env('DEFAULT_LANGUAGE'), 'en_US'),
|
||||
'fallback_locale' => 'en_US',
|
||||
'key' => env('APP_KEY'),
|
||||
'cipher' => 'AES-256-CBC',
|
||||
|
||||
@@ -37,10 +37,10 @@ return [
|
||||
*/
|
||||
|
||||
'defaults' => [
|
||||
'guard' => envDefaultWhenEmpty(env('AUTHENTICATION_GUARD'), 'web'),
|
||||
'guard' => env_default_when_empty(env('AUTHENTICATION_GUARD'), 'web'),
|
||||
'passwords' => 'users',
|
||||
],
|
||||
'guard_header' => envDefaultWhenEmpty(env('AUTHENTICATION_GUARD_HEADER'), 'REMOTE_USER'),
|
||||
'guard_header' => env_default_when_empty(env('AUTHENTICATION_GUARD_HEADER'), 'REMOTE_USER'),
|
||||
'guard_email' => env('AUTHENTICATION_GUARD_EMAIL'),
|
||||
|
||||
/*
|
||||
|
||||
@@ -36,7 +36,7 @@ return [
|
||||
|
|
||||
*/
|
||||
|
||||
'default' => envDefaultWhenEmpty(env('CACHE_DRIVER'), 'file'),
|
||||
'default' => env_default_when_empty(env('CACHE_DRIVER'), 'file'),
|
||||
|
||||
/*
|
||||
|--------------------------------------------------------------------------
|
||||
|
||||
@@ -21,6 +21,7 @@
|
||||
*/
|
||||
|
||||
declare(strict_types=1);
|
||||
use Pdo\Mysql;
|
||||
|
||||
use function Safe\parse_url;
|
||||
|
||||
@@ -49,42 +50,42 @@ $mysql_ssl_ciphers = env('MYSQL_SSL_CIPHER');
|
||||
$mysql_ssl_verify = env('MYSQL_SSL_VERIFY_SERVER_CERT');
|
||||
|
||||
$mySqlSSLOptions = [];
|
||||
$useSSL = envDefaultWhenEmpty(env('MYSQL_USE_SSL'), false);
|
||||
$useSSL = env_default_when_empty(env('MYSQL_USE_SSL'), false);
|
||||
if (false !== $useSSL && null !== $useSSL && '' !== $useSSL) {
|
||||
if (null !== $mysql_ssl_ca_dir) {
|
||||
$mySqlSSLOptions[PDO::MYSQL_ATTR_SSL_CAPATH] = $mysql_ssl_ca_dir;
|
||||
$mySqlSSLOptions[Mysql::ATTR_SSL_CAPATH] = $mysql_ssl_ca_dir;
|
||||
}
|
||||
if (null !== $mysql_ssl_ca_file) {
|
||||
$mySqlSSLOptions[PDO::MYSQL_ATTR_SSL_CA] = $mysql_ssl_ca_file;
|
||||
$mySqlSSLOptions[Mysql::ATTR_SSL_CA] = $mysql_ssl_ca_file;
|
||||
}
|
||||
if (null !== $mysql_ssl_cert) {
|
||||
$mySqlSSLOptions[PDO::MYSQL_ATTR_SSL_CERT] = $mysql_ssl_cert;
|
||||
$mySqlSSLOptions[Mysql::ATTR_SSL_CERT] = $mysql_ssl_cert;
|
||||
}
|
||||
if (null !== $mysql_ssl_key) {
|
||||
$mySqlSSLOptions[PDO::MYSQL_ATTR_SSL_KEY] = $mysql_ssl_key;
|
||||
$mySqlSSLOptions[Mysql::ATTR_SSL_KEY] = $mysql_ssl_key;
|
||||
}
|
||||
if (null !== $mysql_ssl_ciphers) {
|
||||
$mySqlSSLOptions[PDO::MYSQL_ATTR_SSL_CIPHER] = $mysql_ssl_ciphers;
|
||||
$mySqlSSLOptions[Mysql::ATTR_SSL_CIPHER] = $mysql_ssl_ciphers;
|
||||
}
|
||||
if (null !== $mysql_ssl_verify) {
|
||||
$mySqlSSLOptions[PDO::MYSQL_ATTR_SSL_VERIFY_SERVER_CERT] = $mysql_ssl_verify;
|
||||
$mySqlSSLOptions[Mysql::ATTR_SSL_VERIFY_SERVER_CERT] = $mysql_ssl_verify;
|
||||
}
|
||||
}
|
||||
|
||||
return [
|
||||
'default' => envDefaultWhenEmpty(env('DB_CONNECTION'), 'mysql'),
|
||||
'default' => env_default_when_empty(env('DB_CONNECTION'), 'mysql'),
|
||||
'connections' => [
|
||||
'sqlite' => [
|
||||
'driver' => 'sqlite',
|
||||
'database' => envDefaultWhenEmpty(env('DB_DATABASE'), storage_path('database/database.sqlite')),
|
||||
'database' => env_default_when_empty(env('DB_DATABASE'), storage_path('database/database.sqlite')),
|
||||
'prefix' => '',
|
||||
],
|
||||
'mysql' => [
|
||||
'driver' => 'mysql',
|
||||
'host' => envDefaultWhenEmpty(env('DB_HOST'), $host),
|
||||
'port' => envDefaultWhenEmpty(env('DB_PORT'), $port),
|
||||
'database' => envDefaultWhenEmpty(env('DB_DATABASE'), $database),
|
||||
'username' => envDefaultWhenEmpty(env('DB_USERNAME'), $username),
|
||||
'host' => env_default_when_empty(env('DB_HOST'), $host),
|
||||
'port' => env_default_when_empty(env('DB_PORT'), $port),
|
||||
'database' => env_default_when_empty(env('DB_DATABASE'), $database),
|
||||
'username' => env_default_when_empty(env('DB_USERNAME'), $username),
|
||||
'password' => env('DB_PASSWORD', $password),
|
||||
'unix_socket' => env('DB_SOCKET', ''),
|
||||
'charset' => 'utf8mb4',
|
||||
@@ -96,16 +97,16 @@ return [
|
||||
],
|
||||
'pgsql' => [
|
||||
'driver' => 'pgsql',
|
||||
'host' => envDefaultWhenEmpty(env('DB_HOST'), $host),
|
||||
'port' => envDefaultWhenEmpty(env('DB_PORT'), $port),
|
||||
'database' => envDefaultWhenEmpty(env('DB_DATABASE'), $database),
|
||||
'username' => envDefaultWhenEmpty(env('DB_USERNAME'), $username),
|
||||
'host' => env_default_when_empty(env('DB_HOST'), $host),
|
||||
'port' => env_default_when_empty(env('DB_PORT'), $port),
|
||||
'database' => env_default_when_empty(env('DB_DATABASE'), $database),
|
||||
'username' => env_default_when_empty(env('DB_USERNAME'), $username),
|
||||
'password' => env('DB_PASSWORD', $password),
|
||||
'charset' => 'utf8',
|
||||
'prefix' => '',
|
||||
'search_path' => envDefaultWhenEmpty(env('PGSQL_SCHEMA'), 'public'),
|
||||
'schema' => envDefaultWhenEmpty(env('PGSQL_SCHEMA'), 'public'),
|
||||
'sslmode' => envDefaultWhenEmpty(env('PGSQL_SSL_MODE'), 'prefer'),
|
||||
'search_path' => env_default_when_empty(env('PGSQL_SCHEMA'), 'public'),
|
||||
'schema' => env_default_when_empty(env('PGSQL_SCHEMA'), 'public'),
|
||||
'sslmode' => env_default_when_empty(env('PGSQL_SSL_MODE'), 'prefer'),
|
||||
'sslcert' => env('PGSQL_SSL_CERT'),
|
||||
'sslkey' => env('PGSQL_SSL_KEY'),
|
||||
'sslrootcert' => env('PGSQL_SSL_ROOT_CERT'),
|
||||
@@ -139,21 +140,21 @@ return [
|
||||
// 'prefix' => env('REDIS_PREFIX', Str::slug(env('APP_NAME', 'laravel'), '_') . '_database_'),
|
||||
],
|
||||
'default' => [
|
||||
'scheme' => envDefaultWhenEmpty(env('REDIS_SCHEME'), 'tcp'),
|
||||
'scheme' => env_default_when_empty(env('REDIS_SCHEME'), 'tcp'),
|
||||
'url' => env('REDIS_URL'),
|
||||
'path' => env('REDIS_PATH'),
|
||||
'host' => envDefaultWhenEmpty(env('REDIS_HOST'), '127.0.0.1'),
|
||||
'port' => envDefaultWhenEmpty(env('REDIS_PORT'), 6379),
|
||||
'host' => env_default_when_empty(env('REDIS_HOST'), '127.0.0.1'),
|
||||
'port' => env_default_when_empty(env('REDIS_PORT'), 6379),
|
||||
'username' => env('REDIS_USERNAME'),
|
||||
'password' => env('REDIS_PASSWORD'),
|
||||
'database' => env('REDIS_DB', '0'),
|
||||
],
|
||||
'cache' => [
|
||||
'scheme' => envDefaultWhenEmpty(env('REDIS_SCHEME'), 'tcp'),
|
||||
'scheme' => env_default_when_empty(env('REDIS_SCHEME'), 'tcp'),
|
||||
'url' => env('REDIS_URL'),
|
||||
'path' => env('REDIS_PATH'),
|
||||
'host' => envDefaultWhenEmpty(env('REDIS_HOST'), '127.0.0.1'),
|
||||
'port' => envDefaultWhenEmpty(env('REDIS_PORT'), 6379),
|
||||
'host' => env_default_when_empty(env('REDIS_HOST'), '127.0.0.1'),
|
||||
'port' => env_default_when_empty(env('REDIS_PORT'), 6379),
|
||||
'username' => env('REDIS_USERNAME'),
|
||||
'password' => env('REDIS_PASSWORD'),
|
||||
'database' => env('REDIS_CACHE_DB', '1'),
|
||||
|
||||
@@ -75,18 +75,18 @@ return [
|
||||
'webhooks' => true,
|
||||
'handle_debts' => true,
|
||||
'expression_engine' => true,
|
||||
'running_balance_column' => (bool)envDefaultWhenEmpty(env('USE_RUNNING_BALANCE'), true), // this is only the default value, is not used.
|
||||
'running_balance_column' => (bool)env_default_when_empty(env('USE_RUNNING_BALANCE'), true), // this is only the default value, is not used.
|
||||
// see cer.php for exchange rates feature flag.
|
||||
],
|
||||
'version' => 'develop/2026-04-22',
|
||||
'build_time' => 1776876664,
|
||||
'version' => 'develop/2026-05-03',
|
||||
'build_time' => 1777795578,
|
||||
'api_version' => '2.1.0', // field is no longer used.
|
||||
'db_version' => 28, // field is no longer used.
|
||||
|
||||
// Docker build info, if present:
|
||||
'is_docker' => env('IS_DOCKER', false),
|
||||
'base_image_build' => envDefaultWhenEmpty(env('BASE_IMAGE_BUILD'), '(unknown)'),
|
||||
'base_image_date' => envDefaultWhenEmpty(env('BASE_IMAGE_DATE'), '(unknown)'),
|
||||
'base_image_build' => env_default_when_empty(env('BASE_IMAGE_BUILD'), '(unknown)'),
|
||||
'base_image_date' => env_default_when_empty(env('BASE_IMAGE_DATE'), '(unknown)'),
|
||||
'is_local_dev' => env('IS_LOCAL_DEV', false),
|
||||
|
||||
// generic settings
|
||||
@@ -112,8 +112,8 @@ return [
|
||||
'tracker_url' => env('TRACKER_URL', ''),
|
||||
|
||||
// authentication settings
|
||||
'authentication_guard' => envDefaultWhenEmpty(env('AUTHENTICATION_GUARD'), 'web'),
|
||||
'custom_logout_url' => envDefaultWhenEmpty(env('CUSTOM_LOGOUT_URL'), ''),
|
||||
'authentication_guard' => env_default_when_empty(env('AUTHENTICATION_GUARD'), 'web'),
|
||||
'custom_logout_url' => env_default_when_empty(env('CUSTOM_LOGOUT_URL'), ''),
|
||||
|
||||
// static config (cannot be changed by user)
|
||||
'update_endpoint' => 'https://version.firefly-iii.org/index.json',
|
||||
@@ -194,8 +194,8 @@ return [
|
||||
'convertToPrimary' => false,
|
||||
],
|
||||
'default_currency' => 'EUR',
|
||||
'default_language' => envDefaultWhenEmpty(env('DEFAULT_LANGUAGE'), 'en_US'),
|
||||
'default_locale' => envDefaultWhenEmpty(env('DEFAULT_LOCALE'), 'equal'),
|
||||
'default_language' => env_default_when_empty(env('DEFAULT_LANGUAGE'), 'en_US'),
|
||||
'default_locale' => env_default_when_empty(env('DEFAULT_LOCALE'), 'equal'),
|
||||
|
||||
// account types that may have or set a currency
|
||||
'valid_currency_account_types' => [
|
||||
@@ -224,7 +224,7 @@ return [
|
||||
'available_dark_modes' => ['light', 'dark', 'browser'],
|
||||
'bill_reminder_periods' => [90, 30, 14, 7, 0],
|
||||
'valid_view_ranges' => ['1D', '1W', '1M', '3M', '6M', '1Y'],
|
||||
'valid_url_protocols' => envDefaultWhenEmpty(env('VALID_URL_PROTOCOLS'), 'http,https,ftp,ftps,mailto'), // no longer used, only for default.
|
||||
'valid_url_protocols' => env_default_when_empty(env('VALID_URL_PROTOCOLS'), 'http,https,ftp,ftps,mailto'), // no longer used, only for default.
|
||||
'allowedMimes' => [
|
||||
// plain files
|
||||
'text/plain',
|
||||
|
||||
@@ -34,7 +34,7 @@ $validChannels = ['single', 'papertrail', 'stdout', 'daily', 'syslog', 'err
|
||||
$validAuditChannels = ['audit_papertrail', 'audit_stdout', 'audit_stdout', 'audit_daily', 'audit_syslog', 'audit_errorlog'];
|
||||
|
||||
// which settings did the user set, if any?
|
||||
$defaultLogChannel = (string) envDefaultWhenEmpty(env('LOG_CHANNEL'), 'stack');
|
||||
$defaultLogChannel = (string) env_default_when_empty(env('LOG_CHANNEL'), 'stack');
|
||||
$auditLogChannel = (string) env('AUDIT_LOG_CHANNEL');
|
||||
|
||||
if ('stack' === $defaultLogChannel) {
|
||||
@@ -60,8 +60,8 @@ return [
|
||||
|
|
||||
*/
|
||||
|
||||
'default' => envDefaultWhenEmpty(env('LOG_CHANNEL'), 'stack'),
|
||||
'level' => envDefaultWhenEmpty(env('APP_LOG_LEVEL'), 'info'),
|
||||
'default' => env_default_when_empty(env('LOG_CHANNEL'), 'stack'),
|
||||
'level' => env_default_when_empty(env('APP_LOG_LEVEL'), 'info'),
|
||||
/*
|
||||
|--------------------------------------------------------------------------
|
||||
| Log Channels
|
||||
@@ -93,11 +93,11 @@ return [
|
||||
'single' => [
|
||||
'driver' => 'single',
|
||||
'path' => storage_path('logs/laravel.log'),
|
||||
'level' => envDefaultWhenEmpty(env('APP_LOG_LEVEL'), 'info'),
|
||||
'level' => env_default_when_empty(env('APP_LOG_LEVEL'), 'info'),
|
||||
],
|
||||
'papertrail' => [
|
||||
'driver' => 'monolog',
|
||||
'level' => envDefaultWhenEmpty(env('APP_LOG_LEVEL'), 'info'),
|
||||
'level' => env_default_when_empty(env('APP_LOG_LEVEL'), 'info'),
|
||||
'handler' => SyslogUdpHandler::class,
|
||||
'handler_with' => [
|
||||
'host' => env('PAPERTRAIL_HOST'),
|
||||
@@ -107,21 +107,21 @@ return [
|
||||
'stdout' => [
|
||||
'driver' => 'single',
|
||||
'path' => 'php://stdout',
|
||||
'level' => envDefaultWhenEmpty(env('APP_LOG_LEVEL'), 'info'),
|
||||
'level' => env_default_when_empty(env('APP_LOG_LEVEL'), 'info'),
|
||||
],
|
||||
'daily' => [
|
||||
'driver' => 'daily',
|
||||
'path' => storage_path('logs/ff3-'.PHP_SAPI.'.log'),
|
||||
'level' => envDefaultWhenEmpty(env('APP_LOG_LEVEL'), 'info'),
|
||||
'level' => env_default_when_empty(env('APP_LOG_LEVEL'), 'info'),
|
||||
'days' => 7,
|
||||
],
|
||||
'syslog' => [
|
||||
'driver' => 'syslog',
|
||||
'level' => envDefaultWhenEmpty(env('APP_LOG_LEVEL'), 'info'),
|
||||
'level' => env_default_when_empty(env('APP_LOG_LEVEL'), 'info'),
|
||||
],
|
||||
'errorlog' => [
|
||||
'driver' => 'errorlog',
|
||||
'level' => envDefaultWhenEmpty(env('APP_LOG_LEVEL'), 'info'),
|
||||
'level' => env_default_when_empty(env('APP_LOG_LEVEL'), 'info'),
|
||||
],
|
||||
|
||||
/*
|
||||
@@ -130,7 +130,7 @@ return [
|
||||
*/
|
||||
'audit_papertrail' => [
|
||||
'driver' => 'monolog',
|
||||
'level' => envDefaultWhenEmpty(env('AUDIT_LOG_LEVEL'), 'info'),
|
||||
'level' => env_default_when_empty(env('AUDIT_LOG_LEVEL'), 'info'),
|
||||
'handler' => SyslogUdpHandler::class,
|
||||
'tap' => [AuditLogger::class],
|
||||
'handler_with' => [
|
||||
@@ -142,24 +142,24 @@ return [
|
||||
'driver' => 'single',
|
||||
'path' => 'php://stdout',
|
||||
'tap' => [AuditLogger::class],
|
||||
'level' => envDefaultWhenEmpty(env('AUDIT_LOG_LEVEL'), 'info'),
|
||||
'level' => env_default_when_empty(env('AUDIT_LOG_LEVEL'), 'info'),
|
||||
],
|
||||
'audit_daily' => [
|
||||
'driver' => 'daily',
|
||||
'path' => storage_path('logs/ff3-audit.log'),
|
||||
'tap' => [AuditLogger::class],
|
||||
'level' => envDefaultWhenEmpty(env('AUDIT_LOG_LEVEL'), 'info'),
|
||||
'level' => env_default_when_empty(env('AUDIT_LOG_LEVEL'), 'info'),
|
||||
'days' => 90,
|
||||
],
|
||||
'audit_syslog' => [
|
||||
'driver' => 'syslog',
|
||||
'tap' => [AuditLogger::class],
|
||||
'level' => envDefaultWhenEmpty(env('AUDIT_LOG_LEVEL'), 'info'),
|
||||
'level' => env_default_when_empty(env('AUDIT_LOG_LEVEL'), 'info'),
|
||||
],
|
||||
'audit_errorlog' => [
|
||||
'driver' => 'errorlog',
|
||||
'tap' => [AuditLogger::class],
|
||||
'level' => envDefaultWhenEmpty(env('AUDIT_LOG_LEVEL'), 'info'),
|
||||
'level' => env_default_when_empty(env('AUDIT_LOG_LEVEL'), 'info'),
|
||||
],
|
||||
],
|
||||
];
|
||||
|
||||
@@ -34,16 +34,16 @@ return [
|
||||
| and used as needed; however, this mailer will be used by default.
|
||||
|
|
||||
*/
|
||||
'default' => envDefaultWhenEmpty(env('MAIL_MAILER'), 'log'),
|
||||
'default' => env_default_when_empty(env('MAIL_MAILER'), 'log'),
|
||||
|
||||
'mailers' => [
|
||||
'smtp' => [
|
||||
'transport' => 'smtp',
|
||||
'host' => envDefaultWhenEmpty(env('MAIL_HOST'), 'smtp.mailtrap.io'),
|
||||
'host' => env_default_when_empty(env('MAIL_HOST'), 'smtp.mailtrap.io'),
|
||||
'port' => (int) env('MAIL_PORT', 2525),
|
||||
'encryption' => envDefaultWhenEmpty(env('MAIL_ENCRYPTION'), 'tls'),
|
||||
'username' => envDefaultWhenEmpty(env('MAIL_USERNAME'), 'user@example.com'),
|
||||
'password' => envDefaultWhenEmpty(env('MAIL_PASSWORD'), 'password'),
|
||||
'encryption' => env_default_when_empty(env('MAIL_ENCRYPTION'), 'tls'),
|
||||
'username' => env_default_when_empty(env('MAIL_USERNAME'), 'user@example.com'),
|
||||
'password' => env_default_when_empty(env('MAIL_PASSWORD'), 'password'),
|
||||
'timeout' => null,
|
||||
'scheme' => env('MAIL_SCHEME'),
|
||||
'url' => env('MAIL_URL'),
|
||||
@@ -73,7 +73,7 @@ return [
|
||||
|
||||
'sendmail' => [
|
||||
'transport' => 'sendmail',
|
||||
'path' => envDefaultWhenEmpty(env('MAIL_SENDMAIL_COMMAND'), '/usr/sbin/sendmail -bs'),
|
||||
'path' => env_default_when_empty(env('MAIL_SENDMAIL_COMMAND'), '/usr/sbin/sendmail -bs'),
|
||||
],
|
||||
'log' => [
|
||||
'transport' => 'log',
|
||||
@@ -91,7 +91,7 @@ return [
|
||||
],
|
||||
],
|
||||
|
||||
'from' => ['address' => envDefaultWhenEmpty(env('MAIL_FROM'), 'changeme@example.com'), 'name' => 'Firefly III Mailer'],
|
||||
'from' => ['address' => env_default_when_empty(env('MAIL_FROM'), 'changeme@example.com'), 'name' => 'Firefly III Mailer'],
|
||||
'markdown' => [
|
||||
'theme' => 'default',
|
||||
|
||||
|
||||
@@ -15,7 +15,7 @@ return [
|
||||
|
|
||||
*/
|
||||
|
||||
'guard' => envDefaultWhenEmpty(env('AUTHENTICATION_GUARD'), 'web'),
|
||||
'guard' => env_default_when_empty(env('AUTHENTICATION_GUARD'), 'web'),
|
||||
|
||||
/*
|
||||
|--------------------------------------------------------------------------
|
||||
|
||||
398
package-lock.json
generated
398
package-lock.json
generated
@@ -32,9 +32,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@babel/compat-data": {
|
||||
"version": "7.29.0",
|
||||
"resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.29.0.tgz",
|
||||
"integrity": "sha512-T1NCJqT/j9+cn8fvkt7jtwbLBfLC/1y1c7NtCeXFRgzGTsafi68MRv8yzkYSapBnFA6L3U2VSc02ciDzoAJhJg==",
|
||||
"version": "7.29.3",
|
||||
"resolved": "https://registry.npmjs.org/@babel/compat-data/-/compat-data-7.29.3.tgz",
|
||||
"integrity": "sha512-LIVqM46zQWZhj17qA8wb4nW/ixr2y1Nw+r1etiAWgRM6U1IqP+LNhL1yg440jYZR72jCWcWbLWzIosH+uP1fqg==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
@@ -140,9 +140,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@babel/helper-create-class-features-plugin": {
|
||||
"version": "7.28.6",
|
||||
"resolved": "https://registry.npmjs.org/@babel/helper-create-class-features-plugin/-/helper-create-class-features-plugin-7.28.6.tgz",
|
||||
"integrity": "sha512-dTOdvsjnG3xNT9Y0AUg1wAl38y+4Rl4sf9caSQZOXdNqVn+H+HbbJ4IyyHaIqNR6SW9oJpA/RuRjsjCw2IdIow==",
|
||||
"version": "7.29.3",
|
||||
"resolved": "https://registry.npmjs.org/@babel/helper-create-class-features-plugin/-/helper-create-class-features-plugin-7.29.3.tgz",
|
||||
"integrity": "sha512-RpLYy2sb51oNLjuu1iD3bwBqCBWUzjO0ocp+iaCP/lJtb2CPLcnC2Fftw+4sAzaMELGeWTgExSKADbdo0GFVzA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@@ -151,7 +151,7 @@
|
||||
"@babel/helper-optimise-call-expression": "^7.27.1",
|
||||
"@babel/helper-replace-supers": "^7.28.6",
|
||||
"@babel/helper-skip-transparent-expression-wrappers": "^7.27.1",
|
||||
"@babel/traverse": "^7.28.6",
|
||||
"@babel/traverse": "^7.29.0",
|
||||
"semver": "^6.3.1"
|
||||
},
|
||||
"engines": {
|
||||
@@ -405,9 +405,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@babel/parser": {
|
||||
"version": "7.29.2",
|
||||
"resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.29.2.tgz",
|
||||
"integrity": "sha512-4GgRzy/+fsBa72/RZVJmGKPmZu9Byn8o4MoLpmNe1m8ZfYnz5emHLQz3U4gLud6Zwl0RZIcgiLD7Uq7ySFuDLA==",
|
||||
"version": "7.29.3",
|
||||
"resolved": "https://registry.npmjs.org/@babel/parser/-/parser-7.29.3.tgz",
|
||||
"integrity": "sha512-b3ctpQwp+PROvU/cttc4OYl4MzfJUWy6FZg+PMXfzmt/+39iHVF0sDfqay8TQM3JA2EUOyKcFZt75jWriQijsA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@@ -469,6 +469,23 @@
|
||||
"@babel/core": "^7.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@babel/plugin-bugfix-safari-rest-destructuring-rhs-array": {
|
||||
"version": "7.29.3",
|
||||
"resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-safari-rest-destructuring-rhs-array/-/plugin-bugfix-safari-rest-destructuring-rhs-array-7.29.3.tgz",
|
||||
"integrity": "sha512-SRS46DFR4HqzUzCVgi90/xMoL+zeBDBvWdKYXSEzh79kXswNFEglUpMKxR04//dPqwYXWUBJ3mpUd933ru9Kmg==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"@babel/helper-plugin-utils": "^7.28.6",
|
||||
"@babel/helper-skip-transparent-expression-wrappers": "^7.27.1"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=6.9.0"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"@babel/core": "^7.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": {
|
||||
"version": "7.27.1",
|
||||
"resolved": "https://registry.npmjs.org/@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining/-/plugin-bugfix-v8-spread-parameters-in-optional-chaining-7.27.1.tgz",
|
||||
@@ -1501,19 +1518,20 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@babel/preset-env": {
|
||||
"version": "7.29.2",
|
||||
"resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.29.2.tgz",
|
||||
"integrity": "sha512-DYD23veRYGvBFhcTY1iUvJnDNpuqNd/BzBwCvzOTKUnJjKg5kpUBh3/u9585Agdkgj+QuygG7jLfOPWMa2KVNw==",
|
||||
"version": "7.29.3",
|
||||
"resolved": "https://registry.npmjs.org/@babel/preset-env/-/preset-env-7.29.3.tgz",
|
||||
"integrity": "sha512-ySZypNLAIH1ClygLDQzVMoGQRViATnkHkYYV6TcNDz+8+jwZCdsguGvsb3EY5d9wyWyhmF1iSuFM0Yh5XPnqSA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"@babel/compat-data": "^7.29.0",
|
||||
"@babel/compat-data": "^7.29.3",
|
||||
"@babel/helper-compilation-targets": "^7.28.6",
|
||||
"@babel/helper-plugin-utils": "^7.28.6",
|
||||
"@babel/helper-validator-option": "^7.27.1",
|
||||
"@babel/plugin-bugfix-firefox-class-in-computed-class-key": "^7.28.5",
|
||||
"@babel/plugin-bugfix-safari-class-field-initializer-scope": "^7.27.1",
|
||||
"@babel/plugin-bugfix-safari-id-destructuring-collision-in-function-expression": "^7.27.1",
|
||||
"@babel/plugin-bugfix-safari-rest-destructuring-rhs-array": "^7.29.3",
|
||||
"@babel/plugin-bugfix-v8-spread-parameters-in-optional-chaining": "^7.27.1",
|
||||
"@babel/plugin-bugfix-v8-static-class-fields-redefine-readonly": "^7.28.6",
|
||||
"@babel/plugin-proposal-private-property-in-object": "7.21.0-placeholder-for-preset-env.2",
|
||||
@@ -1703,9 +1721,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@emnapi/core": {
|
||||
"version": "1.9.2",
|
||||
"resolved": "https://registry.npmjs.org/@emnapi/core/-/core-1.9.2.tgz",
|
||||
"integrity": "sha512-UC+ZhH3XtczQYfOlu3lNEkdW/p4dsJ1r/bP7H8+rhao3TTTMO1ATq/4DdIi23XuGoFY+Cz0JmCbdVl0hz9jZcA==",
|
||||
"version": "1.10.0",
|
||||
"resolved": "https://registry.npmjs.org/@emnapi/core/-/core-1.10.0.tgz",
|
||||
"integrity": "sha512-yq6OkJ4p82CAfPl0u9mQebQHKPJkY7WrIuk205cTYnYe+k2Z8YBh11FrbRG/H6ihirqcacOgl2BIO8oyMQLeXw==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
@@ -1715,9 +1733,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@emnapi/runtime": {
|
||||
"version": "1.9.2",
|
||||
"resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.9.2.tgz",
|
||||
"integrity": "sha512-3U4+MIWHImeyu1wnmVygh5WlgfYDtyf0k8AbLhMFxOipihf6nrWC4syIm/SwEeec0mNSafiiNnMJwbza/Is6Lw==",
|
||||
"version": "1.10.0",
|
||||
"resolved": "https://registry.npmjs.org/@emnapi/runtime/-/runtime-1.10.0.tgz",
|
||||
"integrity": "sha512-ewvYlk86xUoGI0zQRNq/mC+16R1QeDlKQy21Ki3oSYXNgLb45GV1P6A0M+/s6nyCuNDqe5VpaY84BzXGwVbwFA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
@@ -1897,9 +1915,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@oxc-project/types": {
|
||||
"version": "0.124.0",
|
||||
"resolved": "https://registry.npmjs.org/@oxc-project/types/-/types-0.124.0.tgz",
|
||||
"integrity": "sha512-VBFWMTBvHxS11Z5Lvlr3IWgrwhMTXV+Md+EQF0Xf60+wAdsGFTBx7X7K/hP4pi8N7dcm1RvcHwDxZ16Qx8keUg==",
|
||||
"version": "0.127.0",
|
||||
"resolved": "https://registry.npmjs.org/@oxc-project/types/-/types-0.127.0.tgz",
|
||||
"integrity": "sha512-aIYXQBo4lCbO4z0R3FHeucQHpF46l2LbMdxRvqvuRuW2OxdnSkcng5B8+K12spgLDj93rtN3+J2Vac/TIO+ciQ==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"funding": {
|
||||
@@ -2241,9 +2259,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-android-arm64": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-android-arm64/-/binding-android-arm64-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-YYe6aWruPZDtHNpwu7+qAHEMbQ/yRl6atqb/AhznLTnD3UY99Q1jE7ihLSahNWkF4EqRPVC4SiR4O0UkLK02tA==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-android-arm64/-/binding-android-arm64-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-s70pVGhw4zqGeFnXWvAzJDlvxhlRollagdCCKRgOsgUOH3N1l0LIxf83AtGzmb5SiVM4Hjl5HyarMRfdfj3DaQ==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@@ -2258,9 +2276,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-darwin-arm64": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-darwin-arm64/-/binding-darwin-arm64-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-oArR/ig8wNTPYsXL+Mzhs0oxhxfuHRfG7Ikw7jXsw8mYOtk71W0OkF2VEVh699pdmzjPQsTjlD1JIOoHkLP1Fg==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-darwin-arm64/-/binding-darwin-arm64-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-4ksWc9n0mhlZpZ9PMZgTGjeOPRu8MB1Z3Tz0Mo02eWfWCHMW1zN82Qz/pL/rC+yQa+8ZnutMF0JjJe7PjwasYw==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@@ -2275,9 +2293,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-darwin-x64": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-darwin-x64/-/binding-darwin-x64-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-YzeVqOqjPYvUbJSWJ4EDL8ahbmsIXQpgL3JVipmN+MX0XnXMeWomLN3Fb+nwCmP/jfyqte5I3XRSm7OfQrbyxw==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-darwin-x64/-/binding-darwin-x64-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-SUSDOI6WwUVNcWxd02QEBjLdY1VPHvlEkw6T/8nYG322iYWCTxRb1vzk4E+mWWYehTp7ERibq54LSJGjmouOsw==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
@@ -2292,9 +2310,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-freebsd-x64": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-freebsd-x64/-/binding-freebsd-x64-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-9Erhx956jeQ0nNTyif1+QWAXDRD38ZNjr//bSHrt6wDwB+QkAfl2q6Mn1k6OBPerznjRmbM10lgRb1Pli4xZPw==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-freebsd-x64/-/binding-freebsd-x64-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-hwnz3nw9dbJ05EDO/PvcjaaewqqDy7Y1rn1UO81l8iIK1GjenME75dl16ajbvSSMfv66WXSRCYKIqfgq2KCfxw==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
@@ -2309,9 +2327,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-linux-arm-gnueabihf": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm-gnueabihf/-/binding-linux-arm-gnueabihf-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-cVwk0w8QbZJGTnP/AHQBs5yNwmpgGYStL88t4UIaqcvYJWBfS0s3oqVLZPwsPU6M0zlW4GqjP0Zq5MnAGwFeGA==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm-gnueabihf/-/binding-linux-arm-gnueabihf-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-IS+W7epTcwANmFSQFrS1SivEXHtl1JtuQA9wlxrZTcNi6mx+FDOYrakGevvvTwgj2JvWiK8B29/qD9BELZPyXQ==",
|
||||
"cpu": [
|
||||
"arm"
|
||||
],
|
||||
@@ -2326,9 +2344,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-linux-arm64-gnu": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm64-gnu/-/binding-linux-arm64-gnu-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-eBZ/u8iAK9SoHGanqe/jrPnY0JvBN6iXbVOsbO38mbz+ZJsaobExAm1Iu+rxa4S1l2FjG0qEZn4Rc6X8n+9M+w==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm64-gnu/-/binding-linux-arm64-gnu-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-e6usGaHKW5BMNZOymS1UcEYGowQMWcgZ71Z17Sl/h2+ZziNJ1a9n3Zvcz6LdRyIW5572wBCTH/Z+bKuZouGk9Q==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@@ -2343,9 +2361,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-linux-arm64-musl": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm64-musl/-/binding-linux-arm64-musl-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-ZvRYMGrAklV9PEkgt4LQM6MjQX2P58HPAuecwYObY2DhS2t35R0I810bKi0wmaYORt6m/2Sm+Z+nFgb0WhXNcQ==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-arm64-musl/-/binding-linux-arm64-musl-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-b/CgbwAJpmrRLp02RPfhbudf5tZnN9nsPWK82znefso832etkem8H7FSZwxrOI9djcdTP7U6YfNhbRnh7djErg==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@@ -2360,9 +2378,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-linux-ppc64-gnu": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-ppc64-gnu/-/binding-linux-ppc64-gnu-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-VDpgGBzgfg5hLg+uBpCLoFG5kVvEyafmfxGUV0UHLcL5irxAK7PKNeC2MwClgk6ZAiNhmo9FLhRYgvMmedLtnQ==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-ppc64-gnu/-/binding-linux-ppc64-gnu-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-4EII1iNGRUN5WwGbF/kOh/EIkoDN9HsupgLQoXfY+D1oyJm7/F4t5PYU5n8SWZgG0FEwakyM8pGgwcBYruGTlA==",
|
||||
"cpu": [
|
||||
"ppc64"
|
||||
],
|
||||
@@ -2377,9 +2395,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-linux-s390x-gnu": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-s390x-gnu/-/binding-linux-s390x-gnu-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-y1uXY3qQWCzcPgRJATPSOUP4tCemh4uBdY7e3EZbVwCJTY3gLJWnQABgeUetvED+bt1FQ01OeZwvhLS2bpNrAQ==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-s390x-gnu/-/binding-linux-s390x-gnu-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-AH8oq3XqQo4IibpVXvPeLDI5pzkpYn0WiZAfT05kFzoJ6tQNzwRdDYQ45M8I/gslbodRZwW8uxLhbSBbkv96rA==",
|
||||
"cpu": [
|
||||
"s390x"
|
||||
],
|
||||
@@ -2394,9 +2412,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-linux-x64-gnu": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-x64-gnu/-/binding-linux-x64-gnu-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-023bTPBod7J3Y/4fzAN6QtpkSABR0rigtrwaP+qSEabUh5zf6ELr9Nc7GujaROuPY3uwdSIXWrvhn1KxOvurWA==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-x64-gnu/-/binding-linux-x64-gnu-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-cLnjV3xfo7KslbU41Z7z8BH/E1y5mzUYzAqih1d1MDaIGZRCMqTijqLv76/P7fyHuvUcfGsIpqCdddbxLLK9rA==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
@@ -2411,9 +2429,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-linux-x64-musl": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-x64-musl/-/binding-linux-x64-musl-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-witB2O0/hU4CgfOOKUoeFgQ4GktPi1eEbAhaLAIpgD6+ZnhcPkUtPsoKKHRzmOoWPZue46IThdSgdo4XneOLYw==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-linux-x64-musl/-/binding-linux-x64-musl-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-0phclDw1spsL7dUB37sIARuis2tAgomCJXAHZlpt8PXZ4Ba0dRP1e+66lsRqrfhISeN9bEGNjQs+T/Fbd7oYGw==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
@@ -2428,9 +2446,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-openharmony-arm64": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-openharmony-arm64/-/binding-openharmony-arm64-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-UCL68NJ0Ud5zRipXZE9dF5PmirzJE4E4BCIOOssEnM7wLDsxjc6Qb0sGDxTNRTP53I6MZpygyCpY8Aa8sPfKPg==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-openharmony-arm64/-/binding-openharmony-arm64-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-0ag/hEgXOwgw4t8QyQvUCxvEg+V0KBcA6YuOx9g0r02MprutRF5dyljgm3EmR02O292UX7UeS6HzWHAl6KgyhA==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@@ -2445,9 +2463,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-wasm32-wasi": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-wasm32-wasi/-/binding-wasm32-wasi-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-ApLruZq/ig+nhaE7OJm4lDjayUnOHVUa77zGeqnqZ9pn0ovdVbbNPerVibLXDmWeUZXjIYIT8V3xkT58Rm9u5Q==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-wasm32-wasi/-/binding-wasm32-wasi-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-LEXei6vo0E5wTGwpkJ4KoT3OZJRnglwldt5ziLzOlc6qqb55z4tWNq2A+PFqCJuvWWdP53CVhG1Z9NtToDPJrA==",
|
||||
"cpu": [
|
||||
"wasm32"
|
||||
],
|
||||
@@ -2455,18 +2473,18 @@
|
||||
"license": "MIT",
|
||||
"optional": true,
|
||||
"dependencies": {
|
||||
"@emnapi/core": "1.9.2",
|
||||
"@emnapi/runtime": "1.9.2",
|
||||
"@napi-rs/wasm-runtime": "^1.1.3"
|
||||
"@emnapi/core": "1.10.0",
|
||||
"@emnapi/runtime": "1.10.0",
|
||||
"@napi-rs/wasm-runtime": "^1.1.4"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=14.0.0"
|
||||
"node": "^20.19.0 || >=22.12.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-win32-arm64-msvc": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-win32-arm64-msvc/-/binding-win32-arm64-msvc-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-KmoUoU7HnN+Si5YWJigfTws1jz1bKBYDQKdbLspz0UaqjjFkddHsqorgiW1mxcAj88lYUE6NC/zJNwT+SloqtA==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-win32-arm64-msvc/-/binding-win32-arm64-msvc-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-gUmyzBl3SPMa6hrqFUth9sVfcLBlYsbMzBx5PlexMroZStgzGqlZ26pYG89rBb45Mnia+oil6YAIFeEWGWhoZA==",
|
||||
"cpu": [
|
||||
"arm64"
|
||||
],
|
||||
@@ -2481,9 +2499,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/binding-win32-x64-msvc": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-win32-x64-msvc/-/binding-win32-x64-msvc-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-3P2A8L+x75qavWLe/Dll3EYBJLQmtkJN8rfh+U/eR3MqMgL/h98PhYI+JFfXuDPgPeCB7iZAKiqii5vqOvnA0g==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/binding-win32-x64-msvc/-/binding-win32-x64-msvc-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-3hkiolcUAvPB9FLb3UZdfjVVNWherN1f/skkGWJP/fgSQhYUZpSIRr0/I8ZK9TkF3F7kxvJAk0+IcKvPHk9qQg==",
|
||||
"cpu": [
|
||||
"x64"
|
||||
],
|
||||
@@ -2498,9 +2516,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/@rolldown/pluginutils": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/pluginutils/-/pluginutils-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-UromN0peaE53IaBRe9W7CjrZgXl90fqGpK+mIZbA3qSTeYqg3pqpROBdIPvOG3F5ereDHNwoHBI2e50n1BDr1g==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/@rolldown/pluginutils/-/pluginutils-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-n8iosDOt6Ig1UhJ2AYqoIhHWh/isz0xpicHTzpKBeotdVsTEcxsSA/i3EVM7gQAj0rU27OLAxCjzlj15IWY7bg==",
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
@@ -3315,9 +3333,9 @@
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/ajv": {
|
||||
"version": "6.14.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-6.14.0.tgz",
|
||||
"integrity": "sha512-IWrosm/yrn43eiKqkfkHis7QioDleaXQHdDVPKg0FSwwd/DuvyX79TZnFOnYpB7dcsFAMmtFztZuXPDvSePkFw==",
|
||||
"version": "6.15.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-6.15.0.tgz",
|
||||
"integrity": "sha512-fgFx7Hfoq60ytK2c7DhnF8jIvzYgOMxfugjLOSMHjLIPgenqa7S7oaagATUq99mV6IYvN2tRmC0wnTYX6iPbMw==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@@ -3350,9 +3368,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/ajv-formats/node_modules/ajv": {
|
||||
"version": "8.18.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-8.18.0.tgz",
|
||||
"integrity": "sha512-PlXPeEWMXMZ7sPYOHqmDyCJzcfNrUr3fGNKtezX14ykXOEIvyK81d+qydx89KY5O71FKMPaQ2vBfBFI5NHR63A==",
|
||||
"version": "8.20.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-8.20.0.tgz",
|
||||
"integrity": "sha512-Thbli+OlOj+iMPYFBVBfJ3OmCAnaSyNn4M1vz9T6Gka5Jt9ba/HIR56joy65tY6kx/FCF5VXNB819Y7/GUrBGA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@@ -3384,9 +3402,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/alpinejs": {
|
||||
"version": "3.15.11",
|
||||
"resolved": "https://registry.npmjs.org/alpinejs/-/alpinejs-3.15.11.tgz",
|
||||
"integrity": "sha512-m26gkTg/MId8O+F4jHKK3vB3SjbFxxk/JHP+qzmw1H6aQrZuPAg4CUoAefnASzzp/eNroBjrRQe7950bNeaBJw==",
|
||||
"version": "3.15.12",
|
||||
"resolved": "https://registry.npmjs.org/alpinejs/-/alpinejs-3.15.12.tgz",
|
||||
"integrity": "sha512-nJvPAQVNPdZZ0NrExJ/kzQco3ijR8LwvCOadQecllESiqT4NyZ/57sN9V2XyvhlBGAbmlKYgeWZvYdKq99ij/Q==",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"@vue/reactivity": "~3.1.1"
|
||||
@@ -3569,13 +3587,13 @@
|
||||
}
|
||||
},
|
||||
"node_modules/axios": {
|
||||
"version": "1.15.2",
|
||||
"resolved": "https://registry.npmjs.org/axios/-/axios-1.15.2.tgz",
|
||||
"integrity": "sha512-wLrXxPtcrPTsNlJmKjkPnNPK2Ihe0hn0wGSaTEiHRPxwjvJwT3hKmXF4dpqxmPO9SoNb2FsYXj/xEo0gHN+D5A==",
|
||||
"version": "1.16.0",
|
||||
"resolved": "https://registry.npmjs.org/axios/-/axios-1.16.0.tgz",
|
||||
"integrity": "sha512-6hp5CwvTPlN2A31g5dxnwAX0orzM7pmCRDLnZSX772mv8WDqICwFjowHuPs04Mc8deIld1+ejhtaMn5vp6b+1w==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"follow-redirects": "^1.15.11",
|
||||
"follow-redirects": "^1.16.0",
|
||||
"form-data": "^4.0.5",
|
||||
"proxy-from-env": "^2.1.0"
|
||||
}
|
||||
@@ -3681,9 +3699,9 @@
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/baseline-browser-mapping": {
|
||||
"version": "2.10.21",
|
||||
"resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.10.21.tgz",
|
||||
"integrity": "sha512-Q+rUQ7Uz8AHM7DEaNdwvfFCTq7a43lNTzuS94eiWqwyxfV/wJv+oUivef51T91mmRY4d4A1u9rcSvkeufCVXlA==",
|
||||
"version": "2.10.25",
|
||||
"resolved": "https://registry.npmjs.org/baseline-browser-mapping/-/baseline-browser-mapping-2.10.25.tgz",
|
||||
"integrity": "sha512-QO/VHsXCQdnzADMfmkeOPvHdIAkoB7i0/rGjINPJEetLx75hNttVWGQ/jycHUDP9zZ9rupbm60WRxcwViB0MiA==",
|
||||
"dev": true,
|
||||
"license": "Apache-2.0",
|
||||
"bin": {
|
||||
@@ -3738,9 +3756,9 @@
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/body-parser": {
|
||||
"version": "1.20.4",
|
||||
"resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.20.4.tgz",
|
||||
"integrity": "sha512-ZTgYYLMOXY9qKU/57FAo8F+HA2dGX7bqGc71txDRC1rS4frdFI5R7NhluHxH6M0YItAP0sHB4uqAOcYKxO6uGA==",
|
||||
"version": "1.20.5",
|
||||
"resolved": "https://registry.npmjs.org/body-parser/-/body-parser-1.20.5.tgz",
|
||||
"integrity": "sha512-3grm+/2tUOvu2cjJkvsIxrv/wVpfXQW4PsQHYm7yk4vfpu7Ekl6nEsYBoJUL6qDwZUx8wUhQ8tR2qz+ad9c9OA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@@ -3752,7 +3770,7 @@
|
||||
"http-errors": "~2.0.1",
|
||||
"iconv-lite": "~0.4.24",
|
||||
"on-finished": "~2.4.1",
|
||||
"qs": "~6.14.0",
|
||||
"qs": "~6.15.1",
|
||||
"raw-body": "~2.5.3",
|
||||
"type-is": "~1.6.18",
|
||||
"unpipe": "~1.0.0"
|
||||
@@ -3779,22 +3797,6 @@
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/body-parser/node_modules/qs": {
|
||||
"version": "6.14.2",
|
||||
"resolved": "https://registry.npmjs.org/qs/-/qs-6.14.2.tgz",
|
||||
"integrity": "sha512-V/yCWTTF7VJ9hIh18Ugr2zhJMP01MY7c5kh4J870L7imm6/DIzBsNLTXzMwUA3yZ5b/KBqLx8Kp3uRvd7xSe3Q==",
|
||||
"dev": true,
|
||||
"license": "BSD-3-Clause",
|
||||
"dependencies": {
|
||||
"side-channel": "^1.1.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=0.6"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/sponsors/ljharb"
|
||||
}
|
||||
},
|
||||
"node_modules/bonjour-service": {
|
||||
"version": "1.3.0",
|
||||
"resolved": "https://registry.npmjs.org/bonjour-service/-/bonjour-service-1.3.0.tgz",
|
||||
@@ -4133,9 +4135,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/caniuse-lite": {
|
||||
"version": "1.0.30001790",
|
||||
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001790.tgz",
|
||||
"integrity": "sha512-bOoxfJPyYo+ds6W0YfptaCWbFnJYjh2Y1Eow5lRv+vI2u8ganPZqNm1JwNh0t2ELQCqIWg4B3dWEusgAmsoyOw==",
|
||||
"version": "1.0.30001791",
|
||||
"resolved": "https://registry.npmjs.org/caniuse-lite/-/caniuse-lite-1.0.30001791.tgz",
|
||||
"integrity": "sha512-yk0l/YSrOnFZk3UROpDLQD9+kC1l4meK/wed583AXrzoarMGJcbRi2Q4RaUYbKxYAsZ8sWmaSa/DsLmdBeI1vQ==",
|
||||
"dev": true,
|
||||
"funding": [
|
||||
{
|
||||
@@ -5337,9 +5339,9 @@
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/electron-to-chromium": {
|
||||
"version": "1.5.343",
|
||||
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.343.tgz",
|
||||
"integrity": "sha512-YHnQ3MXI08icvL9ZKnEBy05F2EQ8ob01UaMOuMbM8l+4UcAq6MPPbBTJBbsBUg3H8JeZNt+O4fjsoWth3p6IFg==",
|
||||
"version": "1.5.349",
|
||||
"resolved": "https://registry.npmjs.org/electron-to-chromium/-/electron-to-chromium-1.5.349.tgz",
|
||||
"integrity": "sha512-QsWVGyRuY07Aqb234QytTfwd5d9AJlfNIQ5wIOl1L+PZDzI9d9+Fn0FRale/QYlFxt/bUnB0/nLd1jFPGxGK1A==",
|
||||
"dev": true,
|
||||
"license": "ISC"
|
||||
},
|
||||
@@ -5394,14 +5396,14 @@
|
||||
}
|
||||
},
|
||||
"node_modules/enhanced-resolve": {
|
||||
"version": "5.20.1",
|
||||
"resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.20.1.tgz",
|
||||
"integrity": "sha512-Qohcme7V1inbAfvjItgw0EaxVX5q2rdVEZHRBrEQdRZTssLDGsL8Lwrznl8oQ/6kuTJONLaDcGjkNP247XEhcA==",
|
||||
"version": "5.21.0",
|
||||
"resolved": "https://registry.npmjs.org/enhanced-resolve/-/enhanced-resolve-5.21.0.tgz",
|
||||
"integrity": "sha512-otxSQPw4lkOZWkHpB3zaEQs6gWYEsmX4xQF68ElXC/TWvGxGMSGOvoNbaLXm6/cS/fSfHtsEdw90y20PCd+sCA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"graceful-fs": "^4.2.4",
|
||||
"tapable": "^2.3.0"
|
||||
"tapable": "^2.3.3"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=10.13.0"
|
||||
@@ -5462,9 +5464,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/es-module-lexer": {
|
||||
"version": "2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-2.0.0.tgz",
|
||||
"integrity": "sha512-5POEcUuZybH7IdmGsD8wlf0AI55wMecM9rVBTI/qEAy2c1kTOm3DjFYjrBdI2K3BaJjJYfYFeRtM0t9ssnRuxw==",
|
||||
"version": "2.1.0",
|
||||
"resolved": "https://registry.npmjs.org/es-module-lexer/-/es-module-lexer-2.1.0.tgz",
|
||||
"integrity": "sha512-n27zTYMjYu1aj4MjCWzSP7G9r75utsaoc8m61weK+W8JMBGGQybd43GstCXZ3WNmSFtGT9wi59qQTW6mhTR5LQ==",
|
||||
"dev": true,
|
||||
"license": "MIT"
|
||||
},
|
||||
@@ -6646,9 +6648,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/i18next": {
|
||||
"version": "26.0.6",
|
||||
"resolved": "https://registry.npmjs.org/i18next/-/i18next-26.0.6.tgz",
|
||||
"integrity": "sha512-A4U6eCXodIbrhf8EarRurB9/4ebyaurH4+fu4gig9bqxmpSt+fCAFm/GpRQDcN1Xzu/LdFCx4nYHsnM1edIIbg==",
|
||||
"version": "26.0.8",
|
||||
"resolved": "https://registry.npmjs.org/i18next/-/i18next-26.0.8.tgz",
|
||||
"integrity": "sha512-BRzLom0mhDhV9v0QhgUUHWQJuwFmnr1194xEcNLYD6ym8y8s542n4jXUvRLnhNTbh9PmpU6kGZamyuGHQMsGjw==",
|
||||
"funding": [
|
||||
{
|
||||
"type": "individual",
|
||||
@@ -6664,9 +6666,6 @@
|
||||
}
|
||||
],
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"@babel/runtime": "^7.29.2"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"typescript": "^5 || ^6"
|
||||
},
|
||||
@@ -6686,9 +6685,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/i18next-http-backend": {
|
||||
"version": "3.0.5",
|
||||
"resolved": "https://registry.npmjs.org/i18next-http-backend/-/i18next-http-backend-3.0.5.tgz",
|
||||
"integrity": "sha512-QaWHnsxieEDcqKe+vo/RFqpiIFRi/KBqlOSPcUlvinBaISCeiTRCbtrazHAjtHtsLC66oDsROAH8frWkQzfMMQ==",
|
||||
"version": "3.0.6",
|
||||
"resolved": "https://registry.npmjs.org/i18next-http-backend/-/i18next-http-backend-3.0.6.tgz",
|
||||
"integrity": "sha512-mBOqy8993jtqAoj6XaI1XeC/8/9v6EPS+681ziegrPvTB0DoaCY7PpTS0SpY56qLMoS4OI1TZEM2Zf59zNh05w==",
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"cross-fetch": "4.1.0"
|
||||
@@ -7396,9 +7395,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/laravel-vite-plugin": {
|
||||
"version": "3.0.1",
|
||||
"resolved": "https://registry.npmjs.org/laravel-vite-plugin/-/laravel-vite-plugin-3.0.1.tgz",
|
||||
"integrity": "sha512-Bx8sVcLIaZT1d0eisABcmjQ1GZdJpaXcV66A8RhXGp9JgR3iL8jDnvakVDXuH87Tn5S9KNx3VOhmJZW1CSexOg==",
|
||||
"version": "3.1.0",
|
||||
"resolved": "https://registry.npmjs.org/laravel-vite-plugin/-/laravel-vite-plugin-3.1.0.tgz",
|
||||
"integrity": "sha512-Fzocl+X4eQ9jOi0RwdphYRGkUbPJ3ky1pTAST5Ot18cS2gw6d2vldK2eCrlKDVjtibCjCx5qptYDlA0373n7qg==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@@ -7413,7 +7412,13 @@
|
||||
"node": "^20.19.0 || >=22.12.0"
|
||||
},
|
||||
"peerDependencies": {
|
||||
"fontaine": "^0.5.0",
|
||||
"vite": "^8.0.0"
|
||||
},
|
||||
"peerDependenciesMeta": {
|
||||
"fontaine": {
|
||||
"optional": true
|
||||
}
|
||||
}
|
||||
},
|
||||
"node_modules/launch-editor": {
|
||||
@@ -7712,9 +7717,9 @@
|
||||
"license": "MIT"
|
||||
},
|
||||
"node_modules/loader-runner": {
|
||||
"version": "4.3.1",
|
||||
"resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.3.1.tgz",
|
||||
"integrity": "sha512-IWqP2SCPhyVFTBtRcgMHdzlf9ul25NwaFx4wCEH/KjAXuuHY4yNjvPXsBokp8jCB936PyWRaPKUNh8NvylLp2Q==",
|
||||
"version": "4.3.2",
|
||||
"resolved": "https://registry.npmjs.org/loader-runner/-/loader-runner-4.3.2.tgz",
|
||||
"integrity": "sha512-DFEqQ3ihfS9blba08cLfYf1NRAIEm+dDjic073DRDc3/JspI/8wYmtDsHwd3+4hwvdxSK7PGaElfTmm0awWJ4w==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
@@ -8126,9 +8131,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/nanoid": {
|
||||
"version": "3.3.11",
|
||||
"resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.11.tgz",
|
||||
"integrity": "sha512-N8SpfPUnUp1bK+PMYW8qSWdl9U+wwNWI4QKxOYDy9JAro3WMX7p2OeVRF9v+347pnakNevPmiHhNmZ2HbFA76w==",
|
||||
"version": "3.3.12",
|
||||
"resolved": "https://registry.npmjs.org/nanoid/-/nanoid-3.3.12.tgz",
|
||||
"integrity": "sha512-ZB9RH/39qpq5Vu6Y+NmUaFhQR6pp+M2Xt76XBnEwDaGcVAqhlvxrl3B2bKS5D3NH3QR76v3aSrKaF/Kiy7lEtQ==",
|
||||
"dev": true,
|
||||
"funding": [
|
||||
{
|
||||
@@ -8760,9 +8765,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/postcss": {
|
||||
"version": "8.5.10",
|
||||
"resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.10.tgz",
|
||||
"integrity": "sha512-pMMHxBOZKFU6HgAZ4eyGnwXF/EvPGGqUr0MnZ5+99485wwW41kW91A4LOGxSHhgugZmSChL5AlElNdwlNgcnLQ==",
|
||||
"version": "8.5.13",
|
||||
"resolved": "https://registry.npmjs.org/postcss/-/postcss-8.5.13.tgz",
|
||||
"integrity": "sha512-qif0+jGGZoLWdHey3UFHHWP0H7Gbmsk8T5VEqyYFbWqPr1XqvLGBbk/sl8V5exGmcYJklJOhOQq1pV9IcsiFag==",
|
||||
"dev": true,
|
||||
"funding": [
|
||||
{
|
||||
@@ -9897,14 +9902,14 @@
|
||||
}
|
||||
},
|
||||
"node_modules/rolldown": {
|
||||
"version": "1.0.0-rc.15",
|
||||
"resolved": "https://registry.npmjs.org/rolldown/-/rolldown-1.0.0-rc.15.tgz",
|
||||
"integrity": "sha512-Ff31guA5zT6WjnGp0SXw76X6hzGRk/OQq2hE+1lcDe+lJdHSgnSX6nK3erbONHyCbpSj9a9E+uX/OvytZoWp2g==",
|
||||
"version": "1.0.0-rc.17",
|
||||
"resolved": "https://registry.npmjs.org/rolldown/-/rolldown-1.0.0-rc.17.tgz",
|
||||
"integrity": "sha512-ZrT53oAKrtA4+YtBWPQbtPOxIbVDbxT0orcYERKd63VJTF13zPcgXTvD4843L8pcsI7M6MErt8QtON6lrB9tyA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"@oxc-project/types": "=0.124.0",
|
||||
"@rolldown/pluginutils": "1.0.0-rc.15"
|
||||
"@oxc-project/types": "=0.127.0",
|
||||
"@rolldown/pluginutils": "1.0.0-rc.17"
|
||||
},
|
||||
"bin": {
|
||||
"rolldown": "bin/cli.mjs"
|
||||
@@ -9913,21 +9918,21 @@
|
||||
"node": "^20.19.0 || >=22.12.0"
|
||||
},
|
||||
"optionalDependencies": {
|
||||
"@rolldown/binding-android-arm64": "1.0.0-rc.15",
|
||||
"@rolldown/binding-darwin-arm64": "1.0.0-rc.15",
|
||||
"@rolldown/binding-darwin-x64": "1.0.0-rc.15",
|
||||
"@rolldown/binding-freebsd-x64": "1.0.0-rc.15",
|
||||
"@rolldown/binding-linux-arm-gnueabihf": "1.0.0-rc.15",
|
||||
"@rolldown/binding-linux-arm64-gnu": "1.0.0-rc.15",
|
||||
"@rolldown/binding-linux-arm64-musl": "1.0.0-rc.15",
|
||||
"@rolldown/binding-linux-ppc64-gnu": "1.0.0-rc.15",
|
||||
"@rolldown/binding-linux-s390x-gnu": "1.0.0-rc.15",
|
||||
"@rolldown/binding-linux-x64-gnu": "1.0.0-rc.15",
|
||||
"@rolldown/binding-linux-x64-musl": "1.0.0-rc.15",
|
||||
"@rolldown/binding-openharmony-arm64": "1.0.0-rc.15",
|
||||
"@rolldown/binding-wasm32-wasi": "1.0.0-rc.15",
|
||||
"@rolldown/binding-win32-arm64-msvc": "1.0.0-rc.15",
|
||||
"@rolldown/binding-win32-x64-msvc": "1.0.0-rc.15"
|
||||
"@rolldown/binding-android-arm64": "1.0.0-rc.17",
|
||||
"@rolldown/binding-darwin-arm64": "1.0.0-rc.17",
|
||||
"@rolldown/binding-darwin-x64": "1.0.0-rc.17",
|
||||
"@rolldown/binding-freebsd-x64": "1.0.0-rc.17",
|
||||
"@rolldown/binding-linux-arm-gnueabihf": "1.0.0-rc.17",
|
||||
"@rolldown/binding-linux-arm64-gnu": "1.0.0-rc.17",
|
||||
"@rolldown/binding-linux-arm64-musl": "1.0.0-rc.17",
|
||||
"@rolldown/binding-linux-ppc64-gnu": "1.0.0-rc.17",
|
||||
"@rolldown/binding-linux-s390x-gnu": "1.0.0-rc.17",
|
||||
"@rolldown/binding-linux-x64-gnu": "1.0.0-rc.17",
|
||||
"@rolldown/binding-linux-x64-musl": "1.0.0-rc.17",
|
||||
"@rolldown/binding-openharmony-arm64": "1.0.0-rc.17",
|
||||
"@rolldown/binding-wasm32-wasi": "1.0.0-rc.17",
|
||||
"@rolldown/binding-win32-arm64-msvc": "1.0.0-rc.17",
|
||||
"@rolldown/binding-win32-x64-msvc": "1.0.0-rc.17"
|
||||
}
|
||||
},
|
||||
"node_modules/run-parallel": {
|
||||
@@ -10762,9 +10767,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/terser": {
|
||||
"version": "5.46.1",
|
||||
"resolved": "https://registry.npmjs.org/terser/-/terser-5.46.1.tgz",
|
||||
"integrity": "sha512-vzCjQO/rgUuK9sf8VJZvjqiqiHFaZLnOiimmUuOKODxWL8mm/xua7viT7aqX7dgPY60otQjUotzFMmCB4VdmqQ==",
|
||||
"version": "5.46.2",
|
||||
"resolved": "https://registry.npmjs.org/terser/-/terser-5.46.2.tgz",
|
||||
"integrity": "sha512-uxfo9fPcSgLDYob/w1FuL0c99MWiJDnv+5qXSQc5+Ki5NjVNsYi66INnMFBjf6uFz6OnX12piJQPF4IpjJTNTw==",
|
||||
"dev": true,
|
||||
"license": "BSD-2-Clause",
|
||||
"dependencies": {
|
||||
@@ -10781,9 +10786,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/terser-webpack-plugin": {
|
||||
"version": "5.4.0",
|
||||
"resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.4.0.tgz",
|
||||
"integrity": "sha512-Bn5vxm48flOIfkdl5CaD2+1CiUVbonWQ3KQPyP7/EuIl9Gbzq/gQFOzaMFUEgVjB1396tcK0SG8XcNJ/2kDH8g==",
|
||||
"version": "5.5.0",
|
||||
"resolved": "https://registry.npmjs.org/terser-webpack-plugin/-/terser-webpack-plugin-5.5.0.tgz",
|
||||
"integrity": "sha512-UYhptBwhWvfIjKd/UuFo6D8uq9xpGLDK+z8EDsj/zWhrTaH34cKEbrkMKfV5YWqGBvAYA3tlzZbs2R+qYrbQJA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@@ -10815,9 +10820,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/terser-webpack-plugin/node_modules/ajv": {
|
||||
"version": "8.18.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-8.18.0.tgz",
|
||||
"integrity": "sha512-PlXPeEWMXMZ7sPYOHqmDyCJzcfNrUr3fGNKtezX14ykXOEIvyK81d+qydx89KY5O71FKMPaQ2vBfBFI5NHR63A==",
|
||||
"version": "8.20.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-8.20.0.tgz",
|
||||
"integrity": "sha512-Thbli+OlOj+iMPYFBVBfJ3OmCAnaSyNn4M1vz9T6Gka5Jt9ba/HIR56joy65tY6kx/FCF5VXNB819Y7/GUrBGA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@@ -11235,6 +11240,7 @@
|
||||
"version": "8.3.2",
|
||||
"resolved": "https://registry.npmjs.org/uuid/-/uuid-8.3.2.tgz",
|
||||
"integrity": "sha512-+NYs2QeMWy+GWFOEm9xnn6HCDp0l7QBD7ml8zLUmJ+93Q5NF0NocErnwkTkXVFNiX3/fpC6afS8Dhb/gz7R7eg==",
|
||||
"deprecated": "uuid@10 and below is no longer supported. For ESM codebases, update to uuid@latest. For CommonJS codebases, use uuid@11 (but be aware this version will likely be deprecated in 2028).",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"bin": {
|
||||
@@ -11260,17 +11266,17 @@
|
||||
}
|
||||
},
|
||||
"node_modules/vite": {
|
||||
"version": "8.0.8",
|
||||
"resolved": "https://registry.npmjs.org/vite/-/vite-8.0.8.tgz",
|
||||
"integrity": "sha512-dbU7/iLVa8KZALJyLOBOQ88nOXtNG8vxKuOT4I2mD+Ya70KPceF4IAmDsmU0h1Qsn5bPrvsY9HJstCRh3hG6Uw==",
|
||||
"version": "8.0.10",
|
||||
"resolved": "https://registry.npmjs.org/vite/-/vite-8.0.10.tgz",
|
||||
"integrity": "sha512-rZuUu9j6J5uotLDs+cAA4O5H4K1SfPliUlQwqa6YEwSrWDZzP4rhm00oJR5snMewjxF5V/K3D4kctsUTsIU9Mw==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
"lightningcss": "^1.32.0",
|
||||
"picomatch": "^4.0.4",
|
||||
"postcss": "^8.5.8",
|
||||
"rolldown": "1.0.0-rc.15",
|
||||
"tinyglobby": "^0.2.15"
|
||||
"postcss": "^8.5.10",
|
||||
"rolldown": "1.0.0-rc.17",
|
||||
"tinyglobby": "^0.2.16"
|
||||
},
|
||||
"bin": {
|
||||
"vite": "bin/vite.js"
|
||||
@@ -11689,9 +11695,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/webpack-dev-middleware/node_modules/ajv": {
|
||||
"version": "8.18.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-8.18.0.tgz",
|
||||
"integrity": "sha512-PlXPeEWMXMZ7sPYOHqmDyCJzcfNrUr3fGNKtezX14ykXOEIvyK81d+qydx89KY5O71FKMPaQ2vBfBFI5NHR63A==",
|
||||
"version": "8.20.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-8.20.0.tgz",
|
||||
"integrity": "sha512-Thbli+OlOj+iMPYFBVBfJ3OmCAnaSyNn4M1vz9T6Gka5Jt9ba/HIR56joy65tY6kx/FCF5VXNB819Y7/GUrBGA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@@ -11806,9 +11812,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/webpack-dev-server/node_modules/ajv": {
|
||||
"version": "8.18.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-8.18.0.tgz",
|
||||
"integrity": "sha512-PlXPeEWMXMZ7sPYOHqmDyCJzcfNrUr3fGNKtezX14ykXOEIvyK81d+qydx89KY5O71FKMPaQ2vBfBFI5NHR63A==",
|
||||
"version": "8.20.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-8.20.0.tgz",
|
||||
"integrity": "sha512-Thbli+OlOj+iMPYFBVBfJ3OmCAnaSyNn4M1vz9T6Gka5Jt9ba/HIR56joy65tY6kx/FCF5VXNB819Y7/GUrBGA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@@ -11926,9 +11932,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/webpack/node_modules/ajv": {
|
||||
"version": "8.18.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-8.18.0.tgz",
|
||||
"integrity": "sha512-PlXPeEWMXMZ7sPYOHqmDyCJzcfNrUr3fGNKtezX14ykXOEIvyK81d+qydx89KY5O71FKMPaQ2vBfBFI5NHR63A==",
|
||||
"version": "8.20.0",
|
||||
"resolved": "https://registry.npmjs.org/ajv/-/ajv-8.20.0.tgz",
|
||||
"integrity": "sha512-Thbli+OlOj+iMPYFBVBfJ3OmCAnaSyNn4M1vz9T6Gka5Jt9ba/HIR56joy65tY6kx/FCF5VXNB819Y7/GUrBGA==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"dependencies": {
|
||||
@@ -11983,9 +11989,9 @@
|
||||
}
|
||||
},
|
||||
"node_modules/webpack/node_modules/webpack-sources": {
|
||||
"version": "3.3.4",
|
||||
"resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.3.4.tgz",
|
||||
"integrity": "sha512-7tP1PdV4vF+lYPnkMR0jMY5/la2ub5Fc/8VQrrU+lXkiM6C4TjVfGw7iKfyhnTQOsD+6Q/iKw0eFciziRgD58Q==",
|
||||
"version": "3.4.1",
|
||||
"resolved": "https://registry.npmjs.org/webpack-sources/-/webpack-sources-3.4.1.tgz",
|
||||
"integrity": "sha512-eACpxRN02yaawnt+uUNIF7Qje6A9zArxBbcAJjK1PK3S9Ycg5jIuJ8pW4q8EMnwNZCEGltcjkRx1QzOxOkKD8A==",
|
||||
"dev": true,
|
||||
"license": "MIT",
|
||||
"engines": {
|
||||
@@ -12165,9 +12171,9 @@
|
||||
"license": "ISC"
|
||||
},
|
||||
"node_modules/yaml": {
|
||||
"version": "2.8.3",
|
||||
"resolved": "https://registry.npmjs.org/yaml/-/yaml-2.8.3.tgz",
|
||||
"integrity": "sha512-AvbaCLOO2Otw/lW5bmh9d/WEdcDFdQp2Z2ZUH3pX9U2ihyUY0nvLv7J6TrWowklRGPYbB/IuIMfYgxaCPg5Bpg==",
|
||||
"version": "2.8.4",
|
||||
"resolved": "https://registry.npmjs.org/yaml/-/yaml-2.8.4.tgz",
|
||||
"integrity": "sha512-ml/JPOj9fOQK8RNnWojA67GbZ0ApXAUlN2UQclwv2eVgTgn7O9gg9o7paZWKMp4g0H3nTLtS9LVzhkpOFIKzog==",
|
||||
"license": "ISC",
|
||||
"bin": {
|
||||
"yaml": "bin.mjs"
|
||||
@@ -12257,7 +12263,7 @@
|
||||
"laravel-vite-plugin": "^3",
|
||||
"patch-package": "^8",
|
||||
"sass": "^1",
|
||||
"vite": "=8.0.8",
|
||||
"vite": "=8.0.10",
|
||||
"vite-plugin-manifest-sri": "^0.2.0"
|
||||
}
|
||||
}
|
||||
|
||||
2
public/v1/js/.gitignore
vendored
2
public/v1/js/.gitignore
vendored
@@ -1,3 +1,3 @@
|
||||
*.LICENSE.txt
|
||||
*.js
|
||||
#webhooks
|
||||
!ff/*/*.js
|
||||
|
||||
1
public/v1/js/ff/auth/.htaccess
Normal file
1
public/v1/js/ff/auth/.htaccess
Normal file
@@ -0,0 +1 @@
|
||||
Options -Indexes
|
||||
99
public/v1/js/ff/auth/register.js
Normal file
99
public/v1/js/ff/auth/register.js
Normal file
@@ -0,0 +1,99 @@
|
||||
/*
|
||||
* register.js
|
||||
* Copyright (c) 2026 james@firefly-iii.org
|
||||
*
|
||||
* This file is part of Firefly III (https://github.com/firefly-iii).
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
$(function () {
|
||||
"use strict";
|
||||
const form = document.querySelector('form[action="'+route+'"]');
|
||||
const errorBox = document.getElementById('client-errors');
|
||||
const errorList = document.getElementById('client-errors-list');
|
||||
const submitBtn = form.querySelector('button[type="submit"]');
|
||||
const originalBtnText = submitBtn.textContent;
|
||||
|
||||
function showErrors(errors) {
|
||||
errorList.innerHTML = errors.map(function(e) { return '<li>' + e + '</li>'; }).join('');
|
||||
errorBox.style.display = 'block';
|
||||
errorBox.scrollIntoView({ behavior: 'smooth', block: 'nearest' });
|
||||
}
|
||||
|
||||
async function sha1Hex(str) {
|
||||
const buf = await crypto.subtle.digest('SHA-1', new TextEncoder().encode(str));
|
||||
return Array.from(new Uint8Array(buf))
|
||||
.map(function(b) { return b.toString(16).padStart(2, '0'); })
|
||||
.join('')
|
||||
.toUpperCase();
|
||||
}
|
||||
|
||||
async function isPwned(password) {
|
||||
const hash = await sha1Hex(password);
|
||||
const prefix = hash.slice(0, 5);
|
||||
const suffix = hash.slice(5);
|
||||
const res = await fetch('https://api.pwnedpasswords.com/range/' + prefix, {
|
||||
headers: { 'Add-Padding': 'true' }
|
||||
});
|
||||
if (!res.ok) { return false; }
|
||||
const text = await res.text();
|
||||
return text.toUpperCase().split('\n').some(function(line) {
|
||||
return line.split(':')[0] === suffix;
|
||||
});
|
||||
}
|
||||
|
||||
form.addEventListener('submit', async function (e) {
|
||||
e.preventDefault();
|
||||
errorBox.style.display = 'none';
|
||||
|
||||
const password = form.querySelector('[name="password"]').value;
|
||||
const confirm = form.querySelector('[name="password_confirmation"]').value;
|
||||
const verify = form.querySelector('[name="verify_password"]');
|
||||
const errors = [];
|
||||
|
||||
if (password.length < 16) {
|
||||
errors.push(passwordLengthError);
|
||||
}
|
||||
if (password !== confirm) {
|
||||
errors.push(passwordMatchError);
|
||||
}
|
||||
|
||||
if (errors.length > 0) {
|
||||
showErrors(errors);
|
||||
return;
|
||||
}
|
||||
|
||||
if (verify && verify.checked) {
|
||||
submitBtn.disabled = true;
|
||||
submitBtn.textContent = waitForVerify;
|
||||
try {
|
||||
if (await isPwned(password)) {
|
||||
errors.push(needSecurePassword);
|
||||
}
|
||||
} catch (_) {
|
||||
// network failure — let server validate
|
||||
}
|
||||
submitBtn.disabled = false;
|
||||
submitBtn.textContent = originalBtnText;
|
||||
}
|
||||
|
||||
if (errors.length > 0) {
|
||||
showErrors(errors);
|
||||
return;
|
||||
}
|
||||
|
||||
form.submit();
|
||||
});
|
||||
})();
|
||||
@@ -38,9 +38,9 @@ function parseToLocalDates() {
|
||||
var obj = moment.utc(date).local();
|
||||
|
||||
console.log('auto convert to timezone is: "' + obj.format() + '"');
|
||||
console.log('moment.js format is: "'+date_time_js+'"');
|
||||
console.log('moment.js format is: "' + date_time_js + '"');
|
||||
|
||||
$(this).text(obj.format(date_time_js) + ' ('+ timeZone +')');
|
||||
$(this).text(obj.format(date_time_js) + ' (' + timeZone + ')');
|
||||
});
|
||||
}
|
||||
|
||||
@@ -50,19 +50,25 @@ $(function () {
|
||||
configAccounting(currencySymbol);
|
||||
|
||||
// on submit of logout button:
|
||||
$('.logout-link').click(function(e) {
|
||||
$('.logout-link').click(function (e) {
|
||||
e.preventDefault();
|
||||
document.getElementById('logout-form').submit();
|
||||
return false;
|
||||
});
|
||||
|
||||
// save sidebar collapsed state when page loads.
|
||||
$('[data-toggle="push-menu"]').click(function () {
|
||||
localStorage.setItem('ff3_sidebar_collapsed', (!$('body').hasClass('sidebar-collapse')).toString());
|
||||
});
|
||||
|
||||
|
||||
|
||||
// on submit of form, disable any button in form:
|
||||
$('form.form-horizontal:not(.nodisablebutton)').on('submit', function () {
|
||||
$('button[type="submit"]').prop('disabled', true);
|
||||
});
|
||||
|
||||
|
||||
|
||||
// when you click on a currency, this happens:
|
||||
$('.currency-option').on('click', currencySelect);
|
||||
|
||||
|
||||
@@ -100,29 +100,29 @@ $(function () {
|
||||
// show rule triggers
|
||||
$('.rule-triggers-show').click(function (e) {
|
||||
var obj = $(e.currentTarget);
|
||||
$('.rule-trigger-list[data-id="' + obj.data('id') + '"]').show();
|
||||
$('.rule-triggers-show[data-id="' + obj.data('id') + '"]').hide();
|
||||
$('.rule-trigger-list[data-id="' + obj.data('id') + '"]').removeClass('hidden');
|
||||
$('.rule-triggers-show[data-id="' + obj.data('id') + '"]').addClass('hidden');
|
||||
});
|
||||
|
||||
$('.rule-trigger-list').each(function(i,v) {
|
||||
var obj = $(v);
|
||||
if(obj.data('count') > 2) {
|
||||
obj.hide();
|
||||
$('.rule-triggers-show[data-id="' + obj.data('id') + '"]').show();
|
||||
obj.addClass('hidden');
|
||||
$('.rule-triggers-show[data-id="' + obj.data('id') + '"]').removeClass('hidden');
|
||||
}
|
||||
});
|
||||
// show rule actions
|
||||
$('.rule-actions-show').click(function (e) {
|
||||
var obj = $(e.currentTarget);
|
||||
$('.rule-action-list[data-id="' + obj.data('id') + '"]').show();
|
||||
$('.rule-actions-show[data-id="' + obj.data('id') + '"]').hide();
|
||||
$('.rule-action-list[data-id="' + obj.data('id') + '"]').removeClass('hidden');
|
||||
$('.rule-actions-show[data-id="' + obj.data('id') + '"]').addClass('hidden');
|
||||
});
|
||||
|
||||
$('.rule-action-list').each(function(i,v) {
|
||||
var obj = $(v);
|
||||
if(obj.data('count') > 1) {
|
||||
obj.hide();
|
||||
$('.rule-actions-show[data-id="' + obj.data('id') + '"]').show();
|
||||
obj.addClass('hidden');
|
||||
$('.rule-actions-show[data-id="' + obj.data('id') + '"]').removeClass('hidden');
|
||||
}
|
||||
});
|
||||
|
||||
@@ -194,9 +194,9 @@ function testRuleTriggers(e) {
|
||||
// Show warning if appropriate
|
||||
if (data.warning) {
|
||||
modal.find(".transaction-warning .warning-contents").text(data.warning);
|
||||
modal.find(".transaction-warning").show();
|
||||
modal.find(".transaction-warning").removeClass('hidden');
|
||||
} else {
|
||||
modal.find(".transaction-warning").hide();
|
||||
modal.find(".transaction-warning").addClass('hidden');
|
||||
}
|
||||
|
||||
// Show the modal dialog
|
||||
|
||||
@@ -36,6 +36,7 @@
|
||||
"/public/v1/js/ff/accounts/show.js": "/public/v1/js/ff/accounts/show.js",
|
||||
"/public/v1/js/ff/admin/update/index.js": "/public/v1/js/ff/admin/update/index.js",
|
||||
"/public/v1/js/ff/admin/users.js": "/public/v1/js/ff/admin/users.js",
|
||||
"/public/v1/js/ff/auth/register.js": "/public/v1/js/ff/auth/register.js",
|
||||
"/public/v1/js/ff/bills/create.js": "/public/v1/js/ff/bills/create.js",
|
||||
"/public/v1/js/ff/bills/edit.js": "/public/v1/js/ff/bills/edit.js",
|
||||
"/public/v1/js/ff/bills/index.js": "/public/v1/js/ff/bills/index.js",
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
{
|
||||
"firefly": {
|
||||
"explain_pats": "I token di accesso personale sono chiavi lunghe (con un massimo di 1 anno) che consentono l'accesso diretto e illimitato ai tuoi dati di Firefly III. Strumenti come il Firefly III Data Importer e l'integrazione di Firefly III in Home Assistant utilizzano tali token per connettersi a Firefly III e usarlo. Quando si crea un token, \u00e8 visibile solo una volta. Il token \u00e8 molto lungo.",
|
||||
"profile_oauth_clients_explain": "An OAuth client can be used to connect \"smart\" applications to Firefly III: applications that are capable of redirecting you to your Firefly III, get your permission, and return you back. The Firefly III Data Importer is such an application. OAuth clients can be generated with or without a \"secret\". This secret is used to authenticate the client. Since not all clients are capable of storing the secret, so you have the option to generate a client without one.",
|
||||
"profile_oauth_clients_explain": "Un client OAuth pu\u00f2 essere utilizzato per connettere applicazioni \"intelligenti\" a Firefly III: applicazioni in grado di reindirizzarti al tuo Firefly III, ottenere la tua autorizzazione e riportarti indietro. Firefly III Data Importer \u00e8 un esempio di tale applicazione. I client OAuth possono essere generati con o senza una \"chiave segreta\". Questa chiave segreta viene utilizzata per autenticare il client. Poich\u00e9 non tutti i client sono in grado di memorizzare la chiave segreta, hai la possibilit\u00e0 di generare un client senza di essa.",
|
||||
"regenerate_secret": "Rigenera chiave segreta",
|
||||
"administrations_page_title": "Amministrazioni finanziarie",
|
||||
"administrations_index_menu": "Amministrazioni finanziarie",
|
||||
@@ -104,8 +104,8 @@
|
||||
"piggy_bank": "Salvadanaio",
|
||||
"profile_oauth_client_secret_title": "Segreto del client",
|
||||
"profile_oauth_client_secret_expl": "Ecco il segreto del nuovo client. Questa \u00e8 l'unica occasione in cui viene mostrato pertanto non perderlo! Ora puoi usare questo segreto per effettuare delle richieste alle API.",
|
||||
"profile_oauth_confidential": "Keep a secret?",
|
||||
"profile_oauth_confidential_help": "Can the application you're using this for keep a secret? The Firefly III Data Importer CANNOT keep a secret, so UNCHECK the box. In other cases, it's up to you.",
|
||||
"profile_oauth_confidential": "Mantenere un segreto?",
|
||||
"profile_oauth_confidential_help": "L'applicazione che stai utilizzando pu\u00f2 mantenere un segreto? Firefly III Data Importer NON pu\u00f2 mantenere un segreto, quindi DESELEZIONARE la casella. Negli altri casi, la scelta \u00e8 a tua discrezione.",
|
||||
"multi_account_warning_unknown": "A seconda del tipo di transazione che hai creato, il conto di origine e\/o destinazione delle successive suddivisioni pu\u00f2 essere sovrascritto da qualsiasi cosa sia definita nella prima suddivisione della transazione.",
|
||||
"multi_account_warning_withdrawal": "Ricorda che il conto di origine delle successive suddivisioni verr\u00e0 sovrascritto da quello definito nella prima suddivisione del prelievo.",
|
||||
"multi_account_warning_deposit": "Ricorda che il conto di destinazione delle successive suddivisioni verr\u00e0 sovrascritto da quello definito nella prima suddivisione del deposito.",
|
||||
|
||||
@@ -1,13 +1,13 @@
|
||||
{
|
||||
"firefly": {
|
||||
"explain_pats": "Personal Access Tokens are long lived (with a maximum of 1 year) keys that allow direct and unlimited access to your Firefly III data. Tools like the Firefly III Data Importer and the Firefly III integration in Home Assistant use such tokens to connect to Firefly III and do their thing. When you create a token, it is only visible once. The token is also very long.",
|
||||
"profile_oauth_clients_explain": "An OAuth client can be used to connect \"smart\" applications to Firefly III: applications that are capable of redirecting you to your Firefly III, get your permission, and return you back. The Firefly III Data Importer is such an application. OAuth clients can be generated with or without a \"secret\". This secret is used to authenticate the client. Since not all clients are capable of storing the secret, so you have the option to generate a client without one.",
|
||||
"regenerate_secret": "Regenerate secret",
|
||||
"explain_pats": "\u4e2a\u4eba\u8bbf\u95ee\u4ee4\u724c\u662f\u4e00\u79cd\u957f\u671f\u6709\u6548\uff08\u6700\u957f1\u5e74\uff09\u7684\u4ee4\u724c\uff0c\u53ef\u8ba9\u60a8\u76f4\u63a5\u3001\u65e0\u9650\u5236\u5730\u8bbf\u95ee Firefly III \u6570\u636e\u3002\u8bf8\u5982 `Firefly III Data Importer` \u4ee5\u53ca Home Assistant \u4e2d\u7684 Firefly III \u96c6\u6210\u7b49\u5de5\u5177\uff0c\u6b63\u662f\u4f7f\u7528\u6b64\u7c7b\u4ee4\u724c\u8fde\u63a5\u81f3 Firefly III \u5e76\u5b8c\u6210\u5404\u81ea\u7684\u4efb\u52a1\u3002\u521b\u5efa\u4ee4\u724c\u65f6\uff0c\u5b83\u4ec5\u4f1a\u663e\u793a\u4e00\u6b21\u3002\u4ee4\u724c\u5b57\u7b26\u4e32\u901a\u5e38\u4f1a\u5f88\u957f\u3002",
|
||||
"profile_oauth_clients_explain": "OAuth\u5ba2\u6237\u7aef\u53ef\u7528\u4e8e\u5c06\u201c\u667a\u80fd\u201d\u5e94\u7528\u8fde\u63a5\u5230 Firefly III\uff1a\u5b83\u4eec\u80fd\u591f\u5c06\u60a8\u91cd\u5b9a\u5411\u5230\u60a8\u7684Firefly III\uff0c\u83b7\u53d6\u60a8\u7684\u6388\u6743\uff0c\u7136\u540e\u8fd4\u56de\u5e94\u7528\u3002`Firefly III Data Importer`\u5c31\u662f\u8fd9\u6837\u7684\u5e94\u7528\u3002\u751f\u6210OAuth\u5ba2\u6237\u7aef\u65f6\u53ef\u4ee5\u9009\u62e9\u662f\u5426\u9644\u5e26\u201c\u5bc6\u94a5\uff08secret\uff09\u201d\uff0c\u5b83\u7528\u4e8e\u9a8c\u8bc1\u5ba2\u6237\u7aef\u3002\u5e76\u975e\u6240\u6709\u5ba2\u6237\u7aef\u90fd\u80fd\u591f\u5b89\u5168\u5b58\u50a8\u5bc6\u94a5\uff0c\u6240\u4ee5\u60a8\u53ef\u4ee5\u9009\u62e9\u751f\u6210\u4e00\u4e2a\u4e0d\u5e26\u5bc6\u94a5\u7684\u5ba2\u6237\u7aef\u3002",
|
||||
"regenerate_secret": "\u91cd\u65b0\u751f\u6210\u5bc6\u94a5",
|
||||
"administrations_page_title": "\u8d22\u52a1\u7ba1\u7406",
|
||||
"administrations_index_menu": "\u8d22\u52a1\u7ba1\u7406",
|
||||
"expires_at": "\u8fc7\u671f\u4e8e",
|
||||
"temp_administrations_introduction": "Firefly III will soon get the ability to manage multiple financial administrations. Right now, you only have the one. You can set the title of this administration and its primary currency. This replaces the previous setting where you would set your \"default currency\". This setting is now tied to the financial administration and can be different per administration.",
|
||||
"administration_currency_form_help": "It may take a long time for the page to load if you change the primary currency because transaction may need to be converted to your (new) primary currency.",
|
||||
"temp_administrations_introduction": "Firefly III \u4e0d\u4e45\u5c06\u652f\u6301\u7ba1\u7406\u591a\u4e2a\u8d22\u52a1\u7ba1\u7406\u3002\u76ee\u524d\u60a8\u53ea\u6709\u4e00\u4e2a\u3002\u60a8\u53ef\u4ee5\u8bbe\u7f6e\u8fd9\u4e2a\u8d22\u52a1\u7ba1\u7406\u7684\u540d\u79f0\u53ca\u5176\u4e3b\u8981\u8d27\u5e01\u3002\u8fd9\u53d6\u4ee3\u4e86\u4e4b\u524d\u201c\u9ed8\u8ba4\u8d27\u5e01\u201d\u7684\u8bbe\u7f6e\u3002\u8be5\u8bbe\u7f6e\u73b0\u5728\u5df2\u4e0e\u8d22\u52a1\u7ba1\u7406\u6302\u94a9\uff0c\u6bcf\u4e2a\u8d22\u52a1\u7ba1\u7406\u53ef\u4ee5\u6709\u4e0d\u540c\u8bbe\u7f6e\u3002",
|
||||
"administration_currency_form_help": "\u5982\u679c\u60a8\u66f4\u6539\u4e3b\u8981\u8d27\u5e01\uff0c\u9875\u9762\u52a0\u8f7d\u53ef\u80fd\u9700\u8981\u5f88\u957f\u65f6\u95f4\uff0c\u56e0\u4e3a\u4ea4\u6613\u53ef\u80fd\u9700\u8981\u8f6c\u6362\u4e3a\u60a8\u7684(\u65b0)\u4e3b\u8981\u8d27\u5e01\u3002",
|
||||
"administrations_page_edit_sub_title_js": "\u7f16\u8f91\u8d22\u52a1\u7ba1\u7406{title}",
|
||||
"table": "\u8868\u683c",
|
||||
"welcome_back": "\u4eca\u5929\u7406\u8d22\u4e86\u5417\uff1f",
|
||||
@@ -75,8 +75,8 @@
|
||||
"profile_whoops": "\u5f88\u62b1\u6b49\uff01",
|
||||
"profile_something_wrong": "\u53d1\u751f\u9519\u8bef\uff01",
|
||||
"profile_try_again": "\u53d1\u751f\u9519\u8bef\uff0c\u8bf7\u7a0d\u540e\u518d\u8bd5\u3002",
|
||||
"profile_oauth_clients": "OAuth Clients and Applications",
|
||||
"profile_oauth_no_clients": "You have not created any OAuth clients or applications.",
|
||||
"profile_oauth_clients": "OAuth \u5ba2\u6237\u7aef\u548c\u5e94\u7528\u7a0b\u5e8f",
|
||||
"profile_oauth_no_clients": "\u60a8\u8fd8\u6ca1\u6709\u521b\u5efa\u4efb\u4f55 OAuth \u5ba2\u6237\u7aef\u6216\u5e94\u7528\u7a0b\u5e8f\u3002",
|
||||
"profile_oauth_clients_header": "\u5ba2\u6237\u7aef",
|
||||
"profile_oauth_client_id": "\u5ba2\u6237\u7aef ID",
|
||||
"profile_oauth_client_name": "\u540d\u79f0",
|
||||
@@ -86,7 +86,7 @@
|
||||
"profile_oauth_edit_client": "\u7f16\u8f91\u5ba2\u6237\u7aef",
|
||||
"profile_oauth_name_help": "\u60a8\u7684\u7528\u6237\u53ef\u4ee5\u8bc6\u522b\u5e76\u4fe1\u4efb\u7684\u4fe1\u606f",
|
||||
"profile_oauth_redirect_url": "\u8df3\u8f6c\u7f51\u5740",
|
||||
"profile_oauth_clients_external_auth": "Please note that if you're using an external authentication provider like Authelia, OAuth Clients will not work. You can use Personal Access Tokens only.",
|
||||
"profile_oauth_clients_external_auth": "\u8bf7\u6ce8\u610f\uff1a\u5982\u679c\u60a8\u6b63\u5728\u4f7f\u7528\u5982 Authelia \u7684\u5916\u90e8\u8eab\u4efd\u9a8c\u8bc1\u63d0\u4f9b\u5546\uff0cOAuth \u5ba2\u6237\u7aef\u5c06\u65e0\u6cd5\u4f7f\u7528\u3002\u60a8\u53ea\u80fd\u4f7f\u7528\u4e2a\u4eba\u8bbf\u95ee\u4ee4\u724c\u3002",
|
||||
"profile_oauth_redirect_url_help": "\u60a8\u7684\u5e94\u7528\u7a0b\u5e8f\u7684\u6388\u6743\u56de\u8c03\u7f51\u5740",
|
||||
"profile_authorized_apps": "\u5df2\u6388\u6743\u5e94\u7528",
|
||||
"profile_authorized_clients": "\u5df2\u6388\u6743\u5ba2\u6237\u7aef",
|
||||
@@ -104,24 +104,24 @@
|
||||
"piggy_bank": "\u5b58\u94b1\u7f50",
|
||||
"profile_oauth_client_secret_title": "\u5ba2\u6237\u7aef\u5bc6\u94a5",
|
||||
"profile_oauth_client_secret_expl": "\u8bf7\u59a5\u5584\u4fdd\u5b58\u60a8\u7684\u65b0\u5ba2\u6237\u7aef\u7684\u5bc6\u94a5\uff0c\u6b64\u5bc6\u94a5\u4ec5\u4f1a\u5728\u8fd9\u91cc\u5c55\u793a\u4e00\u6b21\u3002\u60a8\u73b0\u5728\u5df2\u53ef\u4ee5\u4f7f\u7528\u6b64\u5bc6\u94a5\u8fdb\u884c API \u8bf7\u6c42\u3002",
|
||||
"profile_oauth_confidential": "Keep a secret?",
|
||||
"profile_oauth_confidential_help": "Can the application you're using this for keep a secret? The Firefly III Data Importer CANNOT keep a secret, so UNCHECK the box. In other cases, it's up to you.",
|
||||
"profile_oauth_confidential": "\u9644\u5e26\u5bc6\u94a5\uff1f",
|
||||
"profile_oauth_confidential_help": "\u60a8\u8981\u8fde\u63a5\u7684\u5e94\u7528\u80fd\u5426\u5b89\u5168\u4fdd\u5b58\u5bc6\u94a5\uff1f`Firefly III Data Importer`\u65e0\u6cd5\u4fdd\u5b58\u5bc6\u94a5\uff0c\u56e0\u6b64\u8bf7\u53d6\u6d88\u52fe\u9009\u6b64\u6846\u3002\u5176\u4ed6\u60c5\u51b5\u7531\u60a8\u81ea\u884c\u51b3\u5b9a\u3002",
|
||||
"multi_account_warning_unknown": "\u6839\u636e\u60a8\u521b\u5efa\u7684\u4ea4\u6613\u7c7b\u578b\uff0c\u540e\u7eed\u62c6\u5206\u7684\u6765\u6e90\u548c\/\u6216\u76ee\u6807\u8d26\u6237\u53ef\u80fd\u88ab\u4ea4\u6613\u7684\u9996\u7b14\u62c6\u5206\u7684\u914d\u7f6e\u6240\u8986\u76d6\u3002",
|
||||
"multi_account_warning_withdrawal": "\u8bf7\u6ce8\u610f\uff0c\u540e\u7eed\u62c6\u5206\u7684\u6765\u6e90\u8d26\u6237\u5c06\u4f1a\u88ab\u652f\u51fa\u7684\u9996\u7b14\u62c6\u5206\u7684\u914d\u7f6e\u6240\u8986\u76d6\u3002",
|
||||
"multi_account_warning_deposit": "\u8bf7\u6ce8\u610f\uff0c\u540e\u7eed\u62c6\u5206\u7684\u76ee\u6807\u8d26\u6237\u5c06\u4f1a\u88ab\u6536\u5165\u7684\u9996\u7b14\u62c6\u5206\u7684\u914d\u7f6e\u6240\u8986\u76d6\u3002",
|
||||
"multi_account_warning_transfer": "\u8bf7\u6ce8\u610f\uff0c\u540e\u7eed\u62c6\u5206\u7684\u6765\u6e90\u548c\u76ee\u6807\u8d26\u6237\u5c06\u4f1a\u88ab\u8f6c\u8d26\u7684\u9996\u7b14\u62c6\u5206\u7684\u914d\u7f6e\u6240\u8986\u76d6\u3002",
|
||||
"webhook_trigger_ANY": "After any event",
|
||||
"webhook_trigger_ANY": "\u5728\u4efb\u4f55\u4e8b\u4ef6\u4e4b\u540e",
|
||||
"webhook_trigger_STORE_TRANSACTION": "\u4ea4\u6613\u521b\u5efa\u540e",
|
||||
"webhook_trigger_UPDATE_TRANSACTION": "\u4ea4\u6613\u66f4\u65b0\u540e",
|
||||
"webhook_trigger_DESTROY_TRANSACTION": "\u4ea4\u6613\u5220\u9664\u540e",
|
||||
"webhook_trigger_STORE_BUDGET": "After budget creation",
|
||||
"webhook_trigger_UPDATE_BUDGET": "After budget update",
|
||||
"webhook_trigger_DESTROY_BUDGET": "After budget delete",
|
||||
"webhook_trigger_STORE_UPDATE_BUDGET_LIMIT": "After budgeted amount change",
|
||||
"webhook_trigger_STORE_BUDGET": "\u9884\u7b97\u521b\u5efa\u540e",
|
||||
"webhook_trigger_UPDATE_BUDGET": "\u9884\u7b97\u66f4\u65b0\u540e",
|
||||
"webhook_trigger_DESTROY_BUDGET": "\u9884\u7b97\u5220\u9664\u540e",
|
||||
"webhook_trigger_STORE_UPDATE_BUDGET_LIMIT": "\u9884\u7b97\u91d1\u989d\u53d8\u66f4\u540e",
|
||||
"webhook_response_TRANSACTIONS": "\u4ea4\u6613\u8be6\u60c5",
|
||||
"webhook_response_RELEVANT": "Relevant details",
|
||||
"webhook_response_RELEVANT": "\u76f8\u5173\u660e\u7ec6",
|
||||
"webhook_response_ACCOUNTS": "\u8d26\u6237\u8be6\u60c5",
|
||||
"webhook_response_NONE": "No details",
|
||||
"webhook_response_NONE": "\u65e0\u8be6\u7ec6\u4fe1\u606f",
|
||||
"webhook_delivery_JSON": "JSON",
|
||||
"actions": "\u64cd\u4f5c",
|
||||
"meta_data": "\u540e\u8bbe\u8d44\u6599",
|
||||
@@ -163,7 +163,7 @@
|
||||
"url": "\u7f51\u5740",
|
||||
"active": "\u542f\u7528",
|
||||
"interest_date": "\u5229\u606f\u65e5\u671f",
|
||||
"administration_currency": "Primary currency",
|
||||
"administration_currency": "\u4e3b\u8981\u8d27\u5e01",
|
||||
"title": "\u6807\u9898",
|
||||
"date": "\u65e5\u671f",
|
||||
"book_date": "\u767b\u8bb0\u65e5\u671f",
|
||||
@@ -183,7 +183,7 @@
|
||||
"list": {
|
||||
"title": "\u6807\u9898",
|
||||
"active": "\u662f\u5426\u542f\u7528\uff1f",
|
||||
"primary_currency": "Primary currency",
|
||||
"primary_currency": "\u4e3b\u8981\u8d27\u5e01",
|
||||
"trigger": "\u89e6\u53d1\u6761\u4ef6",
|
||||
"response": "\u7b54\u590d",
|
||||
"delivery": "\u4ea4\u4ed8",
|
||||
|
||||
@@ -12,7 +12,7 @@
|
||||
"laravel-vite-plugin": "^3",
|
||||
"patch-package": "^8",
|
||||
"sass": "^1",
|
||||
"vite": "=8.0.8",
|
||||
"vite": "=8.0.10",
|
||||
"vite-plugin-manifest-sri": "^0.2.0"
|
||||
},
|
||||
"dependencies": {
|
||||
|
||||
@@ -1398,6 +1398,7 @@ return [
|
||||
'pref_locale' => 'Locale settings',
|
||||
'pref_languages_help' => 'Firefly III supports several languages. Which one do you prefer?',
|
||||
'pref_locale_help' => 'Firefly III allows you to set other local settings, like how currencies, numbers and dates are formatted. Entries in this list may not be supported by your system. Firefly III doesn\'t have the correct date settings for every locale; contact me for improvements.',
|
||||
'pref_locale_exception' => 'Firefly III can only change how you view dates. Entering a date will always be formatted according to your browser settings, not Firefly III settings. If your browser is set to "English (US)" you must always enter the date formatted as mm/dd/yyyy. No setting in Firefly III can change that.',
|
||||
'pref_locale_no_demo' => 'This feature won\'t work for the demo user.',
|
||||
'pref_convert_to_primary' => 'Display amounts in your primary currency',
|
||||
'pref_convert_to_primary_help' => 'This option will make Firefly III try to display and show your primary currency in as many places as possible, converting amounts where necessary. This sacrifices accuracy for ease of use, because conversion is not always exact. Please verify that Firefly III has the necessary conversion rates on the "exchange rates"-page.',
|
||||
@@ -1621,7 +1622,7 @@ return [
|
||||
'secure_pw_ff' => 'Do you use the same password all over the internet? If one site loses your password, hackers have access to all your data. Firefly III relies on you to choose a strong and unique password to protect your financial records.',
|
||||
'secure_pw_check_box' => 'To help you do that Firefly III can check if the password you want to use has been stolen in the past. If this is the case, Firefly III advises you NOT to use that password.',
|
||||
'secure_pw_working_title' => 'How does it work?',
|
||||
'secure_pw_working' => 'By checking the box, Firefly III will send the first five characters of the SHA1 hash of your password to <a href="https://www.troyhunt.com/introducing-306-million-freely-downloadable-pwned-passwords/">the website of Troy Hunt</a> to see if it is on the list. This will stop you from using unsafe passwords as is recommended in the latest <a href="https://pages.nist.gov/800-63-3/sp800-63b.html">NIST Special Publication</a> on this subject.',
|
||||
'secure_pw_working' => 'By checking the box, Firefly III will send the first five characters of the SHA1 hash of your password to <a href="https://haveibeenpwned.com/API/v3#PwnedPasswords">the website of Troy Hunt</a> to see if it is on the list. This will stop you from using unsafe passwords as is recommended in the latest <a href="https://pages.nist.gov/800-63-3/sp800-63b.html">NIST Special Publication</a> on this subject.',
|
||||
'secure_pw_should' => 'Should I check the box?',
|
||||
'secure_pw_long_password' => 'Yes. Always verify your password is safe.',
|
||||
'command_line_token' => 'Command line token',
|
||||
@@ -1813,6 +1814,13 @@ return [
|
||||
'options' => 'Options',
|
||||
|
||||
// budgets:
|
||||
'spent_this_period' => 'Spent on this budget',
|
||||
'spent_this_period_per_day' => 'Spent on this budget per day (:days day(s))',
|
||||
'spent_in_budget_limit_outside_period' => 'Spent on this budget, but NOT in this period',
|
||||
'spent_in_budget_limit_outside_period_per_day' => 'Spent on this budget, but NOT in this period per day (:days day(s))',
|
||||
'left_in_budget_limit_overview' => 'Left in this budget',
|
||||
'left_in_budget_limit_per_day' => 'Left in this budget per day (:days day(s))',
|
||||
'nothing_left_in_budget' => 'The budget is now empty',
|
||||
'daily_budgets' => 'Daily budgets',
|
||||
'weekly_budgets' => 'Weekly budgets',
|
||||
'monthly_budgets' => 'Monthly budgets',
|
||||
|
||||
@@ -23,6 +23,7 @@
|
||||
declare(strict_types=1);
|
||||
|
||||
return [
|
||||
'verifying_password' => 'Verifying password...',
|
||||
'invalid_account_list' => 'Invalid account type list entry ":value"',
|
||||
'invalid_transaction_type_list' => 'Invalid transaction type list',
|
||||
'limit_exists' => 'There is already a budget limit (amount) for this budget and currency in the given period.',
|
||||
|
||||
@@ -21,6 +21,10 @@
|
||||
</div>
|
||||
@endif
|
||||
|
||||
<div id="client-errors" class="alert alert-danger" role="alert" style="display:none;">
|
||||
<ul id="client-errors-list"></ul>
|
||||
</div>
|
||||
|
||||
<div class="card">
|
||||
<div class="card-body register-card-body">
|
||||
<p class="login-box-msg">{{ trans('firefly.register_new_account') }}</p>
|
||||
@@ -35,17 +39,17 @@
|
||||
</div>
|
||||
<div class="input-group mb-3">
|
||||
<input type="password" autocomplete="new-password" required class="form-control"
|
||||
placeholder="{{ trans('form.password') }}" name="password"/>
|
||||
placeholder="{{ trans('form.password') }}" minlength="16" name="password"/>
|
||||
<div class="input-group-text"> <em class="fa-solid fa-lock"></em> </div>
|
||||
</div>
|
||||
<div class="input-group mb-3">
|
||||
<input type="password" autocomplete="new-password" required class="form-control"
|
||||
<input type="password" autocomplete="new-password" minlength="16" required class="form-control"
|
||||
placeholder="{{ trans('form.password_confirmation') }}" name="password_confirmation"/>
|
||||
<div class="input-group-text"> <em class="fa-solid fa-lock"></em> </div>
|
||||
</div>
|
||||
<div class="row">
|
||||
<div class="col-12">
|
||||
<input type="checkbox" id="verify_password" checked name="verify_password" value="1">
|
||||
<input type="checkbox" id="verify_password" name="verify_password" value="1">
|
||||
<label for="verify_password">
|
||||
{{ trans('form.verify_password') }}
|
||||
<a href="#"
|
||||
@@ -76,5 +80,12 @@
|
||||
|
||||
@endsection
|
||||
@section('scripts')
|
||||
@vite(['src/pages/dashboard/dashboard.js'])
|
||||
<script nonce="{{ $JS_NONCE }}">
|
||||
var route = '{{ route('register') }}';
|
||||
var passwordLengthError = '{{ blade_escape_js((string)trans('validation.min.string', ['attribute' => 'password', 'min' => 16])) }}';
|
||||
var passwordMatchError = '{{ blade_escape_js(trans('validation.confirmed', ['attribute' => 'password'])) }}';
|
||||
var waitForVerify = '{{ blade_escape_js(trans('validation.verifying_password')) }}';
|
||||
var needSecurePassword = '{{ blade_escape_js(trans('validation.secure_password')) }}';
|
||||
</script>
|
||||
<script nonce="{{$JS_NONCE}}" src="v1/js/ff/auth/register.js"></script>
|
||||
@endsection
|
||||
|
||||
@@ -2,21 +2,21 @@
|
||||
{% for budgetLimit in budget.budgeted %}
|
||||
<span class="left_span" data-currency="{{ budgetLimit.currency_id }}" data-limit="{{ budgetLimit.id }}" data-value="{{ budgetLimit.left }}" class="amount_left">
|
||||
{# the amount left #}
|
||||
{{ formatAmountBySymbol(budgetLimit.left, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }}
|
||||
<span title="{{ 'left_in_budget_limit_overview'|_ }}">{{ formatAmountBySymbol(budgetLimit.left, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }}</span>
|
||||
|
||||
{# if the budget limit is in the past, this is not interesting. #}
|
||||
{# if there is nothing left, this is not interesting. #}
|
||||
{% if not budgetLimit.in_past and -1 == bccomp('0',budgetLimit.left) %}
|
||||
{% if 0 == budgetLimit.active_days_left %}
|
||||
({{ formatAmountBySymbol(budgetLimit.left, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }})
|
||||
<span title="{{ trans('firefly.left_in_budget_limit_per_day', {days: 0}) }}">({{ formatAmountBySymbol(budgetLimit.left, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }})
|
||||
{% else %}
|
||||
({{ formatAmountBySymbol(budgetLimit.left / budgetLimit.active_days_left, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }})
|
||||
<span title="{{ trans('firefly.left_in_budget_limit_per_day', {days: budgetLimit.active_days_left}) }}">({{ formatAmountBySymbol(budgetLimit.left / budgetLimit.active_days_left, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }})</span>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
|
||||
{# if there is nothing left, just format 0.00 #}
|
||||
{% if not budgetLimit.in_past and -1 != bccomp('0',budgetLimit.left) %}
|
||||
({{ formatAmountBySymbol('0', budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }})
|
||||
<span title="{{ 'nothing_left_in_budget'|_ }}">({{ formatAmountBySymbol('0', budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }})</span>
|
||||
{% endif %}
|
||||
</span><br />
|
||||
{% endfor %}
|
||||
|
||||
@@ -1,10 +1,10 @@
|
||||
{# this is spent in budget limits: #}
|
||||
{% for budgetLimit in budget.budgeted %}
|
||||
{{ formatAmountBySymbol(budgetLimit.spent, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }}
|
||||
<span title="{{ 'spent_this_period'|_ }}">{{ formatAmountBySymbol(budgetLimit.spent, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }}</span>
|
||||
{% if 0 == budgetLimit.active_days_passed %}
|
||||
({{ formatAmountBySymbol(budgetLimit.spent, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }})
|
||||
<span title="{{ trans('firefly.spent_this_period_per_day', {days: 0}) }}">({{ formatAmountBySymbol(budgetLimit.spent, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }})</span>
|
||||
{% else %}
|
||||
({{ formatAmountBySymbol(budgetLimit.spent / budgetLimit.active_days_passed, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }})
|
||||
<span title="{{ trans('firefly.spent_this_period_per_day', {days: budgetLimit.active_days_passed}) }}">({{ formatAmountBySymbol(budgetLimit.spent / budgetLimit.active_days_passed, budgetLimit.currency_symbol, budgetLimit.currency_decimal_places) }})</span>
|
||||
{% endif %}
|
||||
<br />
|
||||
{% endfor %}
|
||||
@@ -12,11 +12,11 @@
|
||||
{# this is spent NOT in budget limits: #}
|
||||
{% for spent in budget.spent %}
|
||||
{% if 0 != bccomp('0', spent.spent_outside) %}
|
||||
{{ formatAmountBySymbol(spent.spent_outside, spent.currency_symbol, spent.currency_decimal_places) }}
|
||||
<span title="{{ 'spent_in_budget_limit_outside_period'|_ }}">{{ formatAmountBySymbol(spent.spent_outside, spent.currency_symbol, spent.currency_decimal_places) }}</span>
|
||||
{% if 0 == activeDaysPassed %}
|
||||
({{ formatAmountBySymbol(spent.spent_outside, spent.currency_symbol, spent.currency_decimal_places) }})
|
||||
<span title="{{ trans('firefly.spent_in_budget_limit_outside_period_per_day', {days: 0}) }}">({{ formatAmountBySymbol(spent.spent_outside, spent.currency_symbol, spent.currency_decimal_places) }})</span>
|
||||
{% else %}
|
||||
({{ formatAmountBySymbol(spent.spent_outside / activeDaysPassed, spent.currency_symbol, spent.currency_decimal_places) }})
|
||||
<span title="{{ trans('firefly.spent_in_budget_limit_outside_period_per_day', {days: activeDaysPassed}) }}">({{ formatAmountBySymbol(spent.spent_outside / activeDaysPassed, spent.currency_symbol, spent.currency_decimal_places) }})</span>
|
||||
{% endif %}
|
||||
<br />
|
||||
{% endif %}
|
||||
|
||||
@@ -86,14 +86,18 @@
|
||||
<script src="v1/js/lib/respond.min.js?v={{ FF_BUILD_TIME }}" nonce="{{ JS_NONCE }}"></script>
|
||||
<![endif]-->
|
||||
|
||||
{# this entry is in the header so it's loaded early #}
|
||||
<script type="text/javascript" nonce="{{ JS_NONCE }}">var forceDemoOff = false;</script>
|
||||
|
||||
{# favicons #}
|
||||
{% include 'partials.favicons' %}
|
||||
|
||||
</head>
|
||||
<body class="skin-firefly-iii sidebar-mini hold-transition">
|
||||
{# this entry is in the header so it's loaded early #}
|
||||
<script type="text/javascript" nonce="{{ JS_NONCE }}">
|
||||
var forceDemoOff = false;
|
||||
if ('true' === localStorage.getItem('ff3_sidebar_collapsed')) {
|
||||
document.body.classList.add('sidebar-collapse');
|
||||
}
|
||||
</script>
|
||||
<div class="wrapper" id="app">
|
||||
|
||||
<header class="main-header">
|
||||
|
||||
@@ -44,7 +44,7 @@
|
||||
{# language #}
|
||||
<div class="preferences-box">
|
||||
<h3>{{ 'pref_languages'|_ }}</h3>
|
||||
<p class="text-info">{{ 'pref_languages_help'|_ }}</p>
|
||||
<p>{{ 'pref_languages_help'|_ }}</p>
|
||||
<div class="form-group">
|
||||
<div class="col-sm-12">
|
||||
<select class="form-control" id="lang_holder" name="language">
|
||||
@@ -63,7 +63,7 @@
|
||||
</div>
|
||||
|
||||
|
||||
<p class="text-info">
|
||||
<p>
|
||||
<br/>
|
||||
{{ 'pref_languages_locale'|_ }}
|
||||
</p>
|
||||
@@ -73,7 +73,8 @@
|
||||
{% if not isDocker %}
|
||||
<div class="preferences-box">
|
||||
<h3>{{ 'pref_locale'|_ }}</h3>
|
||||
<p class="text-info">{{ 'pref_locale_help'|_ }}</p>
|
||||
<p>{{ 'pref_locale_help'|_ }}</p>
|
||||
<p class="text-warning">{{ 'pref_locale_exception'|_ }}</p>
|
||||
<div class="form-group">
|
||||
<div class="col-sm-12">
|
||||
<select class="form-control" id="locale_holder" name="locale">
|
||||
@@ -104,7 +105,7 @@
|
||||
{# fiscal year #}
|
||||
<div class="preferences-box">
|
||||
<h3>{{ 'pref_custom_fiscal_year'|_ }}</h3>
|
||||
<p class="text-info">
|
||||
<p>
|
||||
{{ 'pref_custom_fiscal_year_help'|_ }}
|
||||
</p>
|
||||
{% set isCustomFiscalYear = customFiscalYear == 1 ? true : false %}
|
||||
@@ -116,7 +117,7 @@
|
||||
{% if fireflyiiiconfig('enable_exchange_rates', true) %}
|
||||
<div class="preferences-box">
|
||||
<h3>{{ 'pref_convert_to_primary'|_ }}</h3>
|
||||
<p class="text-info">
|
||||
<p>
|
||||
{{ 'pref_convert_to_primary_help'|_ }}
|
||||
</p>
|
||||
{{ ExpandedForm.checkbox('convertToPrimary','1',convertToPrimary,{ 'label' : 'pref_convert_primary_help'|_ }) }}
|
||||
@@ -125,7 +126,7 @@
|
||||
{# conversion back to primary currency #}
|
||||
<div class="preferences-box">
|
||||
<h3>{{ 'pref_anonymous'|_ }}</h3>
|
||||
<p class="text-info">
|
||||
<p>
|
||||
{{ 'pref_anonymous_help'|_ }}
|
||||
</p>
|
||||
{{ ExpandedForm.checkbox('anonymous','1',anonymous,{ 'label' : 'pref_anonymous_label'|_ }) }}
|
||||
@@ -138,7 +139,7 @@
|
||||
{# transaction preferences #}
|
||||
<div class="preferences-box">
|
||||
<h3>{{ 'pref_optional_fields_transaction'|_ }}</h3>
|
||||
<p class="text-info">
|
||||
<p>
|
||||
{{ 'pref_optional_fields_transaction_help'|_ }}
|
||||
</p>
|
||||
<h4>{{ 'optional_tj_date_fields'|_ }}</h4>
|
||||
@@ -169,7 +170,7 @@
|
||||
<div class="col-lg-6 col-md-6 col-sm-12 col-xs-12">
|
||||
<div class="preferences-box">
|
||||
<h3>{{ 'pref_home_screen_accounts'|_ }}</h3>
|
||||
<p class="text-info">{{ 'pref_home_screen_accounts_help'|_ }}</p>
|
||||
<p>{{ 'pref_home_screen_accounts_help'|_ }}</p>
|
||||
{% for type, accounts in groupedAccounts %}
|
||||
<strong>{{ type }}</strong>
|
||||
{% for id, name in accounts %}
|
||||
@@ -206,7 +207,7 @@
|
||||
{# view range #}
|
||||
<div class="preferences-box">
|
||||
<h3>{{ 'pref_view_range'|_ }}</h3>
|
||||
<p class="text-info">{{ 'pref_view_range_help'|_ }}</p>
|
||||
<p>{{ 'pref_view_range_help'|_ }}</p>
|
||||
|
||||
<div class="radio">
|
||||
<label>
|
||||
@@ -311,12 +312,12 @@
|
||||
<div class="col-lg-6 col-md-6 col-sm-12 col-xs-12">
|
||||
<div class="preferences-box">
|
||||
<h3>{{ 'list_page_size_title'|_ }}</h3>
|
||||
<p class="text-info">{{ 'list_page_size_help'|_ }}</p>
|
||||
<p>{{ 'list_page_size_help'|_ }}</p>
|
||||
{{ ExpandedForm.integer('listPageSize',listPageSize,{'label' : 'list_page_size_label'|_}) }}
|
||||
</div>
|
||||
<div class="preferences-box">
|
||||
<h3>{{ 'dark_mode_preference'|_ }}</h3>
|
||||
<p class="text-info">{{ 'dark_mode_preference_help'|_ }}</p>
|
||||
<p>{{ 'dark_mode_preference_help'|_ }}</p>
|
||||
{% for mode in availableDarkModes %}
|
||||
<div class="radio">
|
||||
<label>
|
||||
|
||||
@@ -487,6 +487,9 @@
|
||||
{% if '' != link.foreign_amount %}
|
||||
({{ link.foreign_amount|raw }})
|
||||
{% endif %}
|
||||
{% if link.notes != "" %}
|
||||
({{ link.notes }})
|
||||
{% endif %}
|
||||
</td>
|
||||
</tr>
|
||||
{% endfor %}
|
||||
|
||||
@@ -32,8 +32,9 @@ if (!defined('DATEFORMAT')) {
|
||||
// new Passport routes.
|
||||
Route::group(
|
||||
[
|
||||
'as' => 'passport.',
|
||||
'prefix' => 'oauth',
|
||||
'as' => 'passport.',
|
||||
'prefix' => 'oauth',
|
||||
'middleware' => ['user-full-auth'],
|
||||
// 'namespace' => 'FireflyIII\Http\Controllers\OAuth',
|
||||
],
|
||||
function (): void {
|
||||
@@ -386,6 +387,9 @@ Route::group(
|
||||
}
|
||||
);
|
||||
|
||||
|
||||
|
||||
|
||||
// exchange rates controller
|
||||
Route::group(
|
||||
['middleware' => 'user-full-auth', 'namespace' => 'FireflyIII\Http\Controllers\ExchangeRates', 'prefix' => 'exchange-rates', 'as' => 'exchange-rates.'],
|
||||
|
||||
Reference in New Issue
Block a user