mirror of
https://github.com/firefly-iii/firefly-iii.git
synced 2025-10-12 15:35:15 +00:00
Merge branch 'release/4.7.5.1'
This commit is contained in:
@@ -16,8 +16,8 @@ mkdir -p $FIREFLY_PATH/storage/upload
|
|||||||
|
|
||||||
|
|
||||||
# make sure we own the volumes:
|
# make sure we own the volumes:
|
||||||
chown -R www-data:www-data -R $FIREFLY_PATH/storage/export $FIREFLY_PATH/storage/upload $FIREFLY_PATH/storage/logs $FIREFLY_PATH/storage/framework/cache
|
chown -R www-data:www-data -R $FIREFLY_PATH/storage
|
||||||
chmod -R 775 $FIREFLY_PATH/storage/export $FIREFLY_PATH/storage/upload $FIREFLY_PATH/storage/upload $FIREFLY_PATH/storage/logs $FIREFLY_PATH/storage/framework/cache
|
chmod -R 775 $FIREFLY_PATH/storage
|
||||||
|
|
||||||
# remove any lingering files that may break upgrades:
|
# remove any lingering files that may break upgrades:
|
||||||
rm -f $FIREFLY_PATH/storage/logs/laravel.log
|
rm -f $FIREFLY_PATH/storage/logs/laravel.log
|
||||||
|
@@ -1,4 +1,3 @@
|
|||||||
# Ignore composer specific files and vendor folder
|
# Ignore composer specific files and vendor folder
|
||||||
composer.phar
|
composer.phar
|
||||||
composer.lock
|
|
||||||
vendor
|
vendor
|
||||||
|
@@ -1,3 +1,12 @@
|
|||||||
|
# 4.7.5.1
|
||||||
|
- [Issue 1531](https://github.com/firefly-iii/firefly-iii/issues/1531), the database routine incorrectly reports empty categories.
|
||||||
|
- [Issue 1532](https://github.com/firefly-iii/firefly-iii/issues/1532), broken dropdown for autosuggest things.
|
||||||
|
- [Issue 1533](https://github.com/firefly-iii/firefly-iii/issues/1533), fix where the import could not import category names.
|
||||||
|
- [Issue 1538](https://github.com/firefly-iii/firefly-iii/issues/1538), fix a bug where Spectre would not work when ignoring rules.
|
||||||
|
- [Issue 1542](https://github.com/firefly-iii/firefly-iii/issues/1542), fix a bug where the importer was incapable of generating new currencies.
|
||||||
|
- [Issue 1541](https://github.com/firefly-iii/firefly-iii/issues/1541), no longer ignore composer.lock in Docker ignore.
|
||||||
|
- Bills are stored inactive.
|
||||||
|
|
||||||
# 4.7.5
|
# 4.7.5
|
||||||
- A new feature called "recurring transactions" that will make Firefly III automatically create transactions for you.
|
- A new feature called "recurring transactions" that will make Firefly III automatically create transactions for you.
|
||||||
- New API end points for attachments, available budgets, budgets, budget limits, categories, configuration, currency exchange rates, journal links, link types, piggy banks, preferences, recurring transactions, rules, rule groups and tags.
|
- New API end points for attachments, available budgets, budgets, budget limits, categories, configuration, currency exchange rates, journal links, link types, piggy banks, preferences, recurring transactions, rules, rule groups and tags.
|
||||||
|
@@ -16,7 +16,7 @@ const pkgdef :Spk.PackageDefinition = (
|
|||||||
manifest = (
|
manifest = (
|
||||||
appTitle = (defaultText = "Firefly III"),
|
appTitle = (defaultText = "Firefly III"),
|
||||||
appVersion = 14,
|
appVersion = 14,
|
||||||
appMarketingVersion = (defaultText = "4.7.5"),
|
appMarketingVersion = (defaultText = "4.7.5.1"),
|
||||||
|
|
||||||
actions = [
|
actions = [
|
||||||
# Define your "new document" handlers here.
|
# Define your "new document" handlers here.
|
||||||
|
@@ -35,7 +35,7 @@ use League\Fractal\Serializer\JsonApiSerializer;
|
|||||||
/**
|
/**
|
||||||
* Returns basic information about this installation.
|
* Returns basic information about this installation.
|
||||||
*
|
*
|
||||||
* Class AboutController
|
* Class AboutController.
|
||||||
*/
|
*/
|
||||||
class AboutController extends Controller
|
class AboutController extends Controller
|
||||||
{
|
{
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* AccountController.php
|
* AccountController.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -41,13 +40,15 @@ use League\Fractal\Resource\Item;
|
|||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class AccountController
|
* Class AccountController.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class AccountController extends Controller
|
class AccountController extends Controller
|
||||||
{
|
{
|
||||||
/** @var CurrencyRepositoryInterface */
|
/** @var CurrencyRepositoryInterface The currency repository */
|
||||||
private $currencyRepository;
|
private $currencyRepository;
|
||||||
/** @var AccountRepositoryInterface */
|
/** @var AccountRepositoryInterface The account repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -125,6 +126,8 @@ class AccountController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Show single instance.
|
||||||
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
* @param Account $account
|
* @param Account $account
|
||||||
*
|
*
|
||||||
@@ -146,6 +149,8 @@ class AccountController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Store a new instance.
|
||||||
|
*
|
||||||
* @param AccountRequest $request
|
* @param AccountRequest $request
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\JsonResponse
|
* @return \Illuminate\Http\JsonResponse
|
||||||
@@ -197,52 +202,25 @@ class AccountController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* All the available types.
|
||||||
|
*
|
||||||
* @param string $type
|
* @param string $type
|
||||||
*
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
private function mapTypes(string $type): array
|
private function mapTypes(string $type): array
|
||||||
{
|
{
|
||||||
$types = [
|
$types = [
|
||||||
'all' => [
|
'all' => [AccountType::DEFAULT, AccountType::CASH, AccountType::ASSET, AccountType::EXPENSE, AccountType::REVENUE,
|
||||||
AccountType::DEFAULT,
|
AccountType::INITIAL_BALANCE, AccountType::BENEFICIARY, AccountType::IMPORT, AccountType::RECONCILIATION,
|
||||||
AccountType::CASH,
|
AccountType::LOAN,],
|
||||||
AccountType::ASSET,
|
'asset' => [AccountType::DEFAULT, AccountType::ASSET,],
|
||||||
AccountType::EXPENSE,
|
'cash' => [AccountType::CASH,],
|
||||||
AccountType::REVENUE,
|
'expense' => [AccountType::EXPENSE, AccountType::BENEFICIARY,],
|
||||||
AccountType::INITIAL_BALANCE,
|
'revenue' => [AccountType::REVENUE,],
|
||||||
AccountType::BENEFICIARY,
|
'special' => [AccountType::CASH, AccountType::INITIAL_BALANCE, AccountType::IMPORT, AccountType::RECONCILIATION,
|
||||||
AccountType::IMPORT,
|
AccountType::LOAN,],
|
||||||
AccountType::RECONCILIATION,
|
'hidden' => [AccountType::INITIAL_BALANCE, AccountType::IMPORT, AccountType::RECONCILIATION, AccountType::LOAN,],
|
||||||
AccountType::LOAN,
|
|
||||||
],
|
|
||||||
'asset' => [
|
|
||||||
AccountType::DEFAULT,
|
|
||||||
AccountType::ASSET,
|
|
||||||
],
|
|
||||||
'cash' => [
|
|
||||||
AccountType::CASH,
|
|
||||||
],
|
|
||||||
'expense' => [
|
|
||||||
AccountType::EXPENSE,
|
|
||||||
AccountType::BENEFICIARY,
|
|
||||||
],
|
|
||||||
'revenue' => [
|
|
||||||
AccountType::REVENUE,
|
|
||||||
],
|
|
||||||
'special' => [
|
|
||||||
AccountType::CASH,
|
|
||||||
AccountType::INITIAL_BALANCE,
|
|
||||||
AccountType::IMPORT,
|
|
||||||
AccountType::RECONCILIATION,
|
|
||||||
AccountType::LOAN,
|
|
||||||
],
|
|
||||||
'hidden' => [
|
|
||||||
AccountType::INITIAL_BALANCE,
|
|
||||||
AccountType::IMPORT,
|
|
||||||
AccountType::RECONCILIATION,
|
|
||||||
AccountType::LOAN,
|
|
||||||
],
|
|
||||||
AccountType::DEFAULT => [AccountType::DEFAULT],
|
AccountType::DEFAULT => [AccountType::DEFAULT],
|
||||||
AccountType::CASH => [AccountType::CASH],
|
AccountType::CASH => [AccountType::CASH],
|
||||||
AccountType::ASSET => [AccountType::ASSET],
|
AccountType::ASSET => [AccountType::ASSET],
|
||||||
@@ -254,10 +232,11 @@ class AccountController extends Controller
|
|||||||
AccountType::RECONCILIATION => [AccountType::RECONCILIATION],
|
AccountType::RECONCILIATION => [AccountType::RECONCILIATION],
|
||||||
AccountType::LOAN => [AccountType::LOAN],
|
AccountType::LOAN => [AccountType::LOAN],
|
||||||
];
|
];
|
||||||
|
$return = $types['all'];
|
||||||
if (isset($types[$type])) {
|
if (isset($types[$type])) {
|
||||||
return $types[$type];
|
$return = $types[$type];
|
||||||
}
|
}
|
||||||
|
|
||||||
return $types['all']; // @codeCoverageIgnore
|
return $return; // @codeCoverageIgnore
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -41,11 +41,13 @@ use League\Fractal\Resource\Item;
|
|||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class AttachmentController
|
* Class AttachmentController.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class AttachmentController extends Controller
|
class AttachmentController extends Controller
|
||||||
{
|
{
|
||||||
/** @var AttachmentRepositoryInterface */
|
/** @var AttachmentRepositoryInterface The attachment repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -81,6 +83,8 @@ class AttachmentController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Download an attachment.
|
||||||
|
*
|
||||||
* @param Attachment $attachment
|
* @param Attachment $attachment
|
||||||
*
|
*
|
||||||
* @return LaravelResponse
|
* @return LaravelResponse
|
||||||
@@ -88,7 +92,7 @@ class AttachmentController extends Controller
|
|||||||
*/
|
*/
|
||||||
public function download(Attachment $attachment): LaravelResponse
|
public function download(Attachment $attachment): LaravelResponse
|
||||||
{
|
{
|
||||||
if ($attachment->uploaded === false) {
|
if (false === $attachment->uploaded) {
|
||||||
throw new FireflyException('No file has been uploaded for this attachment (yet).');
|
throw new FireflyException('No file has been uploaded for this attachment (yet).');
|
||||||
}
|
}
|
||||||
if ($this->repository->exists($attachment)) {
|
if ($this->repository->exists($attachment)) {
|
||||||
@@ -211,6 +215,8 @@ class AttachmentController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Upload an attachment.
|
||||||
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
* @param Attachment $attachment
|
* @param Attachment $attachment
|
||||||
*
|
*
|
||||||
|
@@ -24,6 +24,7 @@ declare(strict_types=1);
|
|||||||
namespace FireflyIII\Api\V1\Controllers;
|
namespace FireflyIII\Api\V1\Controllers;
|
||||||
|
|
||||||
use FireflyIII\Api\V1\Requests\AvailableBudgetRequest;
|
use FireflyIII\Api\V1\Requests\AvailableBudgetRequest;
|
||||||
|
use FireflyIII\Exceptions\FireflyException;
|
||||||
use FireflyIII\Models\AvailableBudget;
|
use FireflyIII\Models\AvailableBudget;
|
||||||
use FireflyIII\Repositories\Budget\BudgetRepositoryInterface;
|
use FireflyIII\Repositories\Budget\BudgetRepositoryInterface;
|
||||||
use FireflyIII\Repositories\Currency\CurrencyRepositoryInterface;
|
use FireflyIII\Repositories\Currency\CurrencyRepositoryInterface;
|
||||||
@@ -39,13 +40,15 @@ use League\Fractal\Resource\Item;
|
|||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class AvailableBudgetController
|
* Class AvailableBudgetController.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class AvailableBudgetController extends Controller
|
class AvailableBudgetController extends Controller
|
||||||
{
|
{
|
||||||
/** @var CurrencyRepositoryInterface */
|
/** @var CurrencyRepositoryInterface The currency repository */
|
||||||
private $currencyRepository;
|
private $currencyRepository;
|
||||||
/** @var BudgetRepositoryInterface */
|
/** @var BudgetRepositoryInterface The budget repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -144,11 +147,15 @@ class AvailableBudgetController extends Controller
|
|||||||
* @param AvailableBudgetRequest $request
|
* @param AvailableBudgetRequest $request
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
|
* @throws FireflyException
|
||||||
*/
|
*/
|
||||||
public function store(AvailableBudgetRequest $request): JsonResponse
|
public function store(AvailableBudgetRequest $request): JsonResponse
|
||||||
{
|
{
|
||||||
$data = $request->getAll();
|
$data = $request->getAll();
|
||||||
$currency = $this->currencyRepository->findNull($data['transaction_currency_id']);
|
$currency = $this->currencyRepository->findNull($data['transaction_currency_id']);
|
||||||
|
if (null === $currency) {
|
||||||
|
throw new FireflyException('Could not find the indicated currency.');
|
||||||
|
}
|
||||||
$availableBudget = $this->repository->setAvailableBudget($currency, $data['start_date'], $data['end_date'], $data['amount']);
|
$availableBudget = $this->repository->setAvailableBudget($currency, $data['start_date'], $data['end_date'], $data['amount']);
|
||||||
$manager = new Manager;
|
$manager = new Manager;
|
||||||
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
||||||
|
@@ -29,6 +29,7 @@ use FireflyIII\Exceptions\FireflyException;
|
|||||||
use FireflyIII\Models\Bill;
|
use FireflyIII\Models\Bill;
|
||||||
use FireflyIII\Repositories\Bill\BillRepositoryInterface;
|
use FireflyIII\Repositories\Bill\BillRepositoryInterface;
|
||||||
use FireflyIII\Transformers\BillTransformer;
|
use FireflyIII\Transformers\BillTransformer;
|
||||||
|
use FireflyIII\User;
|
||||||
use Illuminate\Http\JsonResponse;
|
use Illuminate\Http\JsonResponse;
|
||||||
use Illuminate\Http\Request;
|
use Illuminate\Http\Request;
|
||||||
use Illuminate\Support\Collection;
|
use Illuminate\Support\Collection;
|
||||||
@@ -39,11 +40,11 @@ use League\Fractal\Resource\Item;
|
|||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class BillController
|
* Class BillController.
|
||||||
*/
|
*/
|
||||||
class BillController extends Controller
|
class BillController extends Controller
|
||||||
{
|
{
|
||||||
/** @var BillRepositoryInterface */
|
/** @var BillRepositoryInterface The bill repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -54,9 +55,12 @@ class BillController extends Controller
|
|||||||
parent::__construct();
|
parent::__construct();
|
||||||
$this->middleware(
|
$this->middleware(
|
||||||
function ($request, $next) {
|
function ($request, $next) {
|
||||||
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
|
||||||
/** @var BillRepositoryInterface repository */
|
/** @var BillRepositoryInterface repository */
|
||||||
$this->repository = app(BillRepositoryInterface::class);
|
$this->repository = app(BillRepositoryInterface::class);
|
||||||
$this->repository->setUser(auth()->user());
|
$this->repository->setUser($admin);
|
||||||
|
|
||||||
return $next($request);
|
return $next($request);
|
||||||
}
|
}
|
||||||
@@ -103,6 +107,8 @@ class BillController extends Controller
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Show the specified bill.
|
||||||
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
* @param Bill $bill
|
* @param Bill $bill
|
||||||
*
|
*
|
||||||
@@ -124,6 +130,8 @@ class BillController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Store a bill.
|
||||||
|
*
|
||||||
* @param BillRequest $request
|
* @param BillRequest $request
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
@@ -147,6 +155,8 @@ class BillController extends Controller
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update a bill.
|
||||||
|
*
|
||||||
* @param BillRequest $request
|
* @param BillRequest $request
|
||||||
* @param Bill $bill
|
* @param Bill $bill
|
||||||
*
|
*
|
||||||
|
@@ -28,6 +28,7 @@ use FireflyIII\Exceptions\FireflyException;
|
|||||||
use FireflyIII\Models\Budget;
|
use FireflyIII\Models\Budget;
|
||||||
use FireflyIII\Repositories\Budget\BudgetRepositoryInterface;
|
use FireflyIII\Repositories\Budget\BudgetRepositoryInterface;
|
||||||
use FireflyIII\Transformers\BudgetTransformer;
|
use FireflyIII\Transformers\BudgetTransformer;
|
||||||
|
use FireflyIII\User;
|
||||||
use Illuminate\Http\JsonResponse;
|
use Illuminate\Http\JsonResponse;
|
||||||
use Illuminate\Http\Request;
|
use Illuminate\Http\Request;
|
||||||
use Illuminate\Pagination\LengthAwarePaginator;
|
use Illuminate\Pagination\LengthAwarePaginator;
|
||||||
@@ -38,11 +39,13 @@ use League\Fractal\Resource\Item;
|
|||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class BudgetController
|
* Class BudgetController.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class BudgetController extends Controller
|
class BudgetController extends Controller
|
||||||
{
|
{
|
||||||
/** @var BudgetRepositoryInterface */
|
/** @var BudgetRepositoryInterface The budget repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -53,9 +56,12 @@ class BudgetController extends Controller
|
|||||||
parent::__construct();
|
parent::__construct();
|
||||||
$this->middleware(
|
$this->middleware(
|
||||||
function ($request, $next) {
|
function ($request, $next) {
|
||||||
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
|
||||||
/** @var BudgetRepositoryInterface repository */
|
/** @var BudgetRepositoryInterface repository */
|
||||||
$this->repository = app(BudgetRepositoryInterface::class);
|
$this->repository = app(BudgetRepositoryInterface::class);
|
||||||
$this->repository->setUser(auth()->user());
|
$this->repository->setUser($admin);
|
||||||
|
|
||||||
return $next($request);
|
return $next($request);
|
||||||
}
|
}
|
||||||
@@ -111,6 +117,8 @@ class BudgetController extends Controller
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Show a budget.
|
||||||
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
* @param Budget $budget
|
* @param Budget $budget
|
||||||
*
|
*
|
||||||
@@ -132,6 +140,8 @@ class BudgetController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Store a budget.
|
||||||
|
*
|
||||||
* @param BudgetRequest $request
|
* @param BudgetRequest $request
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
@@ -154,6 +164,8 @@ class BudgetController extends Controller
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update a budget.
|
||||||
|
*
|
||||||
* @param BudgetRequest $request
|
* @param BudgetRequest $request
|
||||||
* @param Budget $budget
|
* @param Budget $budget
|
||||||
*
|
*
|
||||||
|
@@ -24,8 +24,6 @@ declare(strict_types=1);
|
|||||||
namespace FireflyIII\Api\V1\Controllers;
|
namespace FireflyIII\Api\V1\Controllers;
|
||||||
|
|
||||||
use Carbon\Carbon;
|
use Carbon\Carbon;
|
||||||
use Exception;
|
|
||||||
use FireflyIII\Api\V1\Requests\AvailableBudgetRequest;
|
|
||||||
use FireflyIII\Api\V1\Requests\BudgetLimitRequest;
|
use FireflyIII\Api\V1\Requests\BudgetLimitRequest;
|
||||||
use FireflyIII\Exceptions\FireflyException;
|
use FireflyIII\Exceptions\FireflyException;
|
||||||
use FireflyIII\Models\BudgetLimit;
|
use FireflyIII\Models\BudgetLimit;
|
||||||
@@ -43,16 +41,15 @@ use League\Fractal\Resource\Collection as FractalCollection;
|
|||||||
use League\Fractal\Resource\Item;
|
use League\Fractal\Resource\Item;
|
||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
use Log;
|
use Log;
|
||||||
use Throwable;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class BudgetLimitController
|
* Class BudgetLimitController.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class BudgetLimitController extends Controller
|
class BudgetLimitController extends Controller
|
||||||
{
|
{
|
||||||
///** @var CurrencyRepositoryInterface */
|
/** @var BudgetRepositoryInterface The budget repository */
|
||||||
//private $currencyRepository;
|
|
||||||
/** @var BudgetRepositoryInterface */
|
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -66,7 +63,6 @@ class BudgetLimitController extends Controller
|
|||||||
/** @var User $user */
|
/** @var User $user */
|
||||||
$user = auth()->user();
|
$user = auth()->user();
|
||||||
$this->repository = app(BudgetRepositoryInterface::class);
|
$this->repository = app(BudgetRepositoryInterface::class);
|
||||||
//$this->currencyRepository = app(CurrencyRepositoryInterface::class);
|
|
||||||
$this->repository->setUser($user);
|
$this->repository->setUser($user);
|
||||||
|
|
||||||
return $next($request);
|
return $next($request);
|
||||||
@@ -97,40 +93,30 @@ class BudgetLimitController extends Controller
|
|||||||
*/
|
*/
|
||||||
public function index(Request $request): JsonResponse
|
public function index(Request $request): JsonResponse
|
||||||
{
|
{
|
||||||
// create some objects:
|
$manager = new Manager;
|
||||||
$manager = new Manager;
|
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
||||||
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
$start = null;
|
||||||
|
$end = null;
|
||||||
// read budget from request
|
|
||||||
$budgetId = (int)($request->get('budget_id') ?? 0);
|
$budgetId = (int)($request->get('budget_id') ?? 0);
|
||||||
$budget = null;
|
$budget = $this->repository->findNull($budgetId);
|
||||||
if ($budgetId > 0) {
|
$this->parameters->set('budget_id', $budgetId);
|
||||||
$budget = $this->repository->findNull($budgetId);
|
|
||||||
}
|
|
||||||
// read start date from request
|
|
||||||
$start = null;
|
|
||||||
try {
|
try {
|
||||||
$start = Carbon::createFromFormat('Y-m-d', $request->get('start'));
|
$start = Carbon::createFromFormat('Y-m-d', $request->get('start'));
|
||||||
$this->parameters->set('start', $start->format('Y-m-d'));
|
$this->parameters->set('start', $start->format('Y-m-d'));
|
||||||
} catch (InvalidArgumentException $e) {
|
} catch (InvalidArgumentException $e) {
|
||||||
Log::debug(sprintf('Could not parse start date "%s": %s', $request->get('start'), $e->getMessage()));
|
Log::debug(sprintf('Invalid date: %s', $e->getMessage()));
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// read end date from request
|
|
||||||
$end = null;
|
|
||||||
try {
|
try {
|
||||||
$end = Carbon::createFromFormat('Y-m-d', $request->get('end'));
|
$end = Carbon::createFromFormat('Y-m-d', $request->get('end'));
|
||||||
$this->parameters->set('end', $end->format('Y-m-d'));
|
$this->parameters->set('end', $end->format('Y-m-d'));
|
||||||
} catch (InvalidArgumentException $e) {
|
} catch (InvalidArgumentException $e) {
|
||||||
Log::debug(sprintf('Could not parse end date "%s": %s', $request->get('end'), $e->getMessage()));
|
Log::debug(sprintf('Invalid date: %s', $e->getMessage()));
|
||||||
}
|
}
|
||||||
$this->parameters->set('budget_id', $budgetId);
|
|
||||||
|
|
||||||
// types to get, page size:
|
|
||||||
$pageSize = (int)app('preferences')->getForUser(auth()->user(), 'listPageSize', 50)->data;
|
$pageSize = (int)app('preferences')->getForUser(auth()->user(), 'listPageSize', 50)->data;
|
||||||
|
|
||||||
// get list of budget limits. Count it and split it.
|
|
||||||
$collection = new Collection;
|
$collection = new Collection;
|
||||||
if (null === $budget) {
|
if (null === $budget) {
|
||||||
$collection = $this->repository->getAllBudgetLimits($start, $end);
|
$collection = $this->repository->getAllBudgetLimits($start, $end);
|
||||||
@@ -141,12 +127,9 @@ class BudgetLimitController extends Controller
|
|||||||
|
|
||||||
$count = $collection->count();
|
$count = $collection->count();
|
||||||
$budgetLimits = $collection->slice(($this->parameters->get('page') - 1) * $pageSize, $pageSize);
|
$budgetLimits = $collection->slice(($this->parameters->get('page') - 1) * $pageSize, $pageSize);
|
||||||
|
$paginator = new LengthAwarePaginator($budgetLimits, $count, $pageSize, $this->parameters->get('page'));
|
||||||
// make paginator:
|
|
||||||
$paginator = new LengthAwarePaginator($budgetLimits, $count, $pageSize, $this->parameters->get('page'));
|
|
||||||
$paginator->setPath(route('api.v1.budget_limits.index') . $this->buildParams());
|
$paginator->setPath(route('api.v1.budget_limits.index') . $this->buildParams());
|
||||||
|
|
||||||
// present to user.
|
|
||||||
$manager->setSerializer(new JsonApiSerializer($baseUrl));
|
$manager->setSerializer(new JsonApiSerializer($baseUrl));
|
||||||
$resource = new FractalCollection($budgetLimits, new BudgetLimitTransformer($this->parameters), 'budget_limits');
|
$resource = new FractalCollection($budgetLimits, new BudgetLimitTransformer($this->parameters), 'budget_limits');
|
||||||
$resource->setPaginator(new IlluminatePaginatorAdapter($paginator));
|
$resource->setPaginator(new IlluminatePaginatorAdapter($paginator));
|
||||||
@@ -206,8 +189,8 @@ class BudgetLimitController extends Controller
|
|||||||
/**
|
/**
|
||||||
* Update the specified resource in storage.
|
* Update the specified resource in storage.
|
||||||
*
|
*
|
||||||
* @param AvailableBudgetRequest $request
|
* @param BudgetLimitRequest $request
|
||||||
* @param BudgetLimit $budgetLimit
|
* @param BudgetLimit $budgetLimit
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
|
@@ -28,6 +28,7 @@ use FireflyIII\Exceptions\FireflyException;
|
|||||||
use FireflyIII\Models\Category;
|
use FireflyIII\Models\Category;
|
||||||
use FireflyIII\Repositories\Category\CategoryRepositoryInterface;
|
use FireflyIII\Repositories\Category\CategoryRepositoryInterface;
|
||||||
use FireflyIII\Transformers\CategoryTransformer;
|
use FireflyIII\Transformers\CategoryTransformer;
|
||||||
|
use FireflyIII\User;
|
||||||
use Illuminate\Http\JsonResponse;
|
use Illuminate\Http\JsonResponse;
|
||||||
use Illuminate\Http\Request;
|
use Illuminate\Http\Request;
|
||||||
use Illuminate\Pagination\LengthAwarePaginator;
|
use Illuminate\Pagination\LengthAwarePaginator;
|
||||||
@@ -38,11 +39,13 @@ use League\Fractal\Resource\Item;
|
|||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class CategoryController
|
* Class CategoryController.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class CategoryController extends Controller
|
class CategoryController extends Controller
|
||||||
{
|
{
|
||||||
/** @var CategoryRepositoryInterface */
|
/** @var CategoryRepositoryInterface The category repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -53,9 +56,12 @@ class CategoryController extends Controller
|
|||||||
parent::__construct();
|
parent::__construct();
|
||||||
$this->middleware(
|
$this->middleware(
|
||||||
function ($request, $next) {
|
function ($request, $next) {
|
||||||
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
|
||||||
/** @var CategoryRepositoryInterface repository */
|
/** @var CategoryRepositoryInterface repository */
|
||||||
$this->repository = app(CategoryRepositoryInterface::class);
|
$this->repository = app(CategoryRepositoryInterface::class);
|
||||||
$this->repository->setUser(auth()->user());
|
$this->repository->setUser($admin);
|
||||||
|
|
||||||
return $next($request);
|
return $next($request);
|
||||||
}
|
}
|
||||||
@@ -111,6 +117,8 @@ class CategoryController extends Controller
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Show the category.
|
||||||
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
* @param Category $category
|
* @param Category $category
|
||||||
*
|
*
|
||||||
@@ -132,6 +140,8 @@ class CategoryController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Store new category.
|
||||||
|
*
|
||||||
* @param CategoryRequest $request
|
* @param CategoryRequest $request
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
@@ -154,6 +164,8 @@ class CategoryController extends Controller
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update the category.
|
||||||
|
*
|
||||||
* @param CategoryRequest $request
|
* @param CategoryRequest $request
|
||||||
* @param Category $category
|
* @param Category $category
|
||||||
*
|
*
|
||||||
|
@@ -25,39 +25,66 @@ namespace FireflyIII\Api\V1\Controllers;
|
|||||||
|
|
||||||
use FireflyIII\Exceptions\FireflyException;
|
use FireflyIII\Exceptions\FireflyException;
|
||||||
use FireflyIII\Models\Configuration;
|
use FireflyIII\Models\Configuration;
|
||||||
|
use FireflyIII\Repositories\User\UserRepositoryInterface;
|
||||||
|
use FireflyIII\User;
|
||||||
use Illuminate\Http\JsonResponse;
|
use Illuminate\Http\JsonResponse;
|
||||||
use Illuminate\Http\Request;
|
use Illuminate\Http\Request;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class ConfigurationController
|
* Class ConfigurationController.
|
||||||
*/
|
*/
|
||||||
class ConfigurationController extends Controller
|
class ConfigurationController extends Controller
|
||||||
{
|
{
|
||||||
|
|
||||||
|
|
||||||
|
/** @var UserRepositoryInterface The user repository */
|
||||||
|
private $repository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @throws FireflyException
|
* BudgetController constructor.
|
||||||
*/
|
*/
|
||||||
public function index()
|
public function __construct()
|
||||||
|
{
|
||||||
|
parent::__construct();
|
||||||
|
$this->middleware(
|
||||||
|
function ($request, $next) {
|
||||||
|
/** @noinspection UnusedConstructorDependenciesInspection */
|
||||||
|
$this->repository = app(UserRepositoryInterface::class);
|
||||||
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
|
||||||
|
if (!$this->repository->hasRole($admin, 'owner')) {
|
||||||
|
throw new FireflyException('No access to method.'); // @codeCoverageIgnore
|
||||||
|
}
|
||||||
|
|
||||||
|
return $next($request);
|
||||||
|
}
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Show all configuration.
|
||||||
|
*
|
||||||
|
* @return JsonResponse
|
||||||
|
*/
|
||||||
|
public function index(): JsonResponse
|
||||||
{
|
{
|
||||||
if (!auth()->user()->hasRole('owner')) {
|
|
||||||
throw new FireflyException('No access to method.'); // @codeCoverageIgnore
|
|
||||||
}
|
|
||||||
$configData = $this->getConfigData();
|
$configData = $this->getConfigData();
|
||||||
|
|
||||||
return response()->json(['data' => $configData], 200)->header('Content-Type', 'application/vnd.api+json');
|
return response()->json(['data' => $configData], 200)->header('Content-Type', 'application/vnd.api+json');
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update the configuration.
|
||||||
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
* @throws FireflyException
|
* @throws FireflyException
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
public function update(Request $request): JsonResponse
|
public function update(Request $request): JsonResponse
|
||||||
{
|
{
|
||||||
if (!auth()->user()->hasRole('owner')) {
|
|
||||||
throw new FireflyException('No access to method.'); // @codeCoverageIgnore
|
|
||||||
}
|
|
||||||
$name = $request->get('name');
|
$name = $request->get('name');
|
||||||
$value = $request->get('value');
|
$value = $request->get('value');
|
||||||
$valid = ['is_demo_site', 'permission_update_check', 'single_user_mode'];
|
$valid = ['is_demo_site', 'permission_update_check', 'single_user_mode'];
|
||||||
@@ -68,7 +95,7 @@ class ConfigurationController extends Controller
|
|||||||
switch ($name) {
|
switch ($name) {
|
||||||
case 'is_demo_site':
|
case 'is_demo_site':
|
||||||
case 'single_user_mode':
|
case 'single_user_mode':
|
||||||
$configValue = $value === 'true';
|
$configValue = 'true' === $value;
|
||||||
break;
|
break;
|
||||||
case 'permission_update_check':
|
case 'permission_update_check':
|
||||||
$configValue = (int)$value >= -1 && (int)$value <= 1 ? (int)$value : -1;
|
$configValue = (int)$value >= -1 && (int)$value <= 1 ? (int)$value : -1;
|
||||||
@@ -81,7 +108,10 @@ class ConfigurationController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all config values.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
private function getConfigData(): array
|
private function getConfigData(): array
|
||||||
{
|
{
|
||||||
|
@@ -37,12 +37,13 @@ use Symfony\Component\HttpFoundation\ParameterBag;
|
|||||||
* Class Controller.
|
* Class Controller.
|
||||||
*
|
*
|
||||||
* @codeCoverageIgnore
|
* @codeCoverageIgnore
|
||||||
|
* @SuppressWarnings(PHPMD.NumberOfChildren)
|
||||||
*/
|
*/
|
||||||
class Controller extends BaseController
|
class Controller extends BaseController
|
||||||
{
|
{
|
||||||
use AuthorizesRequests, DispatchesJobs, ValidatesRequests;
|
use AuthorizesRequests, DispatchesJobs, ValidatesRequests;
|
||||||
|
|
||||||
/** @var ParameterBag */
|
/** @var ParameterBag Parameters from the URI are stored here. */
|
||||||
protected $parameters;
|
protected $parameters;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -56,39 +57,42 @@ class Controller extends BaseController
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Method to help build URI's.
|
||||||
|
*
|
||||||
* @return string
|
* @return string
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
protected function buildParams(): string
|
protected function buildParams(): string
|
||||||
{
|
{
|
||||||
$return = '?';
|
$return = '?';
|
||||||
$params = [];
|
$params = [];
|
||||||
foreach ($this->parameters as $key => $value) {
|
foreach ($this->parameters as $key => $value) {
|
||||||
if ($key === 'page') {
|
if ('page' === $key) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
if ($value instanceof Carbon) {
|
if ($value instanceof Carbon) {
|
||||||
$params[$key] = $value->format('Y-m-d');
|
$params[$key] = $value->format('Y-m-d');
|
||||||
|
continue;
|
||||||
}
|
}
|
||||||
if (!$value instanceof Carbon) {
|
$params[$key] = $value;
|
||||||
$params[$key] = $value;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
$return .= http_build_query($params);
|
$return .= http_build_query($params);
|
||||||
if (\strlen($return) === 1) {
|
|
||||||
return '';
|
|
||||||
}
|
|
||||||
|
|
||||||
return $return;
|
return $return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Method to grab all parameters from the URI.
|
||||||
|
*
|
||||||
* @return ParameterBag
|
* @return ParameterBag
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
private function getParameters(): ParameterBag
|
private function getParameters(): ParameterBag
|
||||||
{
|
{
|
||||||
$bag = new ParameterBag;
|
$bag = new ParameterBag;
|
||||||
$page = (int)request()->get('page');
|
$page = (int)request()->get('page');
|
||||||
if ($page === 0) {
|
if (0 === $page) {
|
||||||
$page = 1;
|
$page = 1;
|
||||||
}
|
}
|
||||||
$bag->set('page', $page);
|
$bag->set('page', $page);
|
||||||
|
@@ -30,6 +30,7 @@ use FireflyIII\Models\TransactionCurrency;
|
|||||||
use FireflyIII\Repositories\Currency\CurrencyRepositoryInterface;
|
use FireflyIII\Repositories\Currency\CurrencyRepositoryInterface;
|
||||||
use FireflyIII\Repositories\User\UserRepositoryInterface;
|
use FireflyIII\Repositories\User\UserRepositoryInterface;
|
||||||
use FireflyIII\Transformers\CurrencyTransformer;
|
use FireflyIII\Transformers\CurrencyTransformer;
|
||||||
|
use FireflyIII\User;
|
||||||
use Illuminate\Http\JsonResponse;
|
use Illuminate\Http\JsonResponse;
|
||||||
use Illuminate\Http\Request;
|
use Illuminate\Http\Request;
|
||||||
use Illuminate\Pagination\LengthAwarePaginator;
|
use Illuminate\Pagination\LengthAwarePaginator;
|
||||||
@@ -40,29 +41,32 @@ use League\Fractal\Resource\Item;
|
|||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class CurrencyController
|
* Class CurrencyController.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class CurrencyController extends Controller
|
class CurrencyController extends Controller
|
||||||
{
|
{
|
||||||
/** @var CurrencyRepositoryInterface */
|
/** @var CurrencyRepositoryInterface The currency repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
/** @var UserRepositoryInterface */
|
/** @var UserRepositoryInterface The user repository */
|
||||||
private $userRepository;
|
private $userRepository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* CurrencyRepository constructor.
|
* CurrencyRepository constructor.
|
||||||
*
|
|
||||||
* @throws FireflyException
|
|
||||||
*/
|
*/
|
||||||
public function __construct()
|
public function __construct()
|
||||||
{
|
{
|
||||||
parent::__construct();
|
parent::__construct();
|
||||||
$this->middleware(
|
$this->middleware(
|
||||||
function ($request, $next) {
|
function ($request, $next) {
|
||||||
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
|
||||||
/** @var CurrencyRepositoryInterface repository */
|
/** @var CurrencyRepositoryInterface repository */
|
||||||
$this->repository = app(CurrencyRepositoryInterface::class);
|
$this->repository = app(CurrencyRepositoryInterface::class);
|
||||||
$this->userRepository = app(UserRepositoryInterface::class);
|
$this->userRepository = app(UserRepositoryInterface::class);
|
||||||
$this->repository->setUser(auth()->user());
|
$this->repository->setUser($admin);
|
||||||
|
|
||||||
return $next($request);
|
return $next($request);
|
||||||
}
|
}
|
||||||
@@ -79,7 +83,10 @@ class CurrencyController extends Controller
|
|||||||
*/
|
*/
|
||||||
public function delete(TransactionCurrency $currency): JsonResponse
|
public function delete(TransactionCurrency $currency): JsonResponse
|
||||||
{
|
{
|
||||||
if (!$this->userRepository->hasRole(auth()->user(), 'owner')) {
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
|
||||||
|
if (!$this->userRepository->hasRole($admin, 'owner')) {
|
||||||
// access denied:
|
// access denied:
|
||||||
throw new FireflyException('No access to method, user is not owner.'); // @codeCoverageIgnore
|
throw new FireflyException('No access to method, user is not owner.'); // @codeCoverageIgnore
|
||||||
}
|
}
|
||||||
@@ -123,6 +130,8 @@ class CurrencyController extends Controller
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Show a currency.
|
||||||
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
* @param TransactionCurrency $currency
|
* @param TransactionCurrency $currency
|
||||||
*
|
*
|
||||||
@@ -146,6 +155,8 @@ class CurrencyController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Store new currency.
|
||||||
|
*
|
||||||
* @param CurrencyRequest $request
|
* @param CurrencyRequest $request
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
@@ -155,11 +166,11 @@ class CurrencyController extends Controller
|
|||||||
{
|
{
|
||||||
$currency = $this->repository->store($request->getAll());
|
$currency = $this->repository->store($request->getAll());
|
||||||
|
|
||||||
if ($request->boolean('default') === true) {
|
|
||||||
app('preferences')->set('currencyPreference', $currency->code);
|
|
||||||
app('preferences')->mark();
|
|
||||||
}
|
|
||||||
if (null !== $currency) {
|
if (null !== $currency) {
|
||||||
|
if (true === $request->boolean('default')) {
|
||||||
|
app('preferences')->set('currencyPreference', $currency->code);
|
||||||
|
app('preferences')->mark();
|
||||||
|
}
|
||||||
$manager = new Manager();
|
$manager = new Manager();
|
||||||
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
||||||
$manager->setSerializer(new JsonApiSerializer($baseUrl));
|
$manager->setSerializer(new JsonApiSerializer($baseUrl));
|
||||||
@@ -176,6 +187,8 @@ class CurrencyController extends Controller
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update a currency.
|
||||||
|
*
|
||||||
* @param CurrencyRequest $request
|
* @param CurrencyRequest $request
|
||||||
* @param TransactionCurrency $currency
|
* @param TransactionCurrency $currency
|
||||||
*
|
*
|
||||||
@@ -186,7 +199,7 @@ class CurrencyController extends Controller
|
|||||||
$data = $request->getAll();
|
$data = $request->getAll();
|
||||||
$currency = $this->repository->update($currency, $data);
|
$currency = $this->repository->update($currency, $data);
|
||||||
|
|
||||||
if ($request->boolean('default') === true) {
|
if (true === $request->boolean('default')) {
|
||||||
app('preferences')->set('currencyPreference', $currency->code);
|
app('preferences')->set('currencyPreference', $currency->code);
|
||||||
app('preferences')->mark();
|
app('preferences')->mark();
|
||||||
}
|
}
|
||||||
|
@@ -28,20 +28,19 @@ use FireflyIII\Exceptions\FireflyException;
|
|||||||
use FireflyIII\Repositories\Currency\CurrencyRepositoryInterface;
|
use FireflyIII\Repositories\Currency\CurrencyRepositoryInterface;
|
||||||
use FireflyIII\Services\Currency\ExchangeRateInterface;
|
use FireflyIII\Services\Currency\ExchangeRateInterface;
|
||||||
use FireflyIII\Transformers\CurrencyExchangeRateTransformer;
|
use FireflyIII\Transformers\CurrencyExchangeRateTransformer;
|
||||||
|
use FireflyIII\User;
|
||||||
use Illuminate\Http\JsonResponse;
|
use Illuminate\Http\JsonResponse;
|
||||||
use Illuminate\Http\Request;
|
use Illuminate\Http\Request;
|
||||||
use InvalidArgumentException;
|
|
||||||
use League\Fractal\Manager;
|
use League\Fractal\Manager;
|
||||||
use League\Fractal\Resource\Item;
|
use League\Fractal\Resource\Item;
|
||||||
use Log;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
|
||||||
* Class CurrencyExchangeRateController
|
* Class CurrencyExchangeRateController
|
||||||
*/
|
*/
|
||||||
class CurrencyExchangeRateController extends Controller
|
class CurrencyExchangeRateController extends Controller
|
||||||
{
|
{
|
||||||
/** @var CurrencyRepositoryInterface */
|
/** @var CurrencyRepositoryInterface The currency repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -52,8 +51,11 @@ class CurrencyExchangeRateController extends Controller
|
|||||||
parent::__construct();
|
parent::__construct();
|
||||||
$this->middleware(
|
$this->middleware(
|
||||||
function ($request, $next) {
|
function ($request, $next) {
|
||||||
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
|
||||||
$this->repository = app(CurrencyRepositoryInterface::class);
|
$this->repository = app(CurrencyRepositoryInterface::class);
|
||||||
$this->repository->setUser(auth()->user());
|
$this->repository->setUser($admin);
|
||||||
|
|
||||||
return $next($request);
|
return $next($request);
|
||||||
}
|
}
|
||||||
@@ -62,6 +64,8 @@ class CurrencyExchangeRateController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Show an exchange rate.
|
||||||
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
@@ -72,8 +76,8 @@ class CurrencyExchangeRateController extends Controller
|
|||||||
// create some objects:
|
// create some objects:
|
||||||
$manager = new Manager;
|
$manager = new Manager;
|
||||||
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
||||||
|
$manager->setSerializer(new JsonApiSerializer($baseUrl));
|
||||||
|
|
||||||
// currencies
|
|
||||||
$fromCurrency = $this->repository->findByCodeNull($request->get('from') ?? 'EUR');
|
$fromCurrency = $this->repository->findByCodeNull($request->get('from') ?? 'EUR');
|
||||||
$toCurrency = $this->repository->findByCodeNull($request->get('to') ?? 'USD');
|
$toCurrency = $this->repository->findByCodeNull($request->get('to') ?? 'USD');
|
||||||
|
|
||||||
@@ -84,27 +88,19 @@ class CurrencyExchangeRateController extends Controller
|
|||||||
throw new FireflyException('Unknown destination currency.');
|
throw new FireflyException('Unknown destination currency.');
|
||||||
}
|
}
|
||||||
|
|
||||||
$dateObj = new Carbon;
|
$dateObj = Carbon::createFromFormat('Y-m-d', $request->get('date') ?? date('Y-m-d'));
|
||||||
try {
|
|
||||||
$dateObj = Carbon::createFromFormat('Y-m-d', $request->get('date') ?? date('Y-m-d'));
|
|
||||||
} catch (InvalidArgumentException $e) {
|
|
||||||
Log::debug($e->getMessage());
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
$this->parameters->set('from', $fromCurrency->code);
|
$this->parameters->set('from', $fromCurrency->code);
|
||||||
$this->parameters->set('to', $toCurrency->code);
|
$this->parameters->set('to', $toCurrency->code);
|
||||||
$this->parameters->set('date', $dateObj->format('Y-m-d'));
|
$this->parameters->set('date', $dateObj->format('Y-m-d'));
|
||||||
|
|
||||||
// get the exchange rate.
|
|
||||||
$rate = $this->repository->getExchangeRate($fromCurrency, $toCurrency, $dateObj);
|
$rate = $this->repository->getExchangeRate($fromCurrency, $toCurrency, $dateObj);
|
||||||
if (null === $rate) {
|
if (null === $rate) {
|
||||||
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
// create service:
|
// create service:
|
||||||
/** @var ExchangeRateInterface $service */
|
/** @var ExchangeRateInterface $service */
|
||||||
$service = app(ExchangeRateInterface::class);
|
$service = app(ExchangeRateInterface::class);
|
||||||
$service->setUser(auth()->user());
|
$service->setUser($admin);
|
||||||
|
|
||||||
// get rate:
|
|
||||||
$rate = $service->getRate($fromCurrency, $toCurrency, $dateObj);
|
$rate = $service->getRate($fromCurrency, $toCurrency, $dateObj);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -39,13 +39,21 @@ use League\Fractal\Resource\Collection as FractalCollection;
|
|||||||
use League\Fractal\Resource\Item;
|
use League\Fractal\Resource\Item;
|
||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class JournalLinkController.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
|
*/
|
||||||
class JournalLinkController extends Controller
|
class JournalLinkController extends Controller
|
||||||
{
|
{
|
||||||
/** @var JournalRepositoryInterface */
|
/** @var JournalRepositoryInterface The journal repository */
|
||||||
private $journalRepository;
|
private $journalRepository;
|
||||||
/** @var LinkTypeRepositoryInterface */
|
/** @var LinkTypeRepositoryInterface The link type repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* JournalLinkController constructor.
|
||||||
|
*/
|
||||||
public function __construct()
|
public function __construct()
|
||||||
{
|
{
|
||||||
parent::__construct();
|
parent::__construct();
|
||||||
@@ -175,6 +183,8 @@ class JournalLinkController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update object.
|
||||||
|
*
|
||||||
* @param JournalLinkRequest $request
|
* @param JournalLinkRequest $request
|
||||||
* @param TransactionJournalLink $journalLink
|
* @param TransactionJournalLink $journalLink
|
||||||
*
|
*
|
||||||
|
@@ -40,17 +40,21 @@ use League\Fractal\Resource\Item;
|
|||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Class LinkTypeController.
|
||||||
*
|
*
|
||||||
* Class LinkTypeController
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class LinkTypeController extends Controller
|
class LinkTypeController extends Controller
|
||||||
{
|
{
|
||||||
/** @var LinkTypeRepositoryInterface */
|
/** @var LinkTypeRepositoryInterface The link type repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
/** @var UserRepositoryInterface */
|
/** @var UserRepositoryInterface The user repository */
|
||||||
private $userRepository;
|
private $userRepository;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* LinkTypeController constructor.
|
||||||
|
*/
|
||||||
public function __construct()
|
public function __construct()
|
||||||
{
|
{
|
||||||
parent::__construct();
|
parent::__construct();
|
||||||
@@ -77,7 +81,7 @@ class LinkTypeController extends Controller
|
|||||||
*/
|
*/
|
||||||
public function delete(LinkType $linkType): JsonResponse
|
public function delete(LinkType $linkType): JsonResponse
|
||||||
{
|
{
|
||||||
if ($linkType->editable === false) {
|
if (false === $linkType->editable) {
|
||||||
throw new FireflyException(sprintf('You cannot delete this link type (#%d, "%s")', $linkType->id, $linkType->name));
|
throw new FireflyException(sprintf('You cannot delete this link type (#%d, "%s")', $linkType->id, $linkType->name));
|
||||||
}
|
}
|
||||||
$this->repository->destroy($linkType, null);
|
$this->repository->destroy($linkType, null);
|
||||||
@@ -151,7 +155,10 @@ class LinkTypeController extends Controller
|
|||||||
*/
|
*/
|
||||||
public function store(LinkTypeRequest $request): JsonResponse
|
public function store(LinkTypeRequest $request): JsonResponse
|
||||||
{
|
{
|
||||||
if (!$this->userRepository->hasRole(auth()->user(), 'owner')) {
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
|
||||||
|
if (!$this->userRepository->hasRole($admin, 'owner')) {
|
||||||
throw new FireflyException('You need the "owner"-role to do this.');
|
throw new FireflyException('You need the "owner"-role to do this.');
|
||||||
}
|
}
|
||||||
$data = $request->getAll();
|
$data = $request->getAll();
|
||||||
@@ -168,6 +175,8 @@ class LinkTypeController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update object.
|
||||||
|
*
|
||||||
* @param LinkTypeRequest $request
|
* @param LinkTypeRequest $request
|
||||||
* @param LinkType $linkType
|
* @param LinkType $linkType
|
||||||
*
|
*
|
||||||
@@ -176,10 +185,14 @@ class LinkTypeController extends Controller
|
|||||||
*/
|
*/
|
||||||
public function update(LinkTypeRequest $request, LinkType $linkType): JsonResponse
|
public function update(LinkTypeRequest $request, LinkType $linkType): JsonResponse
|
||||||
{
|
{
|
||||||
if ($linkType->editable === false) {
|
if (false === $linkType->editable) {
|
||||||
throw new FireflyException(sprintf('You cannot edit this link type (#%d, "%s")', $linkType->id, $linkType->name));
|
throw new FireflyException(sprintf('You cannot edit this link type (#%d, "%s")', $linkType->id, $linkType->name));
|
||||||
}
|
}
|
||||||
if (!$this->userRepository->hasRole(auth()->user(), 'owner')) {
|
|
||||||
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
|
||||||
|
if (!$this->userRepository->hasRole($admin, 'owner')) {
|
||||||
throw new FireflyException('You need the "owner"-role to do this.');
|
throw new FireflyException('You need the "owner"-role to do this.');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -39,24 +39,30 @@ use League\Fractal\Resource\Item;
|
|||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* TODO order up and down.
|
* Class PiggyBankController.
|
||||||
* Class PiggyBankController
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class PiggyBankController extends Controller
|
class PiggyBankController extends Controller
|
||||||
{
|
{
|
||||||
|
|
||||||
/** @var PiggyBankRepositoryInterface */
|
/** @var PiggyBankRepositoryInterface The piggy bank repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* PiggyBankController constructor.
|
||||||
|
*/
|
||||||
public function __construct()
|
public function __construct()
|
||||||
{
|
{
|
||||||
parent::__construct();
|
parent::__construct();
|
||||||
$this->middleware(
|
$this->middleware(
|
||||||
function ($request, $next) {
|
function ($request, $next) {
|
||||||
/** @var User $user */
|
/** @var User $admin */
|
||||||
$user = auth()->user();
|
$admin = auth()->user();
|
||||||
|
|
||||||
$this->repository = app(PiggyBankRepositoryInterface::class);
|
$this->repository = app(PiggyBankRepositoryInterface::class);
|
||||||
|
$this->repository->setUser($admin);
|
||||||
|
|
||||||
|
|
||||||
return $next($request);
|
return $next($request);
|
||||||
}
|
}
|
||||||
@@ -160,6 +166,8 @@ class PiggyBankController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update piggy bank.
|
||||||
|
*
|
||||||
* @param PiggyBankRequest $request
|
* @param PiggyBankRequest $request
|
||||||
* @param PiggyBank $piggyBank
|
* @param PiggyBank $piggyBank
|
||||||
*
|
*
|
||||||
|
@@ -42,20 +42,6 @@ use Preferences;
|
|||||||
*/
|
*/
|
||||||
class PreferenceController extends Controller
|
class PreferenceController extends Controller
|
||||||
{
|
{
|
||||||
public function __construct()
|
|
||||||
{
|
|
||||||
parent::__construct();
|
|
||||||
$this->middleware(
|
|
||||||
function ($request, $next) {
|
|
||||||
/** @var User $user */
|
|
||||||
$user = auth()->user();
|
|
||||||
|
|
||||||
// todo add local repositories.
|
|
||||||
return $next($request);
|
|
||||||
}
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* List all of them.
|
* List all of them.
|
||||||
*
|
*
|
||||||
@@ -116,10 +102,13 @@ class PreferenceController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update a preference.
|
||||||
|
*
|
||||||
* @param PreferenceRequest $request
|
* @param PreferenceRequest $request
|
||||||
* @param Preference $preference
|
* @param Preference $preference
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
public function update(PreferenceRequest $request, Preference $preference): JsonResponse
|
public function update(PreferenceRequest $request, Preference $preference): JsonResponse
|
||||||
{
|
{
|
||||||
@@ -138,7 +127,7 @@ class PreferenceController extends Controller
|
|||||||
break;
|
break;
|
||||||
case 'customFiscalYear':
|
case 'customFiscalYear':
|
||||||
case 'twoFactorAuthEnabled':
|
case 'twoFactorAuthEnabled':
|
||||||
$newValue = (int)$data['data'] === 1;
|
$newValue = 1 === (int)$data['data'];
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
$result = Preferences::set($preference->name, $newValue);
|
$result = Preferences::set($preference->name, $newValue);
|
||||||
|
@@ -38,14 +38,16 @@ use League\Fractal\Resource\Item;
|
|||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
|
||||||
* Class RecurrenceController
|
* Class RecurrenceController
|
||||||
*/
|
*/
|
||||||
class RecurrenceController extends Controller
|
class RecurrenceController extends Controller
|
||||||
{
|
{
|
||||||
/** @var RecurringRepositoryInterface */
|
/** @var RecurringRepositoryInterface The recurring transaction repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* RecurrenceController constructor.
|
||||||
|
*/
|
||||||
public function __construct()
|
public function __construct()
|
||||||
{
|
{
|
||||||
parent::__construct();
|
parent::__construct();
|
||||||
@@ -155,6 +157,8 @@ class RecurrenceController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update single recurrence.
|
||||||
|
*
|
||||||
* @param RecurrenceRequest $request
|
* @param RecurrenceRequest $request
|
||||||
* @param Recurrence $recurrence
|
* @param Recurrence $recurrence
|
||||||
*
|
*
|
||||||
@@ -163,9 +167,6 @@ class RecurrenceController extends Controller
|
|||||||
public function update(RecurrenceRequest $request, Recurrence $recurrence): JsonResponse
|
public function update(RecurrenceRequest $request, Recurrence $recurrence): JsonResponse
|
||||||
{
|
{
|
||||||
$data = $request->getAll();
|
$data = $request->getAll();
|
||||||
|
|
||||||
//
|
|
||||||
|
|
||||||
$category = $this->repository->update($recurrence, $data);
|
$category = $this->repository->update($recurrence, $data);
|
||||||
$manager = new Manager();
|
$manager = new Manager();
|
||||||
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
||||||
|
@@ -42,9 +42,12 @@ use League\Fractal\Serializer\JsonApiSerializer;
|
|||||||
*/
|
*/
|
||||||
class RuleController extends Controller
|
class RuleController extends Controller
|
||||||
{
|
{
|
||||||
/** @var RuleRepositoryInterface */
|
/** @var RuleRepositoryInterface The rule repository */
|
||||||
private $ruleRepository;
|
private $ruleRepository;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* RuleController constructor.
|
||||||
|
*/
|
||||||
public function __construct()
|
public function __construct()
|
||||||
{
|
{
|
||||||
parent::__construct();
|
parent::__construct();
|
||||||
@@ -136,7 +139,7 @@ class RuleController extends Controller
|
|||||||
/**
|
/**
|
||||||
* Store new object.
|
* Store new object.
|
||||||
*
|
*
|
||||||
* @param Request $request
|
* @param RuleRequest $request
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
@@ -153,6 +156,8 @@ class RuleController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update a rule.
|
||||||
|
*
|
||||||
* @param RuleRequest $request
|
* @param RuleRequest $request
|
||||||
* @param Rule $rule
|
* @param Rule $rule
|
||||||
*
|
*
|
||||||
@@ -160,9 +165,9 @@ class RuleController extends Controller
|
|||||||
*/
|
*/
|
||||||
public function update(RuleRequest $request, Rule $rule): JsonResponse
|
public function update(RuleRequest $request, Rule $rule): JsonResponse
|
||||||
{
|
{
|
||||||
$rule = $this->ruleRepository->update($rule, $request->getAll());
|
$rule = $this->ruleRepository->update($rule, $request->getAll());
|
||||||
$manager = new Manager();
|
$manager = new Manager();
|
||||||
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
||||||
$manager->setSerializer(new JsonApiSerializer($baseUrl));
|
$manager->setSerializer(new JsonApiSerializer($baseUrl));
|
||||||
|
|
||||||
$resource = new Item($rule, new RuleTransformer($this->parameters), 'rules');
|
$resource = new Item($rule, new RuleTransformer($this->parameters), 'rules');
|
||||||
|
@@ -38,11 +38,17 @@ use League\Fractal\Resource\Item;
|
|||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class RuleGroupController
|
||||||
|
*/
|
||||||
class RuleGroupController extends Controller
|
class RuleGroupController extends Controller
|
||||||
{
|
{
|
||||||
/** @var RuleGroupRepositoryInterface */
|
/** @var RuleGroupRepositoryInterface The rule group repository */
|
||||||
private $ruleGroupRepository;
|
private $ruleGroupRepository;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* RuleGroupController constructor.
|
||||||
|
*/
|
||||||
public function __construct()
|
public function __construct()
|
||||||
{
|
{
|
||||||
parent::__construct();
|
parent::__construct();
|
||||||
@@ -62,7 +68,7 @@ class RuleGroupController extends Controller
|
|||||||
/**
|
/**
|
||||||
* Delete the resource.
|
* Delete the resource.
|
||||||
*
|
*
|
||||||
* @param string $object
|
* @param RuleGroup $ruleGroup
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
@@ -151,8 +157,10 @@ class RuleGroupController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param Request $request
|
* Update a rule group.
|
||||||
* @param string $object
|
*
|
||||||
|
* @param RuleGroupRequest $request
|
||||||
|
* @param RuleGroup $ruleGroup
|
||||||
*
|
*
|
||||||
* @return JsonResponse
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
|
@@ -25,6 +25,7 @@ declare(strict_types=1);
|
|||||||
namespace FireflyIII\Api\V1\Controllers;
|
namespace FireflyIII\Api\V1\Controllers;
|
||||||
|
|
||||||
use FireflyIII\Api\V1\Requests\TransactionRequest;
|
use FireflyIII\Api\V1\Requests\TransactionRequest;
|
||||||
|
use FireflyIII\Exceptions\FireflyException;
|
||||||
use FireflyIII\Helpers\Collector\JournalCollectorInterface;
|
use FireflyIII\Helpers\Collector\JournalCollectorInterface;
|
||||||
use FireflyIII\Helpers\Filter\InternalTransferFilter;
|
use FireflyIII\Helpers\Filter\InternalTransferFilter;
|
||||||
use FireflyIII\Helpers\Filter\NegativeAmountFilter;
|
use FireflyIII\Helpers\Filter\NegativeAmountFilter;
|
||||||
@@ -33,36 +34,39 @@ use FireflyIII\Models\Transaction;
|
|||||||
use FireflyIII\Models\TransactionType;
|
use FireflyIII\Models\TransactionType;
|
||||||
use FireflyIII\Repositories\Journal\JournalRepositoryInterface;
|
use FireflyIII\Repositories\Journal\JournalRepositoryInterface;
|
||||||
use FireflyIII\Transformers\TransactionTransformer;
|
use FireflyIII\Transformers\TransactionTransformer;
|
||||||
|
use FireflyIII\User;
|
||||||
|
use Illuminate\Http\JsonResponse;
|
||||||
use Illuminate\Http\Request;
|
use Illuminate\Http\Request;
|
||||||
use Illuminate\Support\Collection;
|
use Illuminate\Support\Collection;
|
||||||
use League\Fractal\Manager;
|
use League\Fractal\Manager;
|
||||||
use League\Fractal\Pagination\IlluminatePaginatorAdapter;
|
use League\Fractal\Pagination\IlluminatePaginatorAdapter;
|
||||||
use League\Fractal\Resource\Collection as FractalCollection;
|
use League\Fractal\Resource\Collection as FractalCollection;
|
||||||
use League\Fractal\Serializer\JsonApiSerializer;
|
use League\Fractal\Serializer\JsonApiSerializer;
|
||||||
use Log;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class TransactionController
|
* Class TransactionController
|
||||||
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class TransactionController extends Controller
|
class TransactionController extends Controller
|
||||||
{
|
{
|
||||||
|
|
||||||
/** @var JournalRepositoryInterface */
|
/** @var JournalRepositoryInterface The journal repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* TransactionController constructor.
|
* TransactionController constructor.
|
||||||
*
|
|
||||||
* @throws \FireflyIII\Exceptions\FireflyException
|
|
||||||
*/
|
*/
|
||||||
public function __construct()
|
public function __construct()
|
||||||
{
|
{
|
||||||
parent::__construct();
|
parent::__construct();
|
||||||
$this->middleware(
|
$this->middleware(
|
||||||
function ($request, $next) {
|
function ($request, $next) {
|
||||||
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
|
||||||
/** @var JournalRepositoryInterface repository */
|
/** @var JournalRepositoryInterface repository */
|
||||||
$this->repository = app(JournalRepositoryInterface::class);
|
$this->repository = app(JournalRepositoryInterface::class);
|
||||||
$this->repository->setUser(auth()->user());
|
$this->repository->setUser($admin);
|
||||||
|
|
||||||
return $next($request);
|
return $next($request);
|
||||||
}
|
}
|
||||||
@@ -74,9 +78,9 @@ class TransactionController extends Controller
|
|||||||
*
|
*
|
||||||
* @param \FireflyIII\Models\Transaction $transaction
|
* @param \FireflyIII\Models\Transaction $transaction
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\Response
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
public function delete(Transaction $transaction)
|
public function delete(Transaction $transaction): JsonResponse
|
||||||
{
|
{
|
||||||
$journal = $transaction->transactionJournal;
|
$journal = $transaction->transactionJournal;
|
||||||
$this->repository->destroy($journal);
|
$this->repository->destroy($journal);
|
||||||
@@ -85,33 +89,32 @@ class TransactionController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Show all transactions.
|
||||||
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\JsonResponse
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
public function index(Request $request)
|
public function index(Request $request): JsonResponse
|
||||||
{
|
{
|
||||||
$pageSize = (int)app('preferences')->getForUser(auth()->user(), 'listPageSize', 50)->data;
|
$pageSize = (int)app('preferences')->getForUser(auth()->user(), 'listPageSize', 50)->data;
|
||||||
|
$type = $request->get('type') ?? 'default';
|
||||||
// read type from URI
|
|
||||||
$type = $request->get('type') ?? 'default';
|
|
||||||
$this->parameters->set('type', $type);
|
$this->parameters->set('type', $type);
|
||||||
|
|
||||||
// types to get, page size:
|
$types = $this->mapTypes($this->parameters->get('type'));
|
||||||
$types = $this->mapTypes($this->parameters->get('type'));
|
|
||||||
|
|
||||||
$manager = new Manager();
|
$manager = new Manager();
|
||||||
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
||||||
$manager->setSerializer(new JsonApiSerializer($baseUrl));
|
$manager->setSerializer(new JsonApiSerializer($baseUrl));
|
||||||
|
|
||||||
// collect transactions using the journal collector
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
/** @var JournalCollectorInterface $collector */
|
||||||
$collector = app(JournalCollectorInterface::class);
|
$collector = app(JournalCollectorInterface::class);
|
||||||
$collector->setUser(auth()->user());
|
$collector->setUser($admin);
|
||||||
$collector->withOpposingAccount()->withCategoryInformation()->withBudgetInformation();
|
$collector->withOpposingAccount()->withCategoryInformation()->withBudgetInformation();
|
||||||
$collector->setAllAssetAccounts();
|
$collector->setAllAssetAccounts();
|
||||||
|
|
||||||
// remove internal transfer filter:
|
if (\in_array(TransactionType::TRANSFER, $types, true)) {
|
||||||
if (\in_array(TransactionType::TRANSFER, $types)) {
|
|
||||||
$collector->removeFilter(InternalTransferFilter::class);
|
$collector->removeFilter(InternalTransferFilter::class);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -124,7 +127,6 @@ class TransactionController extends Controller
|
|||||||
$paginator->setPath(route('api.v1.transactions.index') . $this->buildParams());
|
$paginator->setPath(route('api.v1.transactions.index') . $this->buildParams());
|
||||||
$transactions = $paginator->getCollection();
|
$transactions = $paginator->getCollection();
|
||||||
|
|
||||||
|
|
||||||
$resource = new FractalCollection($transactions, new TransactionTransformer($this->parameters), 'transactions');
|
$resource = new FractalCollection($transactions, new TransactionTransformer($this->parameters), 'transactions');
|
||||||
$resource->setPaginator(new IlluminatePaginatorAdapter($paginator));
|
$resource->setPaginator(new IlluminatePaginatorAdapter($paginator));
|
||||||
|
|
||||||
@@ -133,13 +135,15 @@ class TransactionController extends Controller
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Show a single transaction.
|
||||||
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
* @param Transaction $transaction
|
* @param Transaction $transaction
|
||||||
* @param string $include
|
* @param string $include
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\JsonResponse
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
public function show(Request $request, Transaction $transaction, string $include = null)
|
public function show(Request $request, Transaction $transaction, string $include = null): JsonResponse
|
||||||
{
|
{
|
||||||
$manager = new Manager();
|
$manager = new Manager();
|
||||||
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
||||||
@@ -173,13 +177,16 @@ class TransactionController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Store a new transaction.
|
||||||
|
*
|
||||||
* @param TransactionRequest $request
|
* @param TransactionRequest $request
|
||||||
*
|
*
|
||||||
* @param JournalRepositoryInterface $repository
|
* @param JournalRepositoryInterface $repository
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\JsonResponse
|
* @throws FireflyException
|
||||||
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
public function store(TransactionRequest $request, JournalRepositoryInterface $repository)
|
public function store(TransactionRequest $request, JournalRepositoryInterface $repository): JsonResponse
|
||||||
{
|
{
|
||||||
$data = $request->getAll();
|
$data = $request->getAll();
|
||||||
$data['user'] = auth()->user()->id;
|
$data['user'] = auth()->user()->id;
|
||||||
@@ -217,23 +224,21 @@ class TransactionController extends Controller
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update a transaction.
|
||||||
|
*
|
||||||
* @param TransactionRequest $request
|
* @param TransactionRequest $request
|
||||||
* @param JournalRepositoryInterface $repository
|
* @param JournalRepositoryInterface $repository
|
||||||
* @param Transaction $transaction
|
* @param Transaction $transaction
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\JsonResponse
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
public function update(TransactionRequest $request, JournalRepositoryInterface $repository, Transaction $transaction)
|
public function update(TransactionRequest $request, JournalRepositoryInterface $repository, Transaction $transaction): JsonResponse
|
||||||
{
|
{
|
||||||
$data = $request->getAll();
|
$data = $request->getAll();
|
||||||
$data['user'] = auth()->user()->id;
|
$data['user'] = auth()->user()->id;
|
||||||
|
$journal = $repository->update($transaction->transactionJournal, $data);
|
||||||
Log::debug('Inside transaction update');
|
$manager = new Manager();
|
||||||
|
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
||||||
$journal = $repository->update($transaction->transactionJournal, $data);
|
|
||||||
|
|
||||||
$manager = new Manager();
|
|
||||||
$baseUrl = $request->getSchemeAndHttpHost() . '/api/v1';
|
|
||||||
$manager->setSerializer(new JsonApiSerializer($baseUrl));
|
$manager->setSerializer(new JsonApiSerializer($baseUrl));
|
||||||
|
|
||||||
// add include parameter:
|
// add include parameter:
|
||||||
@@ -265,72 +270,38 @@ class TransactionController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* All the types you can request.
|
||||||
|
*
|
||||||
* @param string $type
|
* @param string $type
|
||||||
*
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
private function mapTypes(string $type): array
|
private function mapTypes(string $type): array
|
||||||
{
|
{
|
||||||
$types = [
|
$types = [
|
||||||
'all' => [
|
'all' => [TransactionType::WITHDRAWAL, TransactionType::DEPOSIT, TransactionType::TRANSFER, TransactionType::OPENING_BALANCE,
|
||||||
TransactionType::WITHDRAWAL,
|
TransactionType::RECONCILIATION,],
|
||||||
TransactionType::DEPOSIT,
|
'withdrawal' => [TransactionType::WITHDRAWAL,],
|
||||||
TransactionType::TRANSFER,
|
'withdrawals' => [TransactionType::WITHDRAWAL,],
|
||||||
TransactionType::OPENING_BALANCE,
|
'expense' => [TransactionType::WITHDRAWAL,],
|
||||||
TransactionType::RECONCILIATION,
|
'income' => [TransactionType::DEPOSIT,],
|
||||||
],
|
'deposit' => [TransactionType::DEPOSIT,],
|
||||||
'withdrawal' => [
|
'deposits' => [TransactionType::DEPOSIT,],
|
||||||
TransactionType::WITHDRAWAL,
|
'transfer' => [TransactionType::TRANSFER,],
|
||||||
],
|
'transfers' => [TransactionType::TRANSFER,],
|
||||||
'withdrawals' => [
|
'opening_balance' => [TransactionType::OPENING_BALANCE,],
|
||||||
TransactionType::WITHDRAWAL,
|
'reconciliation' => [TransactionType::RECONCILIATION,],
|
||||||
],
|
'reconciliations' => [TransactionType::RECONCILIATION,],
|
||||||
'expense' => [
|
'special' => [TransactionType::OPENING_BALANCE, TransactionType::RECONCILIATION,],
|
||||||
TransactionType::WITHDRAWAL,
|
'specials' => [TransactionType::OPENING_BALANCE, TransactionType::RECONCILIATION,],
|
||||||
],
|
'default' => [TransactionType::WITHDRAWAL, TransactionType::DEPOSIT, TransactionType::TRANSFER,],
|
||||||
'income' => [
|
|
||||||
TransactionType::DEPOSIT,
|
|
||||||
],
|
|
||||||
'deposit' => [
|
|
||||||
TransactionType::DEPOSIT,
|
|
||||||
],
|
|
||||||
'deposits' => [
|
|
||||||
TransactionType::DEPOSIT,
|
|
||||||
],
|
|
||||||
'transfer' => [
|
|
||||||
TransactionType::TRANSFER,
|
|
||||||
],
|
|
||||||
'transfers' => [
|
|
||||||
TransactionType::TRANSFER,
|
|
||||||
],
|
|
||||||
'opening_balance' => [
|
|
||||||
TransactionType::OPENING_BALANCE,
|
|
||||||
],
|
|
||||||
'reconciliation' => [
|
|
||||||
TransactionType::RECONCILIATION,
|
|
||||||
],
|
|
||||||
'reconciliations' => [
|
|
||||||
TransactionType::RECONCILIATION,
|
|
||||||
],
|
|
||||||
'special' => [
|
|
||||||
TransactionType::OPENING_BALANCE,
|
|
||||||
TransactionType::RECONCILIATION,
|
|
||||||
],
|
|
||||||
'specials' => [
|
|
||||||
TransactionType::OPENING_BALANCE,
|
|
||||||
TransactionType::RECONCILIATION,
|
|
||||||
],
|
|
||||||
'default' => [
|
|
||||||
TransactionType::WITHDRAWAL,
|
|
||||||
TransactionType::DEPOSIT,
|
|
||||||
TransactionType::TRANSFER,
|
|
||||||
],
|
|
||||||
];
|
];
|
||||||
|
$return = $types['default'];
|
||||||
if (isset($types[$type])) {
|
if (isset($types[$type])) {
|
||||||
return $types[$type];
|
$return = $types[$type];
|
||||||
}
|
}
|
||||||
|
|
||||||
return $types['default']; // @codeCoverageIgnore
|
return $return;
|
||||||
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -29,6 +29,7 @@ use FireflyIII\Exceptions\FireflyException;
|
|||||||
use FireflyIII\Repositories\User\UserRepositoryInterface;
|
use FireflyIII\Repositories\User\UserRepositoryInterface;
|
||||||
use FireflyIII\Transformers\UserTransformer;
|
use FireflyIII\Transformers\UserTransformer;
|
||||||
use FireflyIII\User;
|
use FireflyIII\User;
|
||||||
|
use Illuminate\Http\JsonResponse;
|
||||||
use Illuminate\Http\Request;
|
use Illuminate\Http\Request;
|
||||||
use Illuminate\Pagination\LengthAwarePaginator;
|
use Illuminate\Pagination\LengthAwarePaginator;
|
||||||
use League\Fractal\Manager;
|
use League\Fractal\Manager;
|
||||||
@@ -39,18 +40,18 @@ use League\Fractal\Serializer\JsonApiSerializer;
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class UserController
|
* Class UserController.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class UserController extends Controller
|
class UserController extends Controller
|
||||||
{
|
{
|
||||||
|
|
||||||
/** @var UserRepositoryInterface */
|
/** @var UserRepositoryInterface The user repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* UserController constructor.
|
* UserController constructor.
|
||||||
*
|
|
||||||
* @throws \FireflyIII\Exceptions\FireflyException
|
|
||||||
*/
|
*/
|
||||||
public function __construct()
|
public function __construct()
|
||||||
{
|
{
|
||||||
@@ -70,12 +71,14 @@ class UserController extends Controller
|
|||||||
*
|
*
|
||||||
* @param \FireflyIII\User $user
|
* @param \FireflyIII\User $user
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\Response
|
* @return JsonResponse
|
||||||
* @throws FireflyException
|
* @throws FireflyException
|
||||||
*/
|
*/
|
||||||
public function delete(User $user)
|
public function delete(User $user): JsonResponse
|
||||||
{
|
{
|
||||||
if (auth()->user()->hasRole('owner')) {
|
/** @var User $admin */
|
||||||
|
$admin = auth()->user();
|
||||||
|
if ($this->repository->hasRole($admin, 'owner')) {
|
||||||
$this->repository->destroy($user);
|
$this->repository->destroy($user);
|
||||||
|
|
||||||
return response()->json([], 204);
|
return response()->json([], 204);
|
||||||
@@ -88,9 +91,9 @@ class UserController extends Controller
|
|||||||
*
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\JsonResponse
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
public function index(Request $request)
|
public function index(Request $request): JsonResponse
|
||||||
{
|
{
|
||||||
// user preferences
|
// user preferences
|
||||||
$pageSize = (int)app('preferences')->getForUser(auth()->user(), 'listPageSize', 50)->data;
|
$pageSize = (int)app('preferences')->getForUser(auth()->user(), 'listPageSize', 50)->data;
|
||||||
@@ -117,12 +120,14 @@ class UserController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Show a single user.
|
||||||
|
*
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
* @param User $user
|
* @param User $user
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\JsonResponse
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
public function show(Request $request, User $user)
|
public function show(Request $request, User $user): JsonResponse
|
||||||
{
|
{
|
||||||
// make manager
|
// make manager
|
||||||
$manager = new Manager();
|
$manager = new Manager();
|
||||||
@@ -140,11 +145,13 @@ class UserController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Store a new user.
|
||||||
|
*
|
||||||
* @param UserRequest $request
|
* @param UserRequest $request
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\JsonResponse
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
public function store(UserRequest $request)
|
public function store(UserRequest $request): JsonResponse
|
||||||
{
|
{
|
||||||
$data = $request->getAll();
|
$data = $request->getAll();
|
||||||
$user = $this->repository->store($data);
|
$user = $this->repository->store($data);
|
||||||
@@ -165,12 +172,14 @@ class UserController extends Controller
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Update a user.
|
||||||
|
*
|
||||||
* @param UserRequest $request
|
* @param UserRequest $request
|
||||||
* @param User $user
|
* @param User $user
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\JsonResponse
|
* @return JsonResponse
|
||||||
*/
|
*/
|
||||||
public function update(UserRequest $request, User $user)
|
public function update(UserRequest $request, User $user): JsonResponse
|
||||||
{
|
{
|
||||||
$data = $request->getAll();
|
$data = $request->getAll();
|
||||||
$user = $this->repository->update($user, $data);
|
$user = $this->repository->update($user, $data);
|
||||||
|
@@ -23,7 +23,6 @@
|
|||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Api\V1\Requests;
|
namespace FireflyIII\Api\V1\Requests;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class AccountRequest
|
* Class AccountRequest
|
||||||
*/
|
*/
|
||||||
@@ -31,6 +30,8 @@ class AccountRequest extends Request
|
|||||||
{
|
{
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -40,6 +41,8 @@ class AccountRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -67,6 +70,8 @@ class AccountRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -26,7 +26,6 @@ namespace FireflyIII\Api\V1\Requests;
|
|||||||
use FireflyIII\Models\Bill;
|
use FireflyIII\Models\Bill;
|
||||||
use FireflyIII\Models\ImportJob;
|
use FireflyIII\Models\ImportJob;
|
||||||
use FireflyIII\Models\TransactionJournal;
|
use FireflyIII\Models\TransactionJournal;
|
||||||
use FireflyIII\Rules\IsBase64;
|
|
||||||
use FireflyIII\Rules\IsValidAttachmentModel;
|
use FireflyIII\Rules\IsValidAttachmentModel;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -35,6 +34,8 @@ use FireflyIII\Rules\IsValidAttachmentModel;
|
|||||||
class AttachmentRequest extends Request
|
class AttachmentRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -44,6 +45,8 @@ class AttachmentRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -58,6 +61,8 @@ class AttachmentRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -29,6 +29,8 @@ namespace FireflyIII\Api\V1\Requests;
|
|||||||
class AvailableBudgetRequest extends Request
|
class AvailableBudgetRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -38,6 +40,8 @@ class AvailableBudgetRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -51,6 +55,9 @@ class AvailableBudgetRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* TODO must also accept currency code.
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -33,6 +33,8 @@ class BillRequest extends Request
|
|||||||
{
|
{
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -42,6 +44,8 @@ class BillRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -64,6 +68,8 @@ class BillRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -30,6 +30,8 @@ namespace FireflyIII\Api\V1\Requests;
|
|||||||
class BudgetLimitRequest extends Request
|
class BudgetLimitRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -39,6 +41,8 @@ class BudgetLimitRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -52,6 +56,8 @@ class BudgetLimitRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -31,6 +31,8 @@ use FireflyIII\Models\Budget;
|
|||||||
class BudgetRequest extends Request
|
class BudgetRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -40,6 +42,8 @@ class BudgetRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -52,6 +56,8 @@ class BudgetRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -31,6 +31,8 @@ use FireflyIII\Models\Category;
|
|||||||
class CategoryRequest extends Request
|
class CategoryRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -40,6 +42,8 @@ class CategoryRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -51,6 +55,8 @@ class CategoryRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -30,6 +30,8 @@ namespace FireflyIII\Api\V1\Requests;
|
|||||||
class CurrencyRequest extends Request
|
class CurrencyRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -39,6 +41,8 @@ class CurrencyRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -53,6 +57,8 @@ class CurrencyRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
@@ -62,7 +68,7 @@ class CurrencyRequest extends Request
|
|||||||
'code' => 'required|between:3,3|unique:transaction_currencies,code',
|
'code' => 'required|between:3,3|unique:transaction_currencies,code',
|
||||||
'symbol' => 'required|between:1,5|unique:transaction_currencies,symbol',
|
'symbol' => 'required|between:1,5|unique:transaction_currencies,symbol',
|
||||||
'decimal_places' => 'required|between:0,20|numeric|min:0|max:20',
|
'decimal_places' => 'required|between:0,20|numeric|min:0|max:20',
|
||||||
'default' => 'in:true,false',
|
'default' => 'boolean',
|
||||||
];
|
];
|
||||||
|
|
||||||
switch ($this->method()) {
|
switch ($this->method()) {
|
||||||
|
@@ -31,6 +31,8 @@ namespace FireflyIII\Api\V1\Requests;
|
|||||||
class JournalLinkRequest extends Request
|
class JournalLinkRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -40,6 +42,8 @@ class JournalLinkRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -53,6 +57,11 @@ class JournalLinkRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* TODO include link-type name as optional parameter.
|
||||||
|
* TODO be consistent and remove notes from this object.
|
||||||
|
*
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -33,6 +33,8 @@ use Illuminate\Validation\Rule;
|
|||||||
class LinkTypeRequest extends Request
|
class LinkTypeRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -42,6 +44,8 @@ class LinkTypeRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -56,6 +60,8 @@ class LinkTypeRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -33,6 +33,8 @@ use FireflyIII\Rules\IsAssetAccountId;
|
|||||||
class PiggyBankRequest extends Request
|
class PiggyBankRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -42,6 +44,8 @@ class PiggyBankRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -58,6 +62,8 @@ class PiggyBankRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -32,6 +32,8 @@ class PreferenceRequest extends Request
|
|||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -40,6 +42,11 @@ class PreferenceRequest extends Request
|
|||||||
return auth()->check();
|
return auth()->check();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
{
|
{
|
||||||
return [
|
return [
|
||||||
@@ -47,6 +54,11 @@ class PreferenceRequest extends Request
|
|||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
{
|
{
|
||||||
return [
|
return [
|
||||||
|
@@ -24,20 +24,21 @@ declare(strict_types=1);
|
|||||||
namespace FireflyIII\Api\V1\Requests;
|
namespace FireflyIII\Api\V1\Requests;
|
||||||
|
|
||||||
use Carbon\Carbon;
|
use Carbon\Carbon;
|
||||||
use FireflyIII\Models\Account;
|
|
||||||
use FireflyIII\Models\AccountType;
|
|
||||||
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
|
|
||||||
use FireflyIII\Rules\BelongsUser;
|
use FireflyIII\Rules\BelongsUser;
|
||||||
|
use FireflyIII\Validation\RecurrenceValidation;
|
||||||
|
use FireflyIII\Validation\TransactionValidation;
|
||||||
use Illuminate\Validation\Validator;
|
use Illuminate\Validation\Validator;
|
||||||
use InvalidArgumentException;
|
|
||||||
use Log;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class RecurrenceRequest
|
* Class RecurrenceRequest
|
||||||
*/
|
*/
|
||||||
class RecurrenceRequest extends Request
|
class RecurrenceRequest extends Request
|
||||||
{
|
{
|
||||||
|
use RecurrenceValidation, TransactionValidation;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -47,6 +48,8 @@ class RecurrenceRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -67,55 +70,16 @@ class RecurrenceRequest extends Request
|
|||||||
'piggy_bank_name' => $this->string('piggy_bank_name'),
|
'piggy_bank_name' => $this->string('piggy_bank_name'),
|
||||||
'tags' => explode(',', $this->string('tags')),
|
'tags' => explode(',', $this->string('tags')),
|
||||||
],
|
],
|
||||||
'transactions' => [],
|
'transactions' => $this->getTransactionData(),
|
||||||
'repetitions' => [],
|
'repetitions' => $this->getRepetitionData(),
|
||||||
];
|
];
|
||||||
|
|
||||||
// repetition data:
|
|
||||||
/** @var array $repetitions */
|
|
||||||
$repetitions = $this->get('repetitions');
|
|
||||||
/** @var array $repetition */
|
|
||||||
foreach ($repetitions as $repetition) {
|
|
||||||
$return['repetitions'][] = [
|
|
||||||
'type' => $repetition['type'],
|
|
||||||
'moment' => $repetition['moment'],
|
|
||||||
'skip' => (int)$repetition['skip'],
|
|
||||||
'weekend' => (int)$repetition['weekend'],
|
|
||||||
];
|
|
||||||
}
|
|
||||||
// transaction data:
|
|
||||||
/** @var array $transactions */
|
|
||||||
$transactions = $this->get('transactions');
|
|
||||||
/** @var array $transaction */
|
|
||||||
foreach ($transactions as $transaction) {
|
|
||||||
$return['transactions'][] = [
|
|
||||||
'amount' => $transaction['amount'],
|
|
||||||
|
|
||||||
'currency_id' => isset($transaction['currency_id']) ? (int)$transaction['currency_id'] : null,
|
|
||||||
'currency_code' => $transaction['currency_code'] ?? null,
|
|
||||||
|
|
||||||
'foreign_amount' => $transaction['foreign_amount'] ?? null,
|
|
||||||
'foreign_currency_id' => isset($transaction['foreign_currency_id']) ? (int)$transaction['foreign_currency_id'] : null,
|
|
||||||
'foreign_currency_code' => $transaction['foreign_currency_code'] ?? null,
|
|
||||||
|
|
||||||
'budget_id' => isset($transaction['budget_id']) ? (int)$transaction['budget_id'] : null,
|
|
||||||
'budget_name' => $transaction['budget_name'] ?? null,
|
|
||||||
'category_id' => isset($transaction['category_id']) ? (int)$transaction['category_id'] : null,
|
|
||||||
'category_name' => $transaction['category_name'] ?? null,
|
|
||||||
|
|
||||||
'source_id' => isset($transaction['source_id']) ? (int)$transaction['source_id'] : null,
|
|
||||||
'source_name' => isset($transaction['source_name']) ? (string)$transaction['source_name'] : null,
|
|
||||||
'destination_id' => isset($transaction['destination_id']) ? (int)$transaction['destination_id'] : null,
|
|
||||||
'destination_name' => isset($transaction['destination_name']) ? (string)$transaction['destination_name'] : null,
|
|
||||||
|
|
||||||
'description' => $transaction['description'],
|
|
||||||
];
|
|
||||||
}
|
|
||||||
|
|
||||||
return $return;
|
return $return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
@@ -132,18 +96,12 @@ class RecurrenceRequest extends Request
|
|||||||
'nr_of_repetitions' => 'numeric|between:1,31',
|
'nr_of_repetitions' => 'numeric|between:1,31',
|
||||||
'apply_rules' => 'required|boolean',
|
'apply_rules' => 'required|boolean',
|
||||||
'active' => 'required|boolean',
|
'active' => 'required|boolean',
|
||||||
|
|
||||||
// rules for meta values:
|
|
||||||
'tags' => 'between:1,64000',
|
'tags' => 'between:1,64000',
|
||||||
'piggy_bank_id' => 'numeric',
|
'piggy_bank_id' => 'numeric',
|
||||||
|
|
||||||
// rules for repetitions.
|
|
||||||
'repetitions.*.type' => 'required|in:daily,weekly,ndom,monthly,yearly',
|
'repetitions.*.type' => 'required|in:daily,weekly,ndom,monthly,yearly',
|
||||||
'repetitions.*.moment' => 'between:0,10',
|
'repetitions.*.moment' => 'between:0,10',
|
||||||
'repetitions.*.skip' => 'required|numeric|between:0,31',
|
'repetitions.*.skip' => 'required|numeric|between:0,31',
|
||||||
'repetitions.*.weekend' => 'required|numeric|min:1|max:4',
|
'repetitions.*.weekend' => 'required|numeric|min:1|max:4',
|
||||||
|
|
||||||
// rules for transactions.
|
|
||||||
'transactions.*.currency_id' => 'numeric|exists:transaction_currencies,id|required_without:transactions.*.currency_code',
|
'transactions.*.currency_id' => 'numeric|exists:transaction_currencies,id|required_without:transactions.*.currency_code',
|
||||||
'transactions.*.currency_code' => 'min:3|max:3|exists:transaction_currencies,code|required_without:transactions.*.currency_id',
|
'transactions.*.currency_code' => 'min:3|max:3|exists:transaction_currencies,code|required_without:transactions.*.currency_id',
|
||||||
'transactions.*.foreign_amount' => 'numeric|more:0',
|
'transactions.*.foreign_amount' => 'numeric|more:0',
|
||||||
@@ -171,312 +129,76 @@ class RecurrenceRequest extends Request
|
|||||||
{
|
{
|
||||||
$validator->after(
|
$validator->after(
|
||||||
function (Validator $validator) {
|
function (Validator $validator) {
|
||||||
$this->atLeastOneTransaction($validator);
|
$this->validateOneTransaction($validator);
|
||||||
$this->atLeastOneRepetition($validator);
|
$this->validateOneRepetition($validator);
|
||||||
$this->validRepeatsUntil($validator);
|
$this->validateRecurrenceRepetition($validator);
|
||||||
$this->validRepetitionMoment($validator);
|
$this->validateRepetitionMoment($validator);
|
||||||
$this->foreignCurrencyInformation($validator);
|
$this->validateForeignCurrencyInformation($validator);
|
||||||
$this->validateAccountInformation($validator);
|
$this->validateAccountInformation($validator);
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Throws an error when this asset account is invalid.
|
* Returns the repetition data as it is found in the submitted data.
|
||||||
*
|
*
|
||||||
* @noinspection MoreThanThreeArgumentsInspection
|
* @return array
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
* @param int|null $accountId
|
|
||||||
* @param null|string $accountName
|
|
||||||
* @param string $idField
|
|
||||||
* @param string $nameField
|
|
||||||
*
|
|
||||||
* @return null|Account
|
|
||||||
*/
|
*/
|
||||||
protected function assetAccountExists(Validator $validator, ?int $accountId, ?string $accountName, string $idField, string $nameField): ?Account
|
private function getRepetitionData(): array
|
||||||
{
|
{
|
||||||
$accountId = (int)$accountId;
|
$return = [];
|
||||||
$accountName = (string)$accountName;
|
// repetition data:
|
||||||
// both empty? hard exit.
|
/** @var array $repetitions */
|
||||||
if ($accountId < 1 && '' === $accountName) {
|
$repetitions = $this->get('repetitions');
|
||||||
$validator->errors()->add($idField, trans('validation.filled', ['attribute' => $idField]));
|
/** @var array $repetition */
|
||||||
|
foreach ($repetitions as $repetition) {
|
||||||
return null;
|
$return[] = [
|
||||||
}
|
'type' => $repetition['type'],
|
||||||
// ID belongs to user and is asset account:
|
'moment' => $repetition['moment'],
|
||||||
/** @var AccountRepositoryInterface $repository */
|
'skip' => (int)$repetition['skip'],
|
||||||
$repository = app(AccountRepositoryInterface::class);
|
'weekend' => (int)$repetition['weekend'],
|
||||||
$repository->setUser(auth()->user());
|
];
|
||||||
$set = $repository->getAccountsById([$accountId]);
|
|
||||||
Log::debug(sprintf('Count of accounts found by ID %d is: %d', $accountId, $set->count()));
|
|
||||||
if ($set->count() === 1) {
|
|
||||||
/** @var Account $first */
|
|
||||||
$first = $set->first();
|
|
||||||
if ($first->accountType->type !== AccountType::ASSET) {
|
|
||||||
$validator->errors()->add($idField, trans('validation.belongs_user'));
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
// we ignore the account name at this point.
|
|
||||||
return $first;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
$account = $repository->findByName($accountName, [AccountType::ASSET]);
|
return $return;
|
||||||
if (null === $account) {
|
|
||||||
$validator->errors()->add($nameField, trans('validation.belongs_user'));
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return $account;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Adds an error to the validator when there are no repetitions in the array of data.
|
* Returns the transaction data as it is found in the submitted data. It's a complex method according to code
|
||||||
|
* standards but it just has a lot of ??-statements because of the fields that may or may not exist.
|
||||||
*
|
*
|
||||||
* @param Validator $validator
|
* @return array
|
||||||
|
* @SuppressWarnings(PHPMD.NPathComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
protected function atLeastOneRepetition(Validator $validator): void
|
private function getTransactionData(): array
|
||||||
{
|
{
|
||||||
$data = $validator->getData();
|
$return = [];
|
||||||
$repetitions = $data['repetitions'] ?? [];
|
// transaction data:
|
||||||
// need at least one transaction
|
/** @var array $transactions */
|
||||||
if (\count($repetitions) === 0) {
|
$transactions = $this->get('transactions');
|
||||||
$validator->errors()->add('description', trans('validation.at_least_one_repetition'));
|
/** @var array $transaction */
|
||||||
}
|
foreach ($transactions as $transaction) {
|
||||||
}
|
$return[] = [
|
||||||
|
'amount' => $transaction['amount'],
|
||||||
/**
|
'currency_id' => isset($transaction['currency_id']) ? (int)$transaction['currency_id'] : null,
|
||||||
* Adds an error to the validator when there are no transactions in the array of data.
|
'currency_code' => $transaction['currency_code'] ?? null,
|
||||||
*
|
'foreign_amount' => $transaction['foreign_amount'] ?? null,
|
||||||
* @param Validator $validator
|
'foreign_currency_id' => isset($transaction['foreign_currency_id']) ? (int)$transaction['foreign_currency_id'] : null,
|
||||||
*/
|
'foreign_currency_code' => $transaction['foreign_currency_code'] ?? null,
|
||||||
protected function atLeastOneTransaction(Validator $validator): void
|
'budget_id' => isset($transaction['budget_id']) ? (int)$transaction['budget_id'] : null,
|
||||||
{
|
'budget_name' => $transaction['budget_name'] ?? null,
|
||||||
$data = $validator->getData();
|
'category_id' => isset($transaction['category_id']) ? (int)$transaction['category_id'] : null,
|
||||||
$transactions = $data['transactions'] ?? [];
|
'category_name' => $transaction['category_name'] ?? null,
|
||||||
// need at least one transaction
|
'source_id' => isset($transaction['source_id']) ? (int)$transaction['source_id'] : null,
|
||||||
if (\count($transactions) === 0) {
|
'source_name' => isset($transaction['source_name']) ? (string)$transaction['source_name'] : null,
|
||||||
$validator->errors()->add('description', trans('validation.at_least_one_transaction'));
|
'destination_id' => isset($transaction['destination_id']) ? (int)$transaction['destination_id'] : null,
|
||||||
}
|
'destination_name' => isset($transaction['destination_name']) ? (string)$transaction['destination_name'] : null,
|
||||||
}
|
'description' => $transaction['description'],
|
||||||
|
];
|
||||||
/**
|
|
||||||
* TODO can be made a rule?
|
|
||||||
* If the transactions contain foreign amounts, there must also be foreign currency information.
|
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
*/
|
|
||||||
protected function foreignCurrencyInformation(Validator $validator): void
|
|
||||||
{
|
|
||||||
$data = $validator->getData();
|
|
||||||
$transactions = $data['transactions'] ?? [];
|
|
||||||
foreach ($transactions as $index => $transaction) {
|
|
||||||
// must have currency info.
|
|
||||||
if (isset($transaction['foreign_amount'])
|
|
||||||
&& !(isset($transaction['foreign_currency_id'])
|
|
||||||
|| isset($transaction['foreign_currency_code']))) {
|
|
||||||
$validator->errors()->add(
|
|
||||||
'transactions.' . $index . '.foreign_amount',
|
|
||||||
trans('validation.require_currency_info')
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Throws an error when the given opposing account (of type $type) is invalid.
|
|
||||||
* Empty data is allowed, system will default to cash.
|
|
||||||
*
|
|
||||||
* @noinspection MoreThanThreeArgumentsInspection
|
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
* @param string $type
|
|
||||||
* @param int|null $accountId
|
|
||||||
* @param null|string $accountName
|
|
||||||
* @param string $idField
|
|
||||||
*
|
|
||||||
* @return null|Account
|
|
||||||
*/
|
|
||||||
protected function opposingAccountExists(Validator $validator, string $type, ?int $accountId, ?string $accountName, string $idField): ?Account
|
|
||||||
{
|
|
||||||
$accountId = (int)$accountId;
|
|
||||||
$accountName = (string)$accountName;
|
|
||||||
// both empty? done!
|
|
||||||
if ($accountId < 1 && \strlen($accountName) === 0) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
if ($accountId !== 0) {
|
|
||||||
// ID belongs to user and is $type account:
|
|
||||||
/** @var AccountRepositoryInterface $repository */
|
|
||||||
$repository = app(AccountRepositoryInterface::class);
|
|
||||||
$repository->setUser(auth()->user());
|
|
||||||
$set = $repository->getAccountsById([$accountId]);
|
|
||||||
if ($set->count() === 1) {
|
|
||||||
/** @var Account $first */
|
|
||||||
$first = $set->first();
|
|
||||||
if ($first->accountType->type !== $type) {
|
|
||||||
$validator->errors()->add($idField, trans('validation.belongs_user'));
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
// we ignore the account name at this point.
|
|
||||||
return $first;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// not having an opposing account by this name is NOT a problem.
|
return $return;
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* TODO can be a rule?
|
|
||||||
*
|
|
||||||
* Validates the given account information. Switches on given transaction type.
|
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
*/
|
|
||||||
protected function validateAccountInformation(Validator $validator): void
|
|
||||||
{
|
|
||||||
$data = $validator->getData();
|
|
||||||
$transactions = $data['transactions'] ?? [];
|
|
||||||
$idField = 'description';
|
|
||||||
$transactionType = $data['type'] ?? 'false';
|
|
||||||
foreach ($transactions as $index => $transaction) {
|
|
||||||
$sourceId = isset($transaction['source_id']) ? (int)$transaction['source_id'] : null;
|
|
||||||
$sourceName = $transaction['source_name'] ?? null;
|
|
||||||
$destinationId = isset($transaction['destination_id']) ? (int)$transaction['destination_id'] : null;
|
|
||||||
$destinationName = $transaction['destination_name'] ?? null;
|
|
||||||
$sourceAccount = null;
|
|
||||||
$destinationAccount = null;
|
|
||||||
switch ($transactionType) {
|
|
||||||
case 'withdrawal':
|
|
||||||
$idField = 'transactions.' . $index . '.source_id';
|
|
||||||
$nameField = 'transactions.' . $index . '.source_name';
|
|
||||||
$sourceAccount = $this->assetAccountExists($validator, $sourceId, $sourceName, $idField, $nameField);
|
|
||||||
$idField = 'transactions.' . $index . '.destination_id';
|
|
||||||
$destinationAccount = $this->opposingAccountExists($validator, AccountType::EXPENSE, $destinationId, $destinationName, $idField);
|
|
||||||
break;
|
|
||||||
case 'deposit':
|
|
||||||
$idField = 'transactions.' . $index . '.source_id';
|
|
||||||
$sourceAccount = $this->opposingAccountExists($validator, AccountType::REVENUE, $sourceId, $sourceName, $idField);
|
|
||||||
|
|
||||||
$idField = 'transactions.' . $index . '.destination_id';
|
|
||||||
$nameField = 'transactions.' . $index . '.destination_name';
|
|
||||||
$destinationAccount = $this->assetAccountExists($validator, $destinationId, $destinationName, $idField, $nameField);
|
|
||||||
break;
|
|
||||||
case 'transfer':
|
|
||||||
$idField = 'transactions.' . $index . '.source_id';
|
|
||||||
$nameField = 'transactions.' . $index . '.source_name';
|
|
||||||
$sourceAccount = $this->assetAccountExists($validator, $sourceId, $sourceName, $idField, $nameField);
|
|
||||||
|
|
||||||
$idField = 'transactions.' . $index . '.destination_id';
|
|
||||||
$nameField = 'transactions.' . $index . '.destination_name';
|
|
||||||
$destinationAccount = $this->assetAccountExists($validator, $destinationId, $destinationName, $idField, $nameField);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
$validator->errors()->add($idField, trans('validation.invalid_account_info'));
|
|
||||||
|
|
||||||
return;
|
|
||||||
|
|
||||||
}
|
|
||||||
// add some errors in case of same account submitted:
|
|
||||||
if (null !== $sourceAccount && null !== $destinationAccount && $sourceAccount->id === $destinationAccount->id) {
|
|
||||||
$validator->errors()->add($idField, trans('validation.source_equals_destination'));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param Validator $validator
|
|
||||||
*/
|
|
||||||
private function validRepeatsUntil(Validator $validator): void
|
|
||||||
{
|
|
||||||
$data = $validator->getData();
|
|
||||||
$repetitions = $data['nr_of_repetitions'] ?? null;
|
|
||||||
$repeatUntil = $data['repeat_until'] ?? null;
|
|
||||||
if (null !== $repetitions && null !== $repeatUntil) {
|
|
||||||
// expect a date OR count:
|
|
||||||
$validator->errors()->add('repeat_until', trans('validation.require_repeat_until'));
|
|
||||||
$validator->errors()->add('nr_of_repetitions', trans('validation.require_repeat_until'));
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* TODO merge this in a rule somehow.
|
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
*/
|
|
||||||
private function validRepetitionMoment(Validator $validator): void
|
|
||||||
{
|
|
||||||
$data = $validator->getData();
|
|
||||||
$repetitions = $data['repetitions'] ?? [];
|
|
||||||
/**
|
|
||||||
* @var int $index
|
|
||||||
* @var array $repetition
|
|
||||||
*/
|
|
||||||
foreach ($repetitions as $index => $repetition) {
|
|
||||||
switch ($repetition['type']) {
|
|
||||||
default:
|
|
||||||
$validator->errors()->add(sprintf('repetitions.%d.type', $index), trans('validation.valid_recurrence_rep_type'));
|
|
||||||
|
|
||||||
return;
|
|
||||||
case 'daily':
|
|
||||||
if ('' !== (string)$repetition['moment']) {
|
|
||||||
$validator->errors()->add(sprintf('repetitions.%d.moment', $index), trans('validation.valid_recurrence_rep_moment'));
|
|
||||||
}
|
|
||||||
|
|
||||||
return;
|
|
||||||
case 'monthly':
|
|
||||||
$dayOfMonth = (int)$repetition['moment'];
|
|
||||||
if ($dayOfMonth < 1 || $dayOfMonth > 31) {
|
|
||||||
$validator->errors()->add(sprintf('repetitions.%d.moment', $index), trans('validation.valid_recurrence_rep_moment'));
|
|
||||||
}
|
|
||||||
|
|
||||||
return;
|
|
||||||
case 'ndom':
|
|
||||||
$parameters = explode(',', $repetition['moment']);
|
|
||||||
if (\count($parameters) !== 2) {
|
|
||||||
$validator->errors()->add(sprintf('repetitions.%d.moment', $index), trans('validation.valid_recurrence_rep_moment'));
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
$nthDay = (int)($parameters[0] ?? 0.0);
|
|
||||||
$dayOfWeek = (int)($parameters[1] ?? 0.0);
|
|
||||||
if ($nthDay < 1 || $nthDay > 5) {
|
|
||||||
$validator->errors()->add(sprintf('repetitions.%d.moment', $index), trans('validation.valid_recurrence_rep_moment'));
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
if ($dayOfWeek < 1 || $dayOfWeek > 7) {
|
|
||||||
$validator->errors()->add(sprintf('repetitions.%d.moment', $index), trans('validation.valid_recurrence_rep_moment'));
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
return;
|
|
||||||
case 'weekly':
|
|
||||||
$dayOfWeek = (int)$repetition['moment'];
|
|
||||||
if ($dayOfWeek < 1 || $dayOfWeek > 7) {
|
|
||||||
$validator->errors()->add(sprintf('repetitions.%d.moment', $index), trans('validation.valid_recurrence_rep_moment'));
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 'yearly':
|
|
||||||
try {
|
|
||||||
Carbon::createFromFormat('Y-m-d', $repetition['moment']);
|
|
||||||
} catch (InvalidArgumentException $e) {
|
|
||||||
$validator->errors()->add(sprintf('repetitions.%d.moment', $index), trans('validation.valid_recurrence_rep_moment'));
|
|
||||||
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
@@ -28,6 +28,10 @@ use FireflyIII\Http\Requests\Request as FireflyIIIRequest;
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Class Request.
|
* Class Request.
|
||||||
|
*
|
||||||
|
* Technically speaking this class does not have to be extended like this but who knows what the future brings.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.NumberOfChildren)
|
||||||
*/
|
*/
|
||||||
class Request extends FireflyIIIRequest
|
class Request extends FireflyIIIRequest
|
||||||
{
|
{
|
||||||
|
@@ -33,6 +33,8 @@ use FireflyIII\Models\RuleGroup;
|
|||||||
class RuleGroupRequest extends Request
|
class RuleGroupRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -42,6 +44,8 @@ class RuleGroupRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -54,6 +58,8 @@ class RuleGroupRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -32,6 +32,8 @@ use Illuminate\Validation\Validator;
|
|||||||
class RuleRequest extends Request
|
class RuleRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -41,6 +43,8 @@ class RuleRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -62,14 +66,14 @@ class RuleRequest extends Request
|
|||||||
$data['rule-triggers'][] = [
|
$data['rule-triggers'][] = [
|
||||||
'name' => $trigger['name'],
|
'name' => $trigger['name'],
|
||||||
'value' => $trigger['value'],
|
'value' => $trigger['value'],
|
||||||
'stop-processing' => (int)($trigger['stop-processing'] ?? 0) === 1,
|
'stop-processing' => 1 === (int)($trigger['stop-processing'] ?? 0),
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
foreach ($this->get('rule-actions') as $action) {
|
foreach ($this->get('rule-actions') as $action) {
|
||||||
$data['rule-actions'][] = [
|
$data['rule-actions'][] = [
|
||||||
'name' => $action['name'],
|
'name' => $action['name'],
|
||||||
'value' => $action['value'],
|
'value' => $action['value'],
|
||||||
'stop-processing' => (int)($action['stop-processing'] ?? 0) === 1,
|
'stop-processing' => 1 === (int)($action['stop-processing'] ?? 0),
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -77,6 +81,8 @@ class RuleRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
@@ -134,7 +140,7 @@ class RuleRequest extends Request
|
|||||||
$data = $validator->getData();
|
$data = $validator->getData();
|
||||||
$repetitions = $data['rule-actions'] ?? [];
|
$repetitions = $data['rule-actions'] ?? [];
|
||||||
// need at least one transaction
|
// need at least one transaction
|
||||||
if (\count($repetitions) === 0) {
|
if (0 === \count($repetitions)) {
|
||||||
$validator->errors()->add('title', trans('validation.at_least_one_action'));
|
$validator->errors()->add('title', trans('validation.at_least_one_action'));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -149,7 +155,7 @@ class RuleRequest extends Request
|
|||||||
$data = $validator->getData();
|
$data = $validator->getData();
|
||||||
$repetitions = $data['rule-triggers'] ?? [];
|
$repetitions = $data['rule-triggers'] ?? [];
|
||||||
// need at least one transaction
|
// need at least one transaction
|
||||||
if (\count($repetitions) === 0) {
|
if (0 === \count($repetitions)) {
|
||||||
$validator->errors()->add('title', trans('validation.at_least_one_trigger'));
|
$validator->errors()->add('title', trans('validation.at_least_one_trigger'));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -24,12 +24,8 @@ declare(strict_types=1);
|
|||||||
|
|
||||||
namespace FireflyIII\Api\V1\Requests;
|
namespace FireflyIII\Api\V1\Requests;
|
||||||
|
|
||||||
use FireflyIII\Exceptions\FireflyException;
|
|
||||||
use FireflyIII\Models\Account;
|
|
||||||
use FireflyIII\Models\AccountType;
|
|
||||||
use FireflyIII\Models\Transaction;
|
|
||||||
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
|
|
||||||
use FireflyIII\Rules\BelongsUser;
|
use FireflyIII\Rules\BelongsUser;
|
||||||
|
use FireflyIII\Validation\TransactionValidation;
|
||||||
use Illuminate\Validation\Validator;
|
use Illuminate\Validation\Validator;
|
||||||
|
|
||||||
|
|
||||||
@@ -38,7 +34,11 @@ use Illuminate\Validation\Validator;
|
|||||||
*/
|
*/
|
||||||
class TransactionRequest extends Request
|
class TransactionRequest extends Request
|
||||||
{
|
{
|
||||||
|
use TransactionValidation;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
@@ -48,12 +48,15 @@ class TransactionRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data. Is pretty complex because of all the ??-statements.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.NPathComplexity)
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
{
|
{
|
||||||
$data = [
|
$data = [
|
||||||
// basic fields for journal:
|
|
||||||
'type' => $this->string('type'),
|
'type' => $this->string('type'),
|
||||||
'date' => $this->date('date'),
|
'date' => $this->date('date'),
|
||||||
'description' => $this->string('description'),
|
'description' => $this->string('description'),
|
||||||
@@ -62,8 +65,6 @@ class TransactionRequest extends Request
|
|||||||
'bill_id' => $this->integer('bill_id'),
|
'bill_id' => $this->integer('bill_id'),
|
||||||
'bill_name' => $this->string('bill_name'),
|
'bill_name' => $this->string('bill_name'),
|
||||||
'tags' => explode(',', $this->string('tags')),
|
'tags' => explode(',', $this->string('tags')),
|
||||||
|
|
||||||
// then, custom fields for journal
|
|
||||||
'interest_date' => $this->date('interest_date'),
|
'interest_date' => $this->date('interest_date'),
|
||||||
'book_date' => $this->date('book_date'),
|
'book_date' => $this->date('book_date'),
|
||||||
'process_date' => $this->date('process_date'),
|
'process_date' => $this->date('process_date'),
|
||||||
@@ -72,39 +73,17 @@ class TransactionRequest extends Request
|
|||||||
'invoice_date' => $this->date('invoice_date'),
|
'invoice_date' => $this->date('invoice_date'),
|
||||||
'internal_reference' => $this->string('internal_reference'),
|
'internal_reference' => $this->string('internal_reference'),
|
||||||
'notes' => $this->string('notes'),
|
'notes' => $this->string('notes'),
|
||||||
|
'transactions' => $this->getTransactionData(),
|
||||||
// then, transactions (see below).
|
|
||||||
'transactions' => [],
|
|
||||||
|
|
||||||
];
|
];
|
||||||
foreach ($this->get('transactions') as $index => $transaction) {
|
|
||||||
$array = [
|
|
||||||
'description' => $transaction['description'] ?? null,
|
|
||||||
'amount' => $transaction['amount'],
|
|
||||||
'currency_id' => isset($transaction['currency_id']) ? (int)$transaction['currency_id'] : null,
|
|
||||||
'currency_code' => $transaction['currency_code'] ?? null,
|
|
||||||
'foreign_amount' => $transaction['foreign_amount'] ?? null,
|
|
||||||
'foreign_currency_id' => isset($transaction['foreign_currency_id']) ? (int)$transaction['foreign_currency_id'] : null,
|
|
||||||
'foreign_currency_code' => $transaction['foreign_currency_code'] ?? null,
|
|
||||||
'budget_id' => isset($transaction['budget_id']) ? (int)$transaction['budget_id'] : null,
|
|
||||||
'budget_name' => $transaction['budget_name'] ?? null,
|
|
||||||
'category_id' => isset($transaction['category_id']) ? (int)$transaction['category_id'] : null,
|
|
||||||
'category_name' => $transaction['category_name'] ?? null,
|
|
||||||
'source_id' => isset($transaction['source_id']) ? (int)$transaction['source_id'] : null,
|
|
||||||
'source_name' => isset($transaction['source_name']) ? (string)$transaction['source_name'] : null,
|
|
||||||
'destination_id' => isset($transaction['destination_id']) ? (int)$transaction['destination_id'] : null,
|
|
||||||
'destination_name' => isset($transaction['destination_name']) ? (string)$transaction['destination_name'] : null,
|
|
||||||
'reconciled' => $transaction['reconciled'] ?? false,
|
|
||||||
'identifier' => $index,
|
|
||||||
];
|
|
||||||
$data['transactions'][] = $array;
|
|
||||||
}
|
|
||||||
|
|
||||||
return $data;
|
return $data;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
{
|
{
|
||||||
@@ -149,13 +128,8 @@ class TransactionRequest extends Request
|
|||||||
'transactions.*.destination_name' => 'between:1,255|nullable',
|
'transactions.*.destination_name' => 'between:1,255|nullable',
|
||||||
];
|
];
|
||||||
|
|
||||||
switch ($this->method()) {
|
if ('PUT' === $this->method()) {
|
||||||
default:
|
unset($rules['type'], $rules['piggy_bank_id'], $rules['piggy_bank_name']);
|
||||||
break;
|
|
||||||
case 'PUT':
|
|
||||||
case 'PATCH':
|
|
||||||
unset($rules['type'], $rules['piggy_bank_id'], $rules['piggy_bank_name']);
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return $rules;
|
return $rules;
|
||||||
@@ -174,11 +148,11 @@ class TransactionRequest extends Request
|
|||||||
{
|
{
|
||||||
$validator->after(
|
$validator->after(
|
||||||
function (Validator $validator) {
|
function (Validator $validator) {
|
||||||
$this->atLeastOneTransaction($validator);
|
$this->validateOneTransaction($validator);
|
||||||
$this->checkValidDescriptions($validator);
|
$this->validateDescriptions($validator);
|
||||||
$this->equalToJournalDescription($validator);
|
$this->validateJournalDescription($validator);
|
||||||
$this->emptySplitDescriptions($validator);
|
$this->validateSplitDescriptions($validator);
|
||||||
$this->foreignCurrencyInformation($validator);
|
$this->validateForeignCurrencyInformation($validator);
|
||||||
$this->validateAccountInformation($validator);
|
$this->validateAccountInformation($validator);
|
||||||
$this->validateSplitAccounts($validator);
|
$this->validateSplitAccounts($validator);
|
||||||
}
|
}
|
||||||
@@ -186,335 +160,37 @@ class TransactionRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Throws an error when this asset account is invalid.
|
* Get transaction data.
|
||||||
*
|
*
|
||||||
* @noinspection MoreThanThreeArgumentsInspection
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*
|
* @SuppressWarnings(PHPMD.NPathComplexity)
|
||||||
* @param Validator $validator
|
* @return array
|
||||||
* @param int|null $accountId
|
|
||||||
* @param null|string $accountName
|
|
||||||
* @param string $idField
|
|
||||||
* @param string $nameField
|
|
||||||
*
|
|
||||||
* @return null|Account
|
|
||||||
*/
|
*/
|
||||||
protected function assetAccountExists(Validator $validator, ?int $accountId, ?string $accountName, string $idField, string $nameField): ?Account
|
private function getTransactionData(): array
|
||||||
{
|
{
|
||||||
|
$return = [];
|
||||||
$accountId = (int)$accountId;
|
foreach ($this->get('transactions') as $index => $transaction) {
|
||||||
$accountName = (string)$accountName;
|
$return[] = [
|
||||||
// both empty? hard exit.
|
'description' => $transaction['description'] ?? null,
|
||||||
if ($accountId < 1 && \strlen($accountName) === 0) {
|
'amount' => $transaction['amount'],
|
||||||
$validator->errors()->add($idField, trans('validation.filled', ['attribute' => $idField]));
|
'currency_id' => isset($transaction['currency_id']) ? (int)$transaction['currency_id'] : null,
|
||||||
|
'currency_code' => $transaction['currency_code'] ?? null,
|
||||||
return null;
|
'foreign_amount' => $transaction['foreign_amount'] ?? null,
|
||||||
}
|
'foreign_currency_id' => isset($transaction['foreign_currency_id']) ? (int)$transaction['foreign_currency_id'] : null,
|
||||||
// ID belongs to user and is asset account:
|
'foreign_currency_code' => $transaction['foreign_currency_code'] ?? null,
|
||||||
/** @var AccountRepositoryInterface $repository */
|
'budget_id' => isset($transaction['budget_id']) ? (int)$transaction['budget_id'] : null,
|
||||||
$repository = app(AccountRepositoryInterface::class);
|
'budget_name' => $transaction['budget_name'] ?? null,
|
||||||
$repository->setUser(auth()->user());
|
'category_id' => isset($transaction['category_id']) ? (int)$transaction['category_id'] : null,
|
||||||
$set = $repository->getAccountsById([$accountId]);
|
'category_name' => $transaction['category_name'] ?? null,
|
||||||
if ($set->count() === 1) {
|
'source_id' => isset($transaction['source_id']) ? (int)$transaction['source_id'] : null,
|
||||||
/** @var Account $first */
|
'source_name' => isset($transaction['source_name']) ? (string)$transaction['source_name'] : null,
|
||||||
$first = $set->first();
|
'destination_id' => isset($transaction['destination_id']) ? (int)$transaction['destination_id'] : null,
|
||||||
if ($first->accountType->type !== AccountType::ASSET) {
|
'destination_name' => isset($transaction['destination_name']) ? (string)$transaction['destination_name'] : null,
|
||||||
$validator->errors()->add($idField, trans('validation.belongs_user'));
|
'reconciled' => $transaction['reconciled'] ?? false,
|
||||||
|
'identifier' => $index,
|
||||||
return null;
|
];
|
||||||
}
|
|
||||||
|
|
||||||
// we ignore the account name at this point.
|
|
||||||
return $first;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
$account = $repository->findByName($accountName, [AccountType::ASSET]);
|
return $return;
|
||||||
if (null === $account) {
|
|
||||||
$validator->errors()->add($nameField, trans('validation.belongs_user'));
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
return $account;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Adds an error to the validator when there are no transactions in the array of data.
|
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
*/
|
|
||||||
protected function atLeastOneTransaction(Validator $validator): void
|
|
||||||
{
|
|
||||||
$data = $validator->getData();
|
|
||||||
$transactions = $data['transactions'] ?? [];
|
|
||||||
// need at least one transaction
|
|
||||||
if (\count($transactions) === 0) {
|
|
||||||
$validator->errors()->add('description', trans('validation.at_least_one_transaction'));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Adds an error to the "description" field when the user has submitted no descriptions and no
|
|
||||||
* journal description.
|
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
*/
|
|
||||||
protected function checkValidDescriptions(Validator $validator): void
|
|
||||||
{
|
|
||||||
$data = $validator->getData();
|
|
||||||
$transactions = $data['transactions'] ?? [];
|
|
||||||
$journalDescription = (string)($data['description'] ?? '');
|
|
||||||
$validDescriptions = 0;
|
|
||||||
foreach ($transactions as $index => $transaction) {
|
|
||||||
if (\strlen((string)($transaction['description'] ?? '')) > 0) {
|
|
||||||
$validDescriptions++;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// no valid descriptions and empty journal description? error.
|
|
||||||
if ($validDescriptions === 0 && \strlen($journalDescription) === 0) {
|
|
||||||
$validator->errors()->add('description', trans('validation.filled', ['attribute' => trans('validation.attributes.description')]));
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Adds an error to the validator when the user submits a split transaction (more than 1 transactions)
|
|
||||||
* but does not give them a description.
|
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
*/
|
|
||||||
protected function emptySplitDescriptions(Validator $validator): void
|
|
||||||
{
|
|
||||||
$data = $validator->getData();
|
|
||||||
$transactions = $data['transactions'] ?? [];
|
|
||||||
foreach ($transactions as $index => $transaction) {
|
|
||||||
$description = (string)($transaction['description'] ?? '');
|
|
||||||
// filled description is mandatory for split transactions.
|
|
||||||
if (\count($transactions) > 1 && \strlen($description) === 0) {
|
|
||||||
$validator->errors()->add(
|
|
||||||
'transactions.' . $index . '.description',
|
|
||||||
trans('validation.filled', ['attribute' => trans('validation.attributes.transaction_description')])
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Adds an error to the validator when any transaction descriptions are equal to the journal description.
|
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
*/
|
|
||||||
protected function equalToJournalDescription(Validator $validator): void
|
|
||||||
{
|
|
||||||
$data = $validator->getData();
|
|
||||||
$transactions = $data['transactions'] ?? [];
|
|
||||||
$journalDescription = (string)($data['description'] ?? '');
|
|
||||||
foreach ($transactions as $index => $transaction) {
|
|
||||||
$description = (string)($transaction['description'] ?? '');
|
|
||||||
// description cannot be equal to journal description.
|
|
||||||
if ($description === $journalDescription) {
|
|
||||||
$validator->errors()->add('transactions.' . $index . '.description', trans('validation.equal_description'));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* TODO can be made a rule?
|
|
||||||
*
|
|
||||||
* If the transactions contain foreign amounts, there must also be foreign currency information.
|
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
*/
|
|
||||||
protected function foreignCurrencyInformation(Validator $validator): void
|
|
||||||
{
|
|
||||||
$data = $validator->getData();
|
|
||||||
$transactions = $data['transactions'] ?? [];
|
|
||||||
foreach ($transactions as $index => $transaction) {
|
|
||||||
// must have currency info.
|
|
||||||
if (isset($transaction['foreign_amount'])
|
|
||||||
&& !(isset($transaction['foreign_currency_id'])
|
|
||||||
|| isset($transaction['foreign_currency_code']))) {
|
|
||||||
$validator->errors()->add(
|
|
||||||
'transactions.' . $index . '.foreign_amount',
|
|
||||||
trans('validation.require_currency_info')
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Throws an error when the given opposing account (of type $type) is invalid.
|
|
||||||
* Empty data is allowed, system will default to cash.
|
|
||||||
*
|
|
||||||
* @noinspection MoreThanThreeArgumentsInspection
|
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
* @param string $type
|
|
||||||
* @param int|null $accountId
|
|
||||||
* @param null|string $accountName
|
|
||||||
* @param string $idField
|
|
||||||
*
|
|
||||||
* @return null|Account
|
|
||||||
*/
|
|
||||||
protected function opposingAccountExists(Validator $validator, string $type, ?int $accountId, ?string $accountName, string $idField): ?Account
|
|
||||||
{
|
|
||||||
$accountId = (int)$accountId;
|
|
||||||
$accountName = (string)$accountName;
|
|
||||||
// both empty? done!
|
|
||||||
if ($accountId < 1 && \strlen($accountName) === 0) {
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
if ($accountId !== 0) {
|
|
||||||
// ID belongs to user and is $type account:
|
|
||||||
/** @var AccountRepositoryInterface $repository */
|
|
||||||
$repository = app(AccountRepositoryInterface::class);
|
|
||||||
$repository->setUser(auth()->user());
|
|
||||||
$set = $repository->getAccountsById([$accountId]);
|
|
||||||
if ($set->count() === 1) {
|
|
||||||
/** @var Account $first */
|
|
||||||
$first = $set->first();
|
|
||||||
if ($first->accountType->type !== $type) {
|
|
||||||
$validator->errors()->add($idField, trans('validation.belongs_user'));
|
|
||||||
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
// we ignore the account name at this point.
|
|
||||||
return $first;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// not having an opposing account by this name is NOT a problem.
|
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Validates the given account information. Switches on given transaction type.
|
|
||||||
*
|
|
||||||
* @param Validator $validator
|
|
||||||
*
|
|
||||||
* @throws FireflyException
|
|
||||||
*/
|
|
||||||
protected function validateAccountInformation(Validator $validator): void
|
|
||||||
{
|
|
||||||
$data = $validator->getData();
|
|
||||||
$transactions = $data['transactions'] ?? [];
|
|
||||||
if (!isset($data['type'])) {
|
|
||||||
// the journal may exist in the request:
|
|
||||||
/** @var Transaction $transaction */
|
|
||||||
$transaction = $this->route()->parameter('transaction');
|
|
||||||
if (null === $transaction) {
|
|
||||||
return; // @codeCoverageIgnore
|
|
||||||
}
|
|
||||||
$data['type'] = strtolower($transaction->transactionJournal->transactionType->type);
|
|
||||||
}
|
|
||||||
foreach ($transactions as $index => $transaction) {
|
|
||||||
$sourceId = isset($transaction['source_id']) ? (int)$transaction['source_id'] : null;
|
|
||||||
$sourceName = $transaction['source_name'] ?? null;
|
|
||||||
$destinationId = isset($transaction['destination_id']) ? (int)$transaction['destination_id'] : null;
|
|
||||||
$destinationName = $transaction['destination_name'] ?? null;
|
|
||||||
$sourceAccount = null;
|
|
||||||
$destinationAccount = null;
|
|
||||||
switch ($data['type']) {
|
|
||||||
case 'withdrawal':
|
|
||||||
$idField = 'transactions.' . $index . '.source_id';
|
|
||||||
$nameField = 'transactions.' . $index . '.source_name';
|
|
||||||
$sourceAccount = $this->assetAccountExists($validator, $sourceId, $sourceName, $idField, $nameField);
|
|
||||||
$idField = 'transactions.' . $index . '.destination_id';
|
|
||||||
$destinationAccount = $this->opposingAccountExists($validator, AccountType::EXPENSE, $destinationId, $destinationName, $idField);
|
|
||||||
break;
|
|
||||||
case 'deposit':
|
|
||||||
$idField = 'transactions.' . $index . '.source_id';
|
|
||||||
$sourceAccount = $this->opposingAccountExists($validator, AccountType::REVENUE, $sourceId, $sourceName, $idField);
|
|
||||||
|
|
||||||
$idField = 'transactions.' . $index . '.destination_id';
|
|
||||||
$nameField = 'transactions.' . $index . '.destination_name';
|
|
||||||
$destinationAccount = $this->assetAccountExists($validator, $destinationId, $destinationName, $idField, $nameField);
|
|
||||||
break;
|
|
||||||
case 'transfer':
|
|
||||||
$idField = 'transactions.' . $index . '.source_id';
|
|
||||||
$nameField = 'transactions.' . $index . '.source_name';
|
|
||||||
$sourceAccount = $this->assetAccountExists($validator, $sourceId, $sourceName, $idField, $nameField);
|
|
||||||
|
|
||||||
$idField = 'transactions.' . $index . '.destination_id';
|
|
||||||
$nameField = 'transactions.' . $index . '.destination_name';
|
|
||||||
$destinationAccount = $this->assetAccountExists($validator, $destinationId, $destinationName, $idField, $nameField);
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
// @codeCoverageIgnoreStart
|
|
||||||
throw new FireflyException(
|
|
||||||
sprintf('The validator cannot handle transaction type "%s" in validateAccountInformation().', $data['type'])
|
|
||||||
);
|
|
||||||
// @codeCoverageIgnoreEnd
|
|
||||||
|
|
||||||
}
|
|
||||||
// add some errors in case of same account submitted:
|
|
||||||
if (null !== $sourceAccount && null !== $destinationAccount && $sourceAccount->id === $destinationAccount->id) {
|
|
||||||
$validator->errors()->add($idField, trans('validation.source_equals_destination'));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param Validator $validator
|
|
||||||
*
|
|
||||||
* @throws FireflyException
|
|
||||||
*/
|
|
||||||
protected function validateSplitAccounts(Validator $validator): void
|
|
||||||
{
|
|
||||||
$data = $validator->getData();
|
|
||||||
$count = isset($data['transactions']) ? \count($data['transactions']) : 0;
|
|
||||||
if ($count < 2) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
// this is pretty much impossible:
|
|
||||||
// @codeCoverageIgnoreStart
|
|
||||||
if (!isset($data['type'])) {
|
|
||||||
// the journal may exist in the request:
|
|
||||||
/** @var Transaction $transaction */
|
|
||||||
$transaction = $this->route()->parameter('transaction');
|
|
||||||
if (null === $transaction) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
$data['type'] = strtolower($transaction->transactionJournal->transactionType->type);
|
|
||||||
}
|
|
||||||
// @codeCoverageIgnoreEnd
|
|
||||||
|
|
||||||
// collect all source ID's and destination ID's, if present:
|
|
||||||
$sources = [];
|
|
||||||
$destinations = [];
|
|
||||||
|
|
||||||
foreach ($data['transactions'] as $transaction) {
|
|
||||||
$sources[] = isset($transaction['source_id']) ? (int)$transaction['source_id'] : 0;
|
|
||||||
$destinations[] = isset($transaction['destination_id']) ? (int)$transaction['destination_id'] : 0;
|
|
||||||
}
|
|
||||||
$destinations = array_unique($destinations);
|
|
||||||
$sources = array_unique($sources);
|
|
||||||
// switch on type:
|
|
||||||
switch ($data['type']) {
|
|
||||||
case 'withdrawal':
|
|
||||||
if (\count($sources) > 1) {
|
|
||||||
$validator->errors()->add('transactions.0.source_id', trans('validation.all_accounts_equal'));
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 'deposit':
|
|
||||||
if (\count($destinations) > 1) {
|
|
||||||
$validator->errors()->add('transactions.0.destination_id', trans('validation.all_accounts_equal'));
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 'transfer':
|
|
||||||
if (\count($sources) > 1 || \count($destinations) > 1) {
|
|
||||||
$validator->errors()->add('transactions.0.source_id', trans('validation.all_accounts_equal'));
|
|
||||||
$validator->errors()->add('transactions.0.destination_id', trans('validation.all_accounts_equal'));
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
default:
|
|
||||||
// @codeCoverageIgnoreStart
|
|
||||||
throw new FireflyException(
|
|
||||||
sprintf('The validator cannot handle transaction type "%s" in validateSplitAccounts().', $data['type'])
|
|
||||||
);
|
|
||||||
// @codeCoverageIgnoreEnd
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@@ -24,6 +24,7 @@ declare(strict_types=1);
|
|||||||
|
|
||||||
namespace FireflyIII\Api\V1\Requests;
|
namespace FireflyIII\Api\V1\Requests;
|
||||||
|
|
||||||
|
use FireflyIII\Repositories\User\UserRepositoryInterface;
|
||||||
use FireflyIII\User;
|
use FireflyIII\User;
|
||||||
|
|
||||||
|
|
||||||
@@ -33,24 +34,32 @@ use FireflyIII\User;
|
|||||||
class UserRequest extends Request
|
class UserRequest extends Request
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Authorize logged in users.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function authorize(): bool
|
public function authorize(): bool
|
||||||
{
|
{
|
||||||
|
$result = false;
|
||||||
// Only allow authenticated users
|
// Only allow authenticated users
|
||||||
if (!auth()->check()) {
|
if (auth()->check()) {
|
||||||
return false; // @codeCoverageIgnore
|
/** @var User $user */
|
||||||
}
|
$user = auth()->user();
|
||||||
/** @var User $user */
|
|
||||||
$user = auth()->user();
|
/** @var UserRepositoryInterface $repository */
|
||||||
if (!$user->hasRole('owner')) {
|
$repository = app(UserRepositoryInterface::class);
|
||||||
return false; // @codeCoverageIgnore
|
|
||||||
|
if ($repository->hasRole($user, 'owner')) {
|
||||||
|
$result = true; // @codeCoverageIgnore
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return true;
|
return $result;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all data from the request.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function getAll(): array
|
public function getAll(): array
|
||||||
@@ -65,6 +74,8 @@ class UserRequest extends Request
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* The rules that the incoming request must be matched against.
|
||||||
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
public function rules(): array
|
public function rules(): array
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* CreateExport.php
|
* CreateExport.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -20,6 +19,8 @@
|
|||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Console\Commands;
|
namespace FireflyIII\Console\Commands;
|
||||||
@@ -42,6 +43,7 @@ use Storage;
|
|||||||
class CreateExport extends Command
|
class CreateExport extends Command
|
||||||
{
|
{
|
||||||
use VerifiesAccessToken;
|
use VerifiesAccessToken;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* The console command description.
|
* The console command description.
|
||||||
*
|
*
|
||||||
@@ -64,9 +66,11 @@ class CreateExport extends Command
|
|||||||
/**
|
/**
|
||||||
* Execute the console command.
|
* Execute the console command.
|
||||||
*
|
*
|
||||||
* @return mixed
|
* @return int
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
*/
|
*/
|
||||||
public function handle()
|
public function handle(): int
|
||||||
{
|
{
|
||||||
if (!$this->verifyAccessToken()) {
|
if (!$this->verifyAccessToken()) {
|
||||||
$this->error('Invalid access token.');
|
$this->error('Invalid access token.');
|
||||||
@@ -86,6 +90,9 @@ class CreateExport extends Command
|
|||||||
|
|
||||||
// set user
|
// set user
|
||||||
$user = $userRepository->findNull((int)$this->option('user'));
|
$user = $userRepository->findNull((int)$this->option('user'));
|
||||||
|
if (null === $user) {
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
$jobRepository->setUser($user);
|
$jobRepository->setUser($user);
|
||||||
$journalRepository->setUser($user);
|
$journalRepository->setUser($user);
|
||||||
$accountRepository->setUser($user);
|
$accountRepository->setUser($user);
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* CreateImport.php
|
* CreateImport.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -20,6 +19,8 @@
|
|||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Console\Commands;
|
namespace FireflyIII\Console\Commands;
|
||||||
@@ -81,10 +82,15 @@ class CreateImport extends Command
|
|||||||
$configuration = (string)$this->argument('configuration');
|
$configuration = (string)$this->argument('configuration');
|
||||||
$user = $userRepository->findNull((int)$this->option('user'));
|
$user = $userRepository->findNull((int)$this->option('user'));
|
||||||
$cwd = getcwd();
|
$cwd = getcwd();
|
||||||
$type = strtolower((string)$this->option('type'));
|
|
||||||
$provider = strtolower((string)$this->option('provider'));
|
$provider = strtolower((string)$this->option('provider'));
|
||||||
$configurationData = [];
|
$configurationData = [];
|
||||||
|
|
||||||
|
if (null === $user) {
|
||||||
|
$this->errorLine('User is NULL.');
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
if (!$this->validArguments()) {
|
if (!$this->validArguments()) {
|
||||||
$this->errorLine('Invalid arguments.');
|
$this->errorLine('Invalid arguments.');
|
||||||
|
|
||||||
@@ -182,7 +188,7 @@ class CreateImport extends Command
|
|||||||
}
|
}
|
||||||
$count++;
|
$count++;
|
||||||
}
|
}
|
||||||
if ($importJob->status === 'provider_finished') {
|
if ('provider_finished' === $importJob->status) {
|
||||||
$this->infoLine('Import has finished. Please wait for storage of data.');
|
$this->infoLine('Import has finished. Please wait for storage of data.');
|
||||||
// set job to be storing data:
|
// set job to be storing data:
|
||||||
$jobRepository->setStatus($importJob, 'storing_data');
|
$jobRepository->setStatus($importJob, 'storing_data');
|
||||||
@@ -274,19 +280,19 @@ class CreateImport extends Command
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($provider === 'file' && !\in_array($type, $validTypes, true)) {
|
if ('file' === $provider && !\in_array($type, $validTypes, true)) {
|
||||||
$this->errorLine(sprintf('Cannot import file of type "%s"', $type));
|
$this->errorLine(sprintf('Cannot import file of type "%s"', $type));
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($provider === 'file' && !file_exists($file)) {
|
if ('file' === $provider && !file_exists($file)) {
|
||||||
$this->errorLine(sprintf('Firefly III cannot find file "%s" (working directory: "%s").', $file, $cwd));
|
$this->errorLine(sprintf('Firefly III cannot find file "%s" (working directory: "%s").', $file, $cwd));
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($provider === 'file' && !file_exists($configuration)) {
|
if ('file' === $provider && !file_exists($configuration)) {
|
||||||
$this->errorLine(sprintf('Firefly III cannot find configuration file "%s" (working directory: "%s").', $configuration, $cwd));
|
$this->errorLine(sprintf('Firefly III cannot find configuration file "%s" (working directory: "%s").', $configuration, $cwd));
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* DecryptAttachment.php
|
* DecryptAttachment.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -20,6 +19,8 @@
|
|||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Console\Commands;
|
namespace FireflyIII\Console\Commands;
|
||||||
@@ -51,11 +52,12 @@ class DecryptAttachment extends Command
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Execute the console command.
|
* Execute the console command.
|
||||||
*
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
* @SuppressWarnings(PHPMD.CyclomaticComplexity) // it's five its fine.
|
|
||||||
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
|
*
|
||||||
|
* @return int
|
||||||
*/
|
*/
|
||||||
public function handle()
|
public function handle(): int
|
||||||
{
|
{
|
||||||
/** @var AttachmentRepositoryInterface $repository */
|
/** @var AttachmentRepositoryInterface $repository */
|
||||||
$repository = app(AttachmentRepositoryInterface::class);
|
$repository = app(AttachmentRepositoryInterface::class);
|
||||||
@@ -67,28 +69,28 @@ class DecryptAttachment extends Command
|
|||||||
$this->error(sprintf('No attachment with id #%d', $attachmentId));
|
$this->error(sprintf('No attachment with id #%d', $attachmentId));
|
||||||
Log::error(sprintf('DecryptAttachment: No attachment with id #%d', $attachmentId));
|
Log::error(sprintf('DecryptAttachment: No attachment with id #%d', $attachmentId));
|
||||||
|
|
||||||
return;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($attachmentName !== $attachment->filename) {
|
if ($attachmentName !== $attachment->filename) {
|
||||||
$this->error('File name does not match.');
|
$this->error('File name does not match.');
|
||||||
Log::error('DecryptAttachment: File name does not match.');
|
Log::error('DecryptAttachment: File name does not match.');
|
||||||
|
|
||||||
return;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!is_dir($storagePath)) {
|
if (!is_dir($storagePath)) {
|
||||||
$this->error(sprintf('Path "%s" is not a directory.', $storagePath));
|
$this->error(sprintf('Path "%s" is not a directory.', $storagePath));
|
||||||
Log::error(sprintf('DecryptAttachment: Path "%s" is not a directory.', $storagePath));
|
Log::error(sprintf('DecryptAttachment: Path "%s" is not a directory.', $storagePath));
|
||||||
|
|
||||||
return;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!is_writable($storagePath)) {
|
if (!is_writable($storagePath)) {
|
||||||
$this->error(sprintf('Path "%s" is not writable.', $storagePath));
|
$this->error(sprintf('Path "%s" is not writable.', $storagePath));
|
||||||
Log::error(sprintf('DecryptAttachment: Path "%s" is not writable.', $storagePath));
|
Log::error(sprintf('DecryptAttachment: Path "%s" is not writable.', $storagePath));
|
||||||
|
|
||||||
return;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
$fullPath = $storagePath . DIRECTORY_SEPARATOR . $attachment->filename;
|
$fullPath = $storagePath . DIRECTORY_SEPARATOR . $attachment->filename;
|
||||||
@@ -98,9 +100,10 @@ class DecryptAttachment extends Command
|
|||||||
if (false === $result) {
|
if (false === $result) {
|
||||||
$this->error('Could not write to file.');
|
$this->error('Could not write to file.');
|
||||||
|
|
||||||
return;
|
return 1;
|
||||||
}
|
}
|
||||||
$this->info(sprintf('%d bytes written. Exiting now..', $result));
|
$this->info(sprintf('%d bytes written. Exiting now..', $result));
|
||||||
|
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* EncryptFile.php
|
* EncryptFile.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Import.php
|
* Import.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -20,6 +19,9 @@
|
|||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
/** @noinspection PhpDynamicAsStaticMethodCallInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Console\Commands;
|
namespace FireflyIII\Console\Commands;
|
||||||
@@ -27,8 +29,8 @@ namespace FireflyIII\Console\Commands;
|
|||||||
use FireflyIII\Exceptions\FireflyException;
|
use FireflyIII\Exceptions\FireflyException;
|
||||||
use FireflyIII\Import\Routine\RoutineInterface;
|
use FireflyIII\Import\Routine\RoutineInterface;
|
||||||
use FireflyIII\Models\ImportJob;
|
use FireflyIII\Models\ImportJob;
|
||||||
|
use FireflyIII\Models\Tag;
|
||||||
use Illuminate\Console\Command;
|
use Illuminate\Console\Command;
|
||||||
use Illuminate\Support\MessageBag;
|
|
||||||
use Log;
|
use Log;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -52,10 +54,12 @@ class Import extends Command
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Run the import routine.
|
* Run the import routine.
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
*
|
*
|
||||||
* @throws FireflyException
|
* @throws FireflyException
|
||||||
*/
|
*/
|
||||||
public function handle()
|
public function handle(): void
|
||||||
{
|
{
|
||||||
Log::debug('Start start-import command');
|
Log::debug('Start start-import command');
|
||||||
$jobKey = $this->argument('key');
|
$jobKey = $this->argument('key');
|
||||||
@@ -83,21 +87,30 @@ class Import extends Command
|
|||||||
|
|
||||||
/** @var RoutineInterface $routine */
|
/** @var RoutineInterface $routine */
|
||||||
$routine = app($className);
|
$routine = app($className);
|
||||||
$routine->setJob($job);
|
$routine->setImportJob($job);
|
||||||
$routine->run();
|
$routine->run();
|
||||||
|
|
||||||
/** @var MessageBag $error */
|
/**
|
||||||
foreach ($routine->getErrors() as $index => $error) {
|
* @var int $index
|
||||||
|
* @var string $error
|
||||||
|
*/
|
||||||
|
foreach ($job->errors as $index => $error) {
|
||||||
$this->errorLine(sprintf('Error importing line #%d: %s', $index, $error));
|
$this->errorLine(sprintf('Error importing line #%d: %s', $index, $error));
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->infoLine(
|
/** @var Tag $tag */
|
||||||
sprintf('The import has finished. %d transactions have been imported out of %d records.', $routine->getJournals()->count(), $routine->getLines())
|
$tag = $job->tag()->first();
|
||||||
);
|
$count = 0;
|
||||||
|
if (null === $tag) {
|
||||||
|
$count = $tag->transactionJournals()->count();
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->infoLine(sprintf('The import has finished. %d transactions have been imported.', $count));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Displays an error.
|
||||||
|
*
|
||||||
* @param string $message
|
* @param string $message
|
||||||
* @param array|null $data
|
* @param array|null $data
|
||||||
*/
|
*/
|
||||||
@@ -109,6 +122,8 @@ class Import extends Command
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Displays an informational message.
|
||||||
|
*
|
||||||
* @param string $message
|
* @param string $message
|
||||||
* @param array $data
|
* @param array $data
|
||||||
*/
|
*/
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* ScanAttachments.php
|
* ScanAttachments.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -20,6 +19,8 @@
|
|||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection PhpDynamicAsStaticMethodCallInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Console\Commands;
|
namespace FireflyIII\Console\Commands;
|
||||||
@@ -53,7 +54,7 @@ class ScanAttachments extends Command
|
|||||||
/**
|
/**
|
||||||
* Execute the console command.
|
* Execute the console command.
|
||||||
*/
|
*/
|
||||||
public function handle()
|
public function handle(): void
|
||||||
{
|
{
|
||||||
$attachments = Attachment::get();
|
$attachments = Attachment::get();
|
||||||
$disk = Storage::disk('upload');
|
$disk = Storage::disk('upload');
|
||||||
@@ -63,13 +64,13 @@ class ScanAttachments extends Command
|
|||||||
try {
|
try {
|
||||||
$content = $disk->get($fileName);
|
$content = $disk->get($fileName);
|
||||||
} catch (FileNotFoundException $e) {
|
} catch (FileNotFoundException $e) {
|
||||||
$this->error(sprintf('Could not find data for attachment #%d', $attachment->id));
|
$this->error(sprintf('Could not find data for attachment #%d: %s', $attachment->id, $e->getMessage()));
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
try {
|
try {
|
||||||
$decrypted = Crypt::decrypt($content);
|
$decrypted = Crypt::decrypt($content);
|
||||||
} catch (DecryptException $e) {
|
} catch (DecryptException $e) {
|
||||||
$this->error(sprintf('Could not decrypt data of attachment #%d', $attachment->id));
|
$this->error(sprintf('Could not decrypt data of attachment #%d: %s', $attachment->id, $e->getMessage()));
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
$tmpfname = tempnam(sys_get_temp_dir(), 'FireflyIII');
|
$tmpfname = tempnam(sys_get_temp_dir(), 'FireflyIII');
|
||||||
|
@@ -20,6 +20,10 @@
|
|||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
/** @noinspection PhpStaticAsDynamicMethodCallInspection */
|
||||||
|
/** @noinspection PhpDynamicAsStaticMethodCallInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Console\Commands;
|
namespace FireflyIII\Console\Commands;
|
||||||
@@ -42,7 +46,9 @@ use FireflyIII\Models\TransactionCurrency;
|
|||||||
use FireflyIII\Models\TransactionJournal;
|
use FireflyIII\Models\TransactionJournal;
|
||||||
use FireflyIII\Models\TransactionJournalMeta;
|
use FireflyIII\Models\TransactionJournalMeta;
|
||||||
use FireflyIII\Models\TransactionType;
|
use FireflyIII\Models\TransactionType;
|
||||||
|
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
|
||||||
use FireflyIII\Repositories\Currency\CurrencyRepositoryInterface;
|
use FireflyIII\Repositories\Currency\CurrencyRepositoryInterface;
|
||||||
|
use FireflyIII\Repositories\Journal\JournalRepositoryInterface;
|
||||||
use FireflyIII\User;
|
use FireflyIII\User;
|
||||||
use Illuminate\Console\Command;
|
use Illuminate\Console\Command;
|
||||||
use Illuminate\Database\QueryException;
|
use Illuminate\Database\QueryException;
|
||||||
@@ -50,14 +56,14 @@ use Illuminate\Support\Collection;
|
|||||||
use Log;
|
use Log;
|
||||||
use Preferences;
|
use Preferences;
|
||||||
use Schema;
|
use Schema;
|
||||||
|
use UnexpectedValueException;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class UpgradeDatabase.
|
* Class UpgradeDatabase.
|
||||||
*
|
*
|
||||||
* Upgrade user database.
|
* Upgrade user database.
|
||||||
*
|
* @SuppressWarnings(PHPMD.ExcessiveClassComplexity)
|
||||||
*
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
* @SuppressWarnings(PHPMD.CouplingBetweenObjects) // it just touches a lot of things.
|
|
||||||
*/
|
*/
|
||||||
class UpgradeDatabase extends Command
|
class UpgradeDatabase extends Command
|
||||||
{
|
{
|
||||||
@@ -77,7 +83,7 @@ class UpgradeDatabase extends Command
|
|||||||
/**
|
/**
|
||||||
* Execute the console command.
|
* Execute the console command.
|
||||||
*/
|
*/
|
||||||
public function handle()
|
public function handle(): void
|
||||||
{
|
{
|
||||||
$this->setTransactionIdentifier();
|
$this->setTransactionIdentifier();
|
||||||
$this->updateAccountCurrencies();
|
$this->updateAccountCurrencies();
|
||||||
@@ -93,7 +99,14 @@ class UpgradeDatabase extends Command
|
|||||||
$this->info('Firefly III database is up to date.');
|
$this->info('Firefly III database is up to date.');
|
||||||
}
|
}
|
||||||
|
|
||||||
public function migrateBillsToRules()
|
/**
|
||||||
|
* Since it is one routine these warnings make sense and should be supressed.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
|
* @SuppressWarnings(PHPMD.NPathComplexity)
|
||||||
|
*/
|
||||||
|
public function migrateBillsToRules(): void
|
||||||
{
|
{
|
||||||
foreach (User::get() as $user) {
|
foreach (User::get() as $user) {
|
||||||
/** @var Preference $lang */
|
/** @var Preference $lang */
|
||||||
@@ -101,12 +114,20 @@ class UpgradeDatabase extends Command
|
|||||||
$groupName = (string)trans('firefly.rulegroup_for_bills_title', [], $lang->data);
|
$groupName = (string)trans('firefly.rulegroup_for_bills_title', [], $lang->data);
|
||||||
$ruleGroup = $user->ruleGroups()->where('title', $groupName)->first();
|
$ruleGroup = $user->ruleGroups()->where('title', $groupName)->first();
|
||||||
$currencyPreference = Preferences::getForUser($user, 'currencyPreference', config('firefly.default_currency', 'EUR'));
|
$currencyPreference = Preferences::getForUser($user, 'currencyPreference', config('firefly.default_currency', 'EUR'));
|
||||||
$currency = TransactionCurrency::where('code', $currencyPreference->data)->first();
|
|
||||||
|
if (null === $currencyPreference) {
|
||||||
|
$this->error('User has no currency preference. Impossible.');
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
$currency = TransactionCurrency::where('code', $currencyPreference->data)->first();
|
||||||
if (null === $currency) {
|
if (null === $currency) {
|
||||||
|
$this->line('Fall back to default currency in migrateBillsToRules().');
|
||||||
$currency = app('amount')->getDefaultCurrency();
|
$currency = app('amount')->getDefaultCurrency();
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($ruleGroup === null) {
|
if (null === $ruleGroup) {
|
||||||
$array = RuleGroup::get(['order'])->pluck('order')->toArray();
|
$array = RuleGroup::get(['order'])->pluck('order')->toArray();
|
||||||
$order = \count($array) > 0 ? max($array) + 1 : 1;
|
$order = \count($array) > 0 ? max($array) + 1 : 1;
|
||||||
$ruleGroup = RuleGroup::create(
|
$ruleGroup = RuleGroup::create(
|
||||||
@@ -126,7 +147,7 @@ class UpgradeDatabase extends Command
|
|||||||
$collection = $user->bills()->get();
|
$collection = $user->bills()->get();
|
||||||
/** @var Bill $bill */
|
/** @var Bill $bill */
|
||||||
foreach ($collection as $bill) {
|
foreach ($collection as $bill) {
|
||||||
if ($bill->match !== 'MIGRATED_TO_RULES') {
|
if ('MIGRATED_TO_RULES' !== $bill->match) {
|
||||||
$rule = Rule::create(
|
$rule = Rule::create(
|
||||||
[
|
[
|
||||||
'user_id' => $user->id,
|
'user_id' => $user->id,
|
||||||
@@ -260,23 +281,29 @@ class UpgradeDatabase extends Command
|
|||||||
/**
|
/**
|
||||||
* Each (asset) account must have a reference to a preferred currency. If the account does not have one, it's forced upon the account.
|
* Each (asset) account must have a reference to a preferred currency. If the account does not have one, it's forced upon the account.
|
||||||
*
|
*
|
||||||
* @SuppressWarnings(PHPMD.CyclomaticComplexity) // it's seven but it can't really be helped.
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
*/
|
*/
|
||||||
public function updateAccountCurrencies(): void
|
public function updateAccountCurrencies(): void
|
||||||
{
|
{
|
||||||
$accounts = Account::leftJoin('account_types', 'account_types.id', '=', 'accounts.account_type_id')
|
$accounts = Account::leftJoin('account_types', 'account_types.id', '=', 'accounts.account_type_id')
|
||||||
->whereIn('account_types.type', [AccountType::DEFAULT, AccountType::ASSET])->get(['accounts.*']);
|
->whereIn('account_types.type', [AccountType::DEFAULT, AccountType::ASSET])->get(['accounts.*']);
|
||||||
|
/** @var AccountRepositoryInterface $repository */
|
||||||
|
$repository = app(AccountRepositoryInterface::class);
|
||||||
$accounts->each(
|
$accounts->each(
|
||||||
function (Account $account) {
|
function (Account $account) use ($repository) {
|
||||||
|
$repository->setUser($account->user);
|
||||||
// get users preference, fall back to system pref.
|
// get users preference, fall back to system pref.
|
||||||
$defaultCurrencyCode = Preferences::getForUser($account->user, 'currencyPreference', config('firefly.default_currency', 'EUR'))->data;
|
$defaultCurrencyCode = Preferences::getForUser($account->user, 'currencyPreference', config('firefly.default_currency', 'EUR'))->data;
|
||||||
$defaultCurrency = TransactionCurrency::where('code', $defaultCurrencyCode)->first();
|
$defaultCurrency = TransactionCurrency::where('code', $defaultCurrencyCode)->first();
|
||||||
$accountCurrency = (int)$account->getMeta('currency_id');
|
$accountCurrency = (int)$repository->getMetaValue($account, 'currency_id');
|
||||||
$openingBalance = $account->getOpeningBalance();
|
$openingBalance = $account->getOpeningBalance();
|
||||||
$obCurrency = (int)$openingBalance->transaction_currency_id;
|
$obCurrency = (int)$openingBalance->transaction_currency_id;
|
||||||
|
|
||||||
|
if (null === $defaultCurrency) {
|
||||||
|
throw new UnexpectedValueException('The default currency is NULL, and this is more or less impossible.');
|
||||||
|
}
|
||||||
|
|
||||||
// both 0? set to default currency:
|
// both 0? set to default currency:
|
||||||
if (0 === $accountCurrency && 0 === $obCurrency) {
|
if (0 === $accountCurrency && 0 === $obCurrency) {
|
||||||
AccountMeta::where('account_id', $account->id)->where('name', 'currency_id')->forceDelete();
|
AccountMeta::where('account_id', $account->id)->where('name', 'currency_id')->forceDelete();
|
||||||
@@ -317,19 +344,22 @@ class UpgradeDatabase extends Command
|
|||||||
* Both source and destination must match the respective currency preference of the related asset account.
|
* Both source and destination must match the respective currency preference of the related asset account.
|
||||||
* So FF3 must verify all transactions.
|
* So FF3 must verify all transactions.
|
||||||
*
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
*/
|
*/
|
||||||
public function updateOtherCurrencies(): void
|
public function updateOtherCurrencies(): void
|
||||||
{
|
{
|
||||||
/** @var CurrencyRepositoryInterface $repository */
|
/** @var CurrencyRepositoryInterface $repository */
|
||||||
$repository = app(CurrencyRepositoryInterface::class);
|
$repository = app(CurrencyRepositoryInterface::class);
|
||||||
$set = TransactionJournal
|
/** @var AccountRepositoryInterface $accountRepos */
|
||||||
|
$accountRepos = app(AccountRepositoryInterface::class);
|
||||||
|
$set = TransactionJournal
|
||||||
::leftJoin('transaction_types', 'transaction_types.id', '=', 'transaction_journals.transaction_type_id')
|
::leftJoin('transaction_types', 'transaction_types.id', '=', 'transaction_journals.transaction_type_id')
|
||||||
->whereIn('transaction_types.type', [TransactionType::WITHDRAWAL, TransactionType::DEPOSIT, TransactionType::OPENING_BALANCE])
|
->whereIn('transaction_types.type', [TransactionType::WITHDRAWAL, TransactionType::DEPOSIT, TransactionType::OPENING_BALANCE])
|
||||||
->get(['transaction_journals.*']);
|
->get(['transaction_journals.*']);
|
||||||
|
|
||||||
$set->each(
|
$set->each(
|
||||||
function (TransactionJournal $journal) use ($repository) {
|
function (TransactionJournal $journal) use ($repository, $accountRepos) {
|
||||||
// get the transaction with the asset account in it:
|
// get the transaction with the asset account in it:
|
||||||
/** @var Transaction $transaction */
|
/** @var Transaction $transaction */
|
||||||
$transaction = $journal->transactions()
|
$transaction = $journal->transactions()
|
||||||
@@ -339,9 +369,13 @@ class UpgradeDatabase extends Command
|
|||||||
if (null === $transaction) {
|
if (null === $transaction) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
$accountRepos->setUser($journal->user);
|
||||||
/** @var Account $account */
|
/** @var Account $account */
|
||||||
$account = $transaction->account;
|
$account = $transaction->account;
|
||||||
$currency = $repository->find((int)$account->getMeta('currency_id'));
|
$currency = $repository->findNull((int)$accountRepos->getMetaValue($account, 'currency_id'));
|
||||||
|
if (null === $currency) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
$transactions = $journal->transactions()->get();
|
$transactions = $journal->transactions()->get();
|
||||||
$transactions->each(
|
$transactions->each(
|
||||||
function (Transaction $transaction) use ($currency) {
|
function (Transaction $transaction) use ($currency) {
|
||||||
@@ -377,7 +411,7 @@ class UpgradeDatabase extends Command
|
|||||||
* Both source and destination must match the respective currency preference. So FF3 must verify ALL
|
* Both source and destination must match the respective currency preference. So FF3 must verify ALL
|
||||||
* transactions.
|
* transactions.
|
||||||
*/
|
*/
|
||||||
public function updateTransferCurrencies()
|
public function updateTransferCurrencies(): void
|
||||||
{
|
{
|
||||||
$set = TransactionJournal
|
$set = TransactionJournal
|
||||||
::leftJoin('transaction_types', 'transaction_types.id', '=', 'transaction_journals.transaction_type_id')
|
::leftJoin('transaction_types', 'transaction_types.id', '=', 'transaction_journals.transaction_type_id')
|
||||||
@@ -449,6 +483,7 @@ class UpgradeDatabase extends Command
|
|||||||
*/
|
*/
|
||||||
private function migrateNotes(): void
|
private function migrateNotes(): void
|
||||||
{
|
{
|
||||||
|
/** @noinspection PhpUndefinedMethodInspection */
|
||||||
$set = TransactionJournalMeta::whereName('notes')->get();
|
$set = TransactionJournalMeta::whereName('notes')->get();
|
||||||
/** @var TransactionJournalMeta $meta */
|
/** @var TransactionJournalMeta $meta */
|
||||||
foreach ($set as $meta) {
|
foreach ($set as $meta) {
|
||||||
@@ -479,8 +514,15 @@ class UpgradeDatabase extends Command
|
|||||||
{
|
{
|
||||||
/** @var CurrencyRepositoryInterface $repository */
|
/** @var CurrencyRepositoryInterface $repository */
|
||||||
$repository = app(CurrencyRepositoryInterface::class);
|
$repository = app(CurrencyRepositoryInterface::class);
|
||||||
$currency = $repository->find((int)$transaction->account->getMeta('currency_id'));
|
/** @var AccountRepositoryInterface $accountRepos */
|
||||||
$journal = $transaction->transactionJournal;
|
$accountRepos = app(AccountRepositoryInterface::class);
|
||||||
|
$accountRepos->setUser($transaction->account->user);
|
||||||
|
$currency = $repository->findNull((int)$accountRepos->getMetaValue($transaction->account, 'currency_id'));
|
||||||
|
$journal = $transaction->transactionJournal;
|
||||||
|
|
||||||
|
if (null === $currency) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
if (!((int)$currency->id === (int)$journal->transaction_currency_id)) {
|
if (!((int)$currency->id === (int)$journal->transaction_currency_id)) {
|
||||||
$this->line(
|
$this->line(
|
||||||
@@ -549,11 +591,11 @@ class UpgradeDatabase extends Command
|
|||||||
*
|
*
|
||||||
* The transaction that is sent to this function MUST be the source transaction (amount negative).
|
* The transaction that is sent to this function MUST be the source transaction (amount negative).
|
||||||
*
|
*
|
||||||
* Method is long and complex bit I'm taking it for granted.
|
* Method is long and complex but I'll allow it. https://imgur.com/gallery/dVDJiez
|
||||||
*
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
* @SuppressWarnings(PHPMD.NPathComplexity)
|
* @SuppressWarnings(PHPMD.NPathComplexity)
|
||||||
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
|
||||||
*
|
*
|
||||||
* @param Transaction $transaction
|
* @param Transaction $transaction
|
||||||
*/
|
*/
|
||||||
@@ -561,7 +603,14 @@ class UpgradeDatabase extends Command
|
|||||||
{
|
{
|
||||||
/** @var CurrencyRepositoryInterface $repository */
|
/** @var CurrencyRepositoryInterface $repository */
|
||||||
$repository = app(CurrencyRepositoryInterface::class);
|
$repository = app(CurrencyRepositoryInterface::class);
|
||||||
$currency = $repository->findNull((int)$transaction->account->getMeta('currency_id'));
|
/** @var AccountRepositoryInterface $accountRepos */
|
||||||
|
$accountRepos = app(AccountRepositoryInterface::class);
|
||||||
|
/** @var JournalRepositoryInterface $journalRepos */
|
||||||
|
$journalRepos = app(JournalRepositoryInterface::class);
|
||||||
|
|
||||||
|
$accountRepos->setUser($transaction->account->user);
|
||||||
|
$journalRepos->setUser($transaction->account->user);
|
||||||
|
$currency = $repository->findNull((int)$accountRepos->getMetaValue($transaction->account, 'currency_id'));
|
||||||
|
|
||||||
if (null === $currency) {
|
if (null === $currency) {
|
||||||
Log::error(sprintf('Account #%d ("%s") must have currency preference but has none.', $transaction->account->id, $transaction->account->name));
|
Log::error(sprintf('Account #%d ("%s") must have currency preference but has none.', $transaction->account->id, $transaction->account->name));
|
||||||
@@ -597,7 +646,7 @@ class UpgradeDatabase extends Command
|
|||||||
$journal = $transaction->transactionJournal;
|
$journal = $transaction->transactionJournal;
|
||||||
/** @var Transaction $opposing */
|
/** @var Transaction $opposing */
|
||||||
$opposing = $journal->transactions()->where('amount', '>', 0)->where('identifier', $transaction->identifier)->first();
|
$opposing = $journal->transactions()->where('amount', '>', 0)->where('identifier', $transaction->identifier)->first();
|
||||||
$opposingCurrency = $repository->findNull((int)$opposing->account->getMeta('currency_id'));
|
$opposingCurrency = $repository->findNull((int)$accountRepos->getMetaValue($opposing->account, 'currency_id'));
|
||||||
|
|
||||||
if (null === $opposingCurrency) {
|
if (null === $opposingCurrency) {
|
||||||
Log::error(sprintf('Account #%d ("%s") must have currency preference but has none.', $opposing->account->id, $opposing->account->name));
|
Log::error(sprintf('Account #%d ("%s") must have currency preference but has none.', $opposing->account->id, $opposing->account->name));
|
||||||
@@ -653,7 +702,7 @@ class UpgradeDatabase extends Command
|
|||||||
|
|
||||||
// when both are zero, try to grab it from journal:
|
// when both are zero, try to grab it from journal:
|
||||||
if (null === $opposing->foreign_amount && null === $transaction->foreign_amount) {
|
if (null === $opposing->foreign_amount && null === $transaction->foreign_amount) {
|
||||||
$foreignAmount = $journal->getMeta('foreign_amount');
|
$foreignAmount = $journalRepos->getMetaField($journal, 'foreign_amount');
|
||||||
if (null === $foreignAmount) {
|
if (null === $foreignAmount) {
|
||||||
Log::debug(sprintf('Journal #%d has missing foreign currency data, forced to do 1:1 conversion :(.', $transaction->transaction_journal_id));
|
Log::debug(sprintf('Journal #%d has missing foreign currency data, forced to do 1:1 conversion :(.', $transaction->transaction_journal_id));
|
||||||
$transaction->foreign_amount = bcmul((string)$transaction->amount, '-1');
|
$transaction->foreign_amount = bcmul((string)$transaction->amount, '-1');
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* UpgradeFireflyInstructions.php
|
* UpgradeFireflyInstructions.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -47,7 +46,7 @@ class UpgradeFireflyInstructions extends Command
|
|||||||
/**
|
/**
|
||||||
* Execute the console command.
|
* Execute the console command.
|
||||||
*/
|
*/
|
||||||
public function handle()
|
public function handle(): void
|
||||||
{
|
{
|
||||||
if ('update' === $this->argument('task')) {
|
if ('update' === $this->argument('task')) {
|
||||||
$this->updateInstructions();
|
$this->updateInstructions();
|
||||||
@@ -62,7 +61,7 @@ class UpgradeFireflyInstructions extends Command
|
|||||||
*
|
*
|
||||||
* @param string $text
|
* @param string $text
|
||||||
*/
|
*/
|
||||||
private function boxed(string $text)
|
private function boxed(string $text): void
|
||||||
{
|
{
|
||||||
$parts = explode("\n", wordwrap($text));
|
$parts = explode("\n", wordwrap($text));
|
||||||
foreach ($parts as $string) {
|
foreach ($parts as $string) {
|
||||||
@@ -75,7 +74,7 @@ class UpgradeFireflyInstructions extends Command
|
|||||||
*
|
*
|
||||||
* @param string $text
|
* @param string $text
|
||||||
*/
|
*/
|
||||||
private function boxedInfo(string $text)
|
private function boxedInfo(string $text): void
|
||||||
{
|
{
|
||||||
$parts = explode("\n", wordwrap($text));
|
$parts = explode("\n", wordwrap($text));
|
||||||
foreach ($parts as $string) {
|
foreach ($parts as $string) {
|
||||||
@@ -86,7 +85,7 @@ class UpgradeFireflyInstructions extends Command
|
|||||||
/**
|
/**
|
||||||
* Render instructions.
|
* Render instructions.
|
||||||
*/
|
*/
|
||||||
private function installInstructions()
|
private function installInstructions(): void
|
||||||
{
|
{
|
||||||
/** @var string $version */
|
/** @var string $version */
|
||||||
$version = config('firefly.version');
|
$version = config('firefly.version');
|
||||||
@@ -94,8 +93,7 @@ class UpgradeFireflyInstructions extends Command
|
|||||||
$text = '';
|
$text = '';
|
||||||
foreach (array_keys($config) as $compare) {
|
foreach (array_keys($config) as $compare) {
|
||||||
// if string starts with:
|
// if string starts with:
|
||||||
$len = \strlen($compare);
|
if (0 === strpos($version, $compare)) {
|
||||||
if (substr($version, 0, $len) === $compare) {
|
|
||||||
$text = $config[$compare];
|
$text = $config[$compare];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -120,7 +118,7 @@ class UpgradeFireflyInstructions extends Command
|
|||||||
/**
|
/**
|
||||||
* Show a line.
|
* Show a line.
|
||||||
*/
|
*/
|
||||||
private function showLine()
|
private function showLine(): void
|
||||||
{
|
{
|
||||||
$line = '+';
|
$line = '+';
|
||||||
for ($i = 0; $i < 78; ++$i) {
|
for ($i = 0; $i < 78; ++$i) {
|
||||||
@@ -133,7 +131,7 @@ class UpgradeFireflyInstructions extends Command
|
|||||||
/**
|
/**
|
||||||
* Render upgrade instructions.
|
* Render upgrade instructions.
|
||||||
*/
|
*/
|
||||||
private function updateInstructions()
|
private function updateInstructions(): void
|
||||||
{
|
{
|
||||||
/** @var string $version */
|
/** @var string $version */
|
||||||
$version = config('firefly.version');
|
$version = config('firefly.version');
|
||||||
@@ -141,8 +139,7 @@ class UpgradeFireflyInstructions extends Command
|
|||||||
$text = '';
|
$text = '';
|
||||||
foreach (array_keys($config) as $compare) {
|
foreach (array_keys($config) as $compare) {
|
||||||
// if string starts with:
|
// if string starts with:
|
||||||
$len = \strlen($compare);
|
if (0 === strpos($version, $compare)) {
|
||||||
if (substr($version, 0, $len) === $compare) {
|
|
||||||
$text = $config[$compare];
|
$text = $config[$compare];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* UseEncryption.php
|
* UseEncryption.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -48,12 +47,12 @@ class UseEncryption extends Command
|
|||||||
/**
|
/**
|
||||||
* Execute the console command.
|
* Execute the console command.
|
||||||
*/
|
*/
|
||||||
public function handle()
|
public function handle(): void
|
||||||
{
|
{
|
||||||
if (config('firefly.encryption') === true) {
|
if (true === config('firefly.encryption')) {
|
||||||
$this->info('Firefly III configuration calls for encrypted data.');
|
$this->info('Firefly III configuration calls for encrypted data.');
|
||||||
}
|
}
|
||||||
if (config('firefly.encryption') === false) {
|
if (false === config('firefly.encryption')) {
|
||||||
$this->info('Firefly III configuration calls for unencrypted data.');
|
$this->info('Firefly III configuration calls for unencrypted data.');
|
||||||
}
|
}
|
||||||
$this->handleObjects('Account', 'name', 'encrypted');
|
$this->handleObjects('Account', 'name', 'encrypted');
|
||||||
@@ -72,18 +71,21 @@ class UseEncryption extends Command
|
|||||||
* @param string $field
|
* @param string $field
|
||||||
* @param string $indicator
|
* @param string $indicator
|
||||||
*/
|
*/
|
||||||
public function handleObjects(string $class, string $field, string $indicator)
|
public function handleObjects(string $class, string $field, string $indicator): void
|
||||||
{
|
{
|
||||||
$fqn = sprintf('FireflyIII\Models\%s', $class);
|
$fqn = sprintf('FireflyIII\Models\%s', $class);
|
||||||
$encrypt = config('firefly.encryption') === true ? 0 : 1;
|
$encrypt = true === config('firefly.encryption') ? 0 : 1;
|
||||||
$set = $fqn::where($indicator, $encrypt)->get();
|
/** @noinspection PhpUndefinedMethodInspection */
|
||||||
|
$set = $fqn::where($indicator, $encrypt)->get();
|
||||||
|
|
||||||
foreach ($set as $entry) {
|
foreach ($set as $entry) {
|
||||||
$newName = $entry->$field;
|
$newName = $entry->$field;
|
||||||
$entry->$field = $newName;
|
$entry->$field = $newName;
|
||||||
|
/** @noinspection PhpUndefinedMethodInspection */
|
||||||
$entry->save();
|
$entry->save();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** @noinspection PhpUndefinedMethodInspection */
|
||||||
$this->line(sprintf('Updated %d %s.', $set->count(), strtolower(Str::plural($class))));
|
$this->line(sprintf('Updated %d %s.', $set->count(), strtolower(Str::plural($class))));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* VerifiesAccessToken.php
|
* VerifiesAccessToken.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* VerifyDatabase.php
|
* VerifyDatabase.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -20,6 +19,8 @@
|
|||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection PhpDynamicAsStaticMethodCallInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Console\Commands;
|
namespace FireflyIII\Console\Commands;
|
||||||
@@ -29,6 +30,7 @@ use DB;
|
|||||||
use FireflyIII\Models\Account;
|
use FireflyIII\Models\Account;
|
||||||
use FireflyIII\Models\AccountType;
|
use FireflyIII\Models\AccountType;
|
||||||
use FireflyIII\Models\Budget;
|
use FireflyIII\Models\Budget;
|
||||||
|
use FireflyIII\Models\Category;
|
||||||
use FireflyIII\Models\LinkType;
|
use FireflyIII\Models\LinkType;
|
||||||
use FireflyIII\Models\PiggyBankEvent;
|
use FireflyIII\Models\PiggyBankEvent;
|
||||||
use FireflyIII\Models\Transaction;
|
use FireflyIII\Models\Transaction;
|
||||||
@@ -39,6 +41,7 @@ use FireflyIII\User;
|
|||||||
use Illuminate\Console\Command;
|
use Illuminate\Console\Command;
|
||||||
use Illuminate\Contracts\Encryption\DecryptException;
|
use Illuminate\Contracts\Encryption\DecryptException;
|
||||||
use Illuminate\Database\Eloquent\Builder;
|
use Illuminate\Database\Eloquent\Builder;
|
||||||
|
use Log;
|
||||||
use Preferences;
|
use Preferences;
|
||||||
use Schema;
|
use Schema;
|
||||||
use stdClass;
|
use stdClass;
|
||||||
@@ -46,6 +49,7 @@ use stdClass;
|
|||||||
/**
|
/**
|
||||||
* Class VerifyDatabase.
|
* Class VerifyDatabase.
|
||||||
*
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveClassComplexity)
|
||||||
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
* @SuppressWarnings(PHPMD.CouplingBetweenObjects)
|
||||||
*/
|
*/
|
||||||
class VerifyDatabase extends Command
|
class VerifyDatabase extends Command
|
||||||
@@ -66,15 +70,15 @@ class VerifyDatabase extends Command
|
|||||||
/**
|
/**
|
||||||
* Execute the console command.
|
* Execute the console command.
|
||||||
*/
|
*/
|
||||||
public function handle()
|
public function handle(): void
|
||||||
{
|
{
|
||||||
// if table does not exist, return false
|
// if table does not exist, return false
|
||||||
if (!Schema::hasTable('users')) {
|
if (!Schema::hasTable('users')) {
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->reportObject('budget');
|
$this->reportEmptyBudgets();
|
||||||
$this->reportObject('category');
|
$this->reportEmptyCategories();
|
||||||
$this->reportObject('tag');
|
$this->reportObject('tag');
|
||||||
$this->reportAccounts();
|
$this->reportAccounts();
|
||||||
$this->reportBudgetLimits();
|
$this->reportBudgetLimits();
|
||||||
@@ -145,9 +149,10 @@ class VerifyDatabase extends Command
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Fix the situation where the matching transactions
|
* Fix the situation where the matching transactions of a journal somehow have non-matching categories or budgets.
|
||||||
* of a journal somehow have non-matching categories
|
*
|
||||||
* or budgets
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
*/
|
*/
|
||||||
private function fixBadMeta(): void
|
private function fixBadMeta(): void
|
||||||
{
|
{
|
||||||
@@ -208,6 +213,12 @@ class VerifyDatabase extends Command
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Makes sure amounts are stored correctly.
|
||||||
|
*
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
|
*/
|
||||||
private function fixDoubleAmounts(): void
|
private function fixDoubleAmounts(): void
|
||||||
{
|
{
|
||||||
$count = 0;
|
$count = 0;
|
||||||
@@ -257,7 +268,7 @@ class VerifyDatabase extends Command
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
* Removes bills from journals that should not have bills.
|
||||||
*/
|
*/
|
||||||
private function removeBills(): void
|
private function removeBills(): void
|
||||||
{
|
{
|
||||||
@@ -305,7 +316,7 @@ class VerifyDatabase extends Command
|
|||||||
/**
|
/**
|
||||||
* Reports on accounts with no transactions.
|
* Reports on accounts with no transactions.
|
||||||
*/
|
*/
|
||||||
private function reportAccounts()
|
private function reportAccounts(): void
|
||||||
{
|
{
|
||||||
$set = Account::leftJoin('transactions', 'transactions.account_id', '=', 'accounts.id')
|
$set = Account::leftJoin('transactions', 'transactions.account_id', '=', 'accounts.id')
|
||||||
->leftJoin('users', 'accounts.user_id', '=', 'users.id')
|
->leftJoin('users', 'accounts.user_id', '=', 'users.id')
|
||||||
@@ -378,6 +389,82 @@ class VerifyDatabase extends Command
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Report on budgets with no transactions or journals.
|
||||||
|
*/
|
||||||
|
private function reportEmptyBudgets(): void
|
||||||
|
{
|
||||||
|
$set = Budget::leftJoin('budget_transaction_journal', 'budgets.id', '=', 'budget_transaction_journal.budget_id')
|
||||||
|
->leftJoin('users', 'budgets.user_id', '=', 'users.id')
|
||||||
|
->distinct()
|
||||||
|
->whereNull('budget_transaction_journal.budget_id')
|
||||||
|
->whereNull('budgets.deleted_at')
|
||||||
|
->get(['budgets.id', 'budgets.name', 'budgets.user_id', 'users.email']);
|
||||||
|
|
||||||
|
/** @var stdClass $entry */
|
||||||
|
foreach ($set as $entry) {
|
||||||
|
$objName = $entry->name;
|
||||||
|
try {
|
||||||
|
$objName = Crypt::decrypt($objName);
|
||||||
|
} catch (DecryptException $e) {
|
||||||
|
// it probably was not encrypted.
|
||||||
|
Log::debug(sprintf('Not a problem: %s', $e->getMessage()));
|
||||||
|
}
|
||||||
|
|
||||||
|
// also count the transactions:
|
||||||
|
$countTransactions = DB::table('budget_transaction')->where('budget_id', $entry->id)->count();
|
||||||
|
|
||||||
|
if (0 === $countTransactions) {
|
||||||
|
$line = sprintf(
|
||||||
|
'User #%d (%s) has budget #%d ("%s") which has no transactions.',
|
||||||
|
$entry->user_id,
|
||||||
|
$entry->email,
|
||||||
|
$entry->id,
|
||||||
|
$objName
|
||||||
|
);
|
||||||
|
$this->line($line);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Report on categories with no transactions or journals.
|
||||||
|
*/
|
||||||
|
private function reportEmptyCategories(): void
|
||||||
|
{
|
||||||
|
$set = Category::leftJoin('category_transaction_journal', 'categories.id', '=', 'category_transaction_journal.category_id')
|
||||||
|
->leftJoin('users', 'categories.user_id', '=', 'users.id')
|
||||||
|
->distinct()
|
||||||
|
->whereNull('category_transaction_journal.category_id')
|
||||||
|
->whereNull('categories.deleted_at')
|
||||||
|
->get(['categories.id', 'categories.name', 'categories.user_id', 'users.email']);
|
||||||
|
|
||||||
|
/** @var stdClass $entry */
|
||||||
|
foreach ($set as $entry) {
|
||||||
|
$objName = $entry->name;
|
||||||
|
try {
|
||||||
|
$objName = Crypt::decrypt($objName);
|
||||||
|
} catch (DecryptException $e) {
|
||||||
|
// it probably was not encrypted.
|
||||||
|
Log::debug(sprintf('Not a problem: %s', $e->getMessage()));
|
||||||
|
}
|
||||||
|
|
||||||
|
// also count the transactions:
|
||||||
|
$countTransactions = DB::table('category_transaction')->where('category_id', $entry->id)->count();
|
||||||
|
|
||||||
|
if (0 === $countTransactions) {
|
||||||
|
$line = sprintf(
|
||||||
|
'User #%d (%s) has category #%d ("%s") which has no transactions.',
|
||||||
|
$entry->user_id,
|
||||||
|
$entry->email,
|
||||||
|
$entry->id,
|
||||||
|
$objName
|
||||||
|
);
|
||||||
|
$this->line($line);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Report on journals with bad account types linked to them.
|
* Report on journals with bad account types linked to them.
|
||||||
*/
|
*/
|
||||||
@@ -483,12 +570,13 @@ class VerifyDatabase extends Command
|
|||||||
$plural = str_plural($name);
|
$plural = str_plural($name);
|
||||||
$class = sprintf('FireflyIII\Models\%s', ucfirst($name));
|
$class = sprintf('FireflyIII\Models\%s', ucfirst($name));
|
||||||
$field = 'tag' === $name ? 'tag' : 'name';
|
$field = 'tag' === $name ? 'tag' : 'name';
|
||||||
$set = $class::leftJoin($name . '_transaction_journal', $plural . '.id', '=', $name . '_transaction_journal.' . $name . '_id')
|
/** @noinspection PhpUndefinedMethodInspection */
|
||||||
->leftJoin('users', $plural . '.user_id', '=', 'users.id')
|
$set = $class::leftJoin($name . '_transaction_journal', $plural . '.id', '=', $name . '_transaction_journal.' . $name . '_id')
|
||||||
->distinct()
|
->leftJoin('users', $plural . '.user_id', '=', 'users.id')
|
||||||
->whereNull($name . '_transaction_journal.' . $name . '_id')
|
->distinct()
|
||||||
->whereNull($plural . '.deleted_at')
|
->whereNull($name . '_transaction_journal.' . $name . '_id')
|
||||||
->get([$plural . '.id', $plural . '.' . $field . ' as name', $plural . '.user_id', 'users.email']);
|
->whereNull($plural . '.deleted_at')
|
||||||
|
->get([$plural . '.id', $plural . '.' . $field . ' as name', $plural . '.user_id', 'users.email']);
|
||||||
|
|
||||||
/** @var stdClass $entry */
|
/** @var stdClass $entry */
|
||||||
foreach ($set as $entry) {
|
foreach ($set as $entry) {
|
||||||
@@ -497,6 +585,7 @@ class VerifyDatabase extends Command
|
|||||||
$objName = Crypt::decrypt($objName);
|
$objName = Crypt::decrypt($objName);
|
||||||
} catch (DecryptException $e) {
|
} catch (DecryptException $e) {
|
||||||
// it probably was not encrypted.
|
// it probably was not encrypted.
|
||||||
|
Log::debug(sprintf('Not a problem: %s', $e->getMessage()));
|
||||||
}
|
}
|
||||||
|
|
||||||
$line = sprintf(
|
$line = sprintf(
|
||||||
@@ -524,7 +613,8 @@ class VerifyDatabase extends Command
|
|||||||
$sum = (string)$user->transactions()->sum('amount');
|
$sum = (string)$user->transactions()->sum('amount');
|
||||||
if (0 !== bccomp($sum, '0')) {
|
if (0 !== bccomp($sum, '0')) {
|
||||||
$this->error('Error: Transactions for user #' . $user->id . ' (' . $user->email . ') are off by ' . $sum . '!');
|
$this->error('Error: Transactions for user #' . $user->id . ' (' . $user->email . ') are off by ' . $sum . '!');
|
||||||
} else {
|
}
|
||||||
|
if (0 === bccomp($sum, '0')) {
|
||||||
$this->info(sprintf('Amount integrity OK for user #%d', $user->id));
|
$this->info(sprintf('Amount integrity OK for user #%d', $user->id));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -554,7 +644,7 @@ class VerifyDatabase extends Command
|
|||||||
/**
|
/**
|
||||||
* Report on transfers that have budgets.
|
* Report on transfers that have budgets.
|
||||||
*/
|
*/
|
||||||
private function reportTransfersBudgets()
|
private function reportTransfersBudgets(): void
|
||||||
{
|
{
|
||||||
$set = TransactionJournal::distinct()
|
$set = TransactionJournal::distinct()
|
||||||
->leftJoin('transaction_types', 'transaction_types.id', '=', 'transaction_journals.transaction_type_id')
|
->leftJoin('transaction_types', 'transaction_types.id', '=', 'transaction_journals.transaction_type_id')
|
||||||
|
@@ -34,15 +34,6 @@ use Illuminate\Foundation\Console\Kernel as ConsoleKernel;
|
|||||||
*/
|
*/
|
||||||
class Kernel extends ConsoleKernel
|
class Kernel extends ConsoleKernel
|
||||||
{
|
{
|
||||||
/**
|
|
||||||
* The Artisan commands provided by your application.
|
|
||||||
*
|
|
||||||
* @var array
|
|
||||||
*/
|
|
||||||
protected $commands
|
|
||||||
= [
|
|
||||||
];
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Register the commands for the application.
|
* Register the commands for the application.
|
||||||
*/
|
*/
|
||||||
@@ -50,6 +41,7 @@ class Kernel extends ConsoleKernel
|
|||||||
{
|
{
|
||||||
$this->load(__DIR__ . '/Commands');
|
$this->load(__DIR__ . '/Commands');
|
||||||
|
|
||||||
|
/** @noinspection PhpIncludeInspection */
|
||||||
require base_path('routes/console.php');
|
require base_path('routes/console.php');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -35,13 +35,9 @@ class AdminRequestedTestMessage extends Event
|
|||||||
{
|
{
|
||||||
use SerializesModels;
|
use SerializesModels;
|
||||||
|
|
||||||
/**
|
/** @var string The users IP address */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $ipAddress;
|
public $ipAddress;
|
||||||
/**
|
/** @var User The user */
|
||||||
* @var User
|
|
||||||
*/
|
|
||||||
public $user;
|
public $user;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@@ -34,13 +34,9 @@ class RegisteredUser extends Event
|
|||||||
{
|
{
|
||||||
use SerializesModels;
|
use SerializesModels;
|
||||||
|
|
||||||
/**
|
/** @var string The users IP address */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $ipAddress;
|
public $ipAddress;
|
||||||
/**
|
/** @var User The user */
|
||||||
* @var User
|
|
||||||
*/
|
|
||||||
public $user;
|
public $user;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@@ -34,18 +34,12 @@ class RequestedNewPassword extends Event
|
|||||||
{
|
{
|
||||||
use SerializesModels;
|
use SerializesModels;
|
||||||
|
|
||||||
/**
|
/** @var string The users IP address */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $ipAddress;
|
public $ipAddress;
|
||||||
/**
|
/** @var User The user */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $token;
|
|
||||||
/**
|
|
||||||
* @var User
|
|
||||||
*/
|
|
||||||
public $user;
|
public $user;
|
||||||
|
/** @var string The token */
|
||||||
|
public $token;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Create a new event instance. This event is triggered when a users tries to reset his or her password.
|
* Create a new event instance. This event is triggered when a users tries to reset his or her password.
|
||||||
|
@@ -1,4 +1,23 @@
|
|||||||
<?php
|
<?php
|
||||||
|
/**
|
||||||
|
* RequestedReportOnJournals.php
|
||||||
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
|
*
|
||||||
|
* This file is part of Firefly III.
|
||||||
|
*
|
||||||
|
* Firefly III is free software: you can redistribute it and/or modify
|
||||||
|
* it under the terms of the GNU General Public License as published by
|
||||||
|
* the Free Software Foundation, either version 3 of the License, or
|
||||||
|
* (at your option) any later version.
|
||||||
|
*
|
||||||
|
* Firefly III 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 General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU General Public License
|
||||||
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
|
*/
|
||||||
|
|
||||||
namespace FireflyIII\Events;
|
namespace FireflyIII\Events;
|
||||||
|
|
||||||
@@ -16,9 +35,9 @@ class RequestedReportOnJournals
|
|||||||
{
|
{
|
||||||
use Dispatchable, InteractsWithSockets, SerializesModels;
|
use Dispatchable, InteractsWithSockets, SerializesModels;
|
||||||
|
|
||||||
/** @var Collection */
|
/** @var Collection The journals to report on. */
|
||||||
public $journals;
|
public $journals;
|
||||||
/** @var int */
|
/** @var int The ID of the user. */
|
||||||
public $userId;
|
public $userId;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@@ -35,9 +35,7 @@ class RequestedVersionCheckStatus extends Event
|
|||||||
{
|
{
|
||||||
use SerializesModels;
|
use SerializesModels;
|
||||||
|
|
||||||
/**
|
/** @var User The user */
|
||||||
* @var User
|
|
||||||
*/
|
|
||||||
public $user;
|
public $user;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@@ -28,16 +28,17 @@ use FireflyIII\Models\TransactionJournal;
|
|||||||
use Illuminate\Queue\SerializesModels;
|
use Illuminate\Queue\SerializesModels;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @codeCoverageIgnore
|
|
||||||
* Class StoredTransactionJournal.
|
* Class StoredTransactionJournal.
|
||||||
|
*
|
||||||
|
* @codeCoverageIgnore
|
||||||
*/
|
*/
|
||||||
class StoredTransactionJournal extends Event
|
class StoredTransactionJournal extends Event
|
||||||
{
|
{
|
||||||
use SerializesModels;
|
use SerializesModels;
|
||||||
|
|
||||||
/** @var TransactionJournal */
|
/** @var TransactionJournal The journal that was stored. */
|
||||||
public $journal;
|
public $journal;
|
||||||
/** @var int */
|
/** @var int The piggy bank ID. */
|
||||||
public $piggyBankId;
|
public $piggyBankId;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@@ -37,7 +37,7 @@ class UpdatedTransactionJournal extends Event
|
|||||||
{
|
{
|
||||||
use SerializesModels;
|
use SerializesModels;
|
||||||
|
|
||||||
/** @var TransactionJournal */
|
/** @var TransactionJournal The journal. */
|
||||||
public $journal;
|
public $journal;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@@ -34,13 +34,13 @@ class UserChangedEmail extends Event
|
|||||||
{
|
{
|
||||||
use SerializesModels;
|
use SerializesModels;
|
||||||
|
|
||||||
/** @var string */
|
/** @var string The user's IP address */
|
||||||
public $ipAddress;
|
public $ipAddress;
|
||||||
/** @var string */
|
/** @var string The user's new email address */
|
||||||
public $newEmail;
|
public $newEmail;
|
||||||
/** @var string */
|
/** @var string The user's old email address */
|
||||||
public $oldEmail;
|
public $oldEmail;
|
||||||
/** @var User */
|
/** @var User The user itself */
|
||||||
public $user;
|
public $user;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@@ -20,6 +20,8 @@
|
|||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Exceptions;
|
namespace FireflyIII\Exceptions;
|
||||||
@@ -39,32 +41,16 @@ use Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
|
|||||||
*/
|
*/
|
||||||
class Handler extends ExceptionHandler
|
class Handler extends ExceptionHandler
|
||||||
{
|
{
|
||||||
/**
|
|
||||||
* A list of the inputs that are never flashed for validation exceptions.
|
|
||||||
*
|
|
||||||
* @var array
|
|
||||||
*/
|
|
||||||
protected $dontFlash
|
|
||||||
= [
|
|
||||||
'password',
|
|
||||||
'password_confirmation',
|
|
||||||
];
|
|
||||||
/**
|
|
||||||
* A list of the exception types that are not reported.
|
|
||||||
*
|
|
||||||
* @var array
|
|
||||||
*/
|
|
||||||
protected $dontReport
|
|
||||||
= [
|
|
||||||
];
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Render an exception into an HTTP response.
|
* Render an exception into an HTTP response.
|
||||||
*
|
*
|
||||||
* @param \Illuminate\Http\Request $request
|
* @param Request $request
|
||||||
* @param \Exception $exception
|
* @param Exception $exception
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.NPathComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
*
|
*
|
||||||
* @return \Illuminate\Http\Response
|
* @return mixed
|
||||||
*/
|
*/
|
||||||
public function render($request, Exception $exception)
|
public function render($request, Exception $exception)
|
||||||
{
|
{
|
||||||
@@ -130,18 +116,10 @@ class Handler extends ExceptionHandler
|
|||||||
{
|
{
|
||||||
|
|
||||||
$doMailError = env('SEND_ERROR_MESSAGE', true);
|
$doMailError = env('SEND_ERROR_MESSAGE', true);
|
||||||
if (
|
// if the user wants us to mail:
|
||||||
// if the user wants us to mail:
|
if (true === $doMailError
|
||||||
$doMailError === true
|
// and if is one of these error instances
|
||||||
&& (
|
&& ($exception instanceof FireflyException || $exception instanceof ErrorException || $exception instanceof OAuthServerException)) {
|
||||||
// and if is one of these error instances
|
|
||||||
$exception instanceof FireflyException
|
|
||||||
|| $exception instanceof ErrorException
|
|
||||||
|| $exception instanceof OAuthServerException
|
|
||||||
|
|
||||||
)
|
|
||||||
) {
|
|
||||||
// then, send email
|
|
||||||
$userData = [
|
$userData = [
|
||||||
'id' => 0,
|
'id' => 0,
|
||||||
'email' => 'unknown@example.com',
|
'email' => 'unknown@example.com',
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* AttachmentCollector.php
|
* AttachmentCollector.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -29,6 +28,7 @@ use Crypt;
|
|||||||
use FireflyIII\Models\Attachment;
|
use FireflyIII\Models\Attachment;
|
||||||
use FireflyIII\Repositories\Attachment\AttachmentRepositoryInterface;
|
use FireflyIII\Repositories\Attachment\AttachmentRepositoryInterface;
|
||||||
use Illuminate\Contracts\Encryption\DecryptException;
|
use Illuminate\Contracts\Encryption\DecryptException;
|
||||||
|
use Illuminate\Contracts\Filesystem\FileNotFoundException;
|
||||||
use Illuminate\Support\Collection;
|
use Illuminate\Support\Collection;
|
||||||
use Log;
|
use Log;
|
||||||
use Storage;
|
use Storage;
|
||||||
@@ -38,15 +38,15 @@ use Storage;
|
|||||||
*/
|
*/
|
||||||
class AttachmentCollector extends BasicCollector implements CollectorInterface
|
class AttachmentCollector extends BasicCollector implements CollectorInterface
|
||||||
{
|
{
|
||||||
/** @var Carbon */
|
/** @var Carbon The end date of the range. */
|
||||||
private $end;
|
private $end;
|
||||||
/** @var \Illuminate\Contracts\Filesystem\Filesystem */
|
/** @var \Illuminate\Contracts\Filesystem\Filesystem File system */
|
||||||
private $exportDisk;
|
private $exportDisk;
|
||||||
/** @var AttachmentRepositoryInterface */
|
/** @var AttachmentRepositoryInterface Attachment repository */
|
||||||
private $repository;
|
private $repository;
|
||||||
/** @var Carbon */
|
/** @var Carbon Start date of range */
|
||||||
private $start;
|
private $start;
|
||||||
/** @var \Illuminate\Contracts\Filesystem\Filesystem */
|
/** @var \Illuminate\Contracts\Filesystem\Filesystem Disk with uploads on it */
|
||||||
private $uploadDisk;
|
private $uploadDisk;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -64,6 +64,8 @@ class AttachmentCollector extends BasicCollector implements CollectorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Run the routine.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function run(): bool
|
public function run(): bool
|
||||||
@@ -80,6 +82,8 @@ class AttachmentCollector extends BasicCollector implements CollectorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the start and end date.
|
||||||
|
*
|
||||||
* @param Carbon $start
|
* @param Carbon $start
|
||||||
* @param Carbon $end
|
* @param Carbon $end
|
||||||
*/
|
*/
|
||||||
@@ -89,7 +93,10 @@ class AttachmentCollector extends BasicCollector implements CollectorInterface
|
|||||||
$this->end = $end;
|
$this->end = $end;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
/**
|
/**
|
||||||
|
* Export attachments.
|
||||||
|
*
|
||||||
* @param Attachment $attachment
|
* @param Attachment $attachment
|
||||||
*
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
@@ -101,13 +108,13 @@ class AttachmentCollector extends BasicCollector implements CollectorInterface
|
|||||||
if ($this->uploadDisk->exists($file)) {
|
if ($this->uploadDisk->exists($file)) {
|
||||||
try {
|
try {
|
||||||
$decrypted = Crypt::decrypt($this->uploadDisk->get($file));
|
$decrypted = Crypt::decrypt($this->uploadDisk->get($file));
|
||||||
} catch (DecryptException $e) {
|
} catch (FileNotFoundException|DecryptException $e) {
|
||||||
Log::error('Catchable error: could not decrypt attachment #' . $attachment->id . ' because: ' . $e->getMessage());
|
Log::error('Catchable error: could not decrypt attachment #' . $attachment->id . ' because: ' . $e->getMessage());
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
if ($decrypted === false) {
|
if (false === $decrypted) {
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
$exportFile = $this->exportFileName($attachment);
|
$exportFile = $this->exportFileName($attachment);
|
||||||
@@ -130,6 +137,8 @@ class AttachmentCollector extends BasicCollector implements CollectorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get the attachments.
|
||||||
|
*
|
||||||
* @return Collection
|
* @return Collection
|
||||||
*/
|
*/
|
||||||
private function getAttachments(): Collection
|
private function getAttachments(): Collection
|
||||||
|
@@ -33,11 +33,11 @@ use Illuminate\Support\Collection;
|
|||||||
*/
|
*/
|
||||||
class BasicCollector
|
class BasicCollector
|
||||||
{
|
{
|
||||||
/** @var ExportJob */
|
/** @var ExportJob The job to export. */
|
||||||
protected $job;
|
protected $job;
|
||||||
/** @var User */
|
/** @var User The user */
|
||||||
protected $user;
|
protected $user;
|
||||||
/** @var Collection */
|
/** @var Collection All the entries. */
|
||||||
private $entries;
|
private $entries;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -49,6 +49,8 @@ class BasicCollector
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all entries.
|
||||||
|
*
|
||||||
* @return Collection
|
* @return Collection
|
||||||
*/
|
*/
|
||||||
public function getEntries(): Collection
|
public function getEntries(): Collection
|
||||||
@@ -57,26 +59,32 @@ class BasicCollector
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set entries.
|
||||||
|
*
|
||||||
* @param Collection $entries
|
* @param Collection $entries
|
||||||
*/
|
*/
|
||||||
public function setEntries(Collection $entries)
|
public function setEntries(Collection $entries): void
|
||||||
{
|
{
|
||||||
$this->entries = $entries;
|
$this->entries = $entries;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set export job.
|
||||||
|
*
|
||||||
* @param ExportJob $job
|
* @param ExportJob $job
|
||||||
*/
|
*/
|
||||||
public function setJob(ExportJob $job)
|
public function setJob(ExportJob $job): void
|
||||||
{
|
{
|
||||||
$this->job = $job;
|
$this->job = $job;
|
||||||
$this->user = $job->user;
|
$this->user = $job->user;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set user.
|
||||||
|
*
|
||||||
* @param User $user
|
* @param User $user
|
||||||
*/
|
*/
|
||||||
public function setUser(User $user)
|
public function setUser(User $user): void
|
||||||
{
|
{
|
||||||
$this->user = $user;
|
$this->user = $user;
|
||||||
}
|
}
|
||||||
|
@@ -33,21 +33,29 @@ use Illuminate\Support\Collection;
|
|||||||
interface CollectorInterface
|
interface CollectorInterface
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Get entries.
|
||||||
|
*
|
||||||
* @return Collection
|
* @return Collection
|
||||||
*/
|
*/
|
||||||
public function getEntries(): Collection;
|
public function getEntries(): Collection;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Run the collector.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function run(): bool;
|
public function run(): bool;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set entries.
|
||||||
|
*
|
||||||
* @param Collection $entries
|
* @param Collection $entries
|
||||||
*/
|
*/
|
||||||
public function setEntries(Collection $entries);
|
public function setEntries(Collection $entries);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set export job.
|
||||||
|
*
|
||||||
* @param ExportJob $job
|
* @param ExportJob $job
|
||||||
*
|
*
|
||||||
* @return mixed
|
* @return mixed
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* UploadCollector.php
|
* UploadCollector.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -84,7 +83,10 @@ class UploadCollector extends BasicCollector implements CollectorInterface
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
/**
|
/**
|
||||||
|
* Process new file uploads.
|
||||||
|
*
|
||||||
* @param string $key
|
* @param string $key
|
||||||
*
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
|
@@ -46,137 +46,65 @@ use FireflyIII\Models\Transaction;
|
|||||||
*/
|
*/
|
||||||
final class Entry
|
final class Entry
|
||||||
{
|
{
|
||||||
// @formatter:off
|
/** @var int ID of the journal */
|
||||||
/**
|
|
||||||
* @var int
|
|
||||||
*/
|
|
||||||
public $journal_id;
|
public $journal_id;
|
||||||
/**
|
/** @var int ID of the transaction */
|
||||||
* @var int
|
|
||||||
*/
|
|
||||||
public $transaction_id = 0;
|
public $transaction_id = 0;
|
||||||
|
/** @var string The date. */
|
||||||
/**
|
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $date;
|
public $date;
|
||||||
/**
|
/** @var string The description */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $description;
|
public $description;
|
||||||
|
/** @var string The currency code. */
|
||||||
/**
|
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $currency_code;
|
public $currency_code;
|
||||||
/**
|
/** @var string The amount. */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $amount;
|
public $amount;
|
||||||
/**
|
/** @var string The foreign currency code */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $foreign_currency_code = '';
|
public $foreign_currency_code = '';
|
||||||
/**
|
/** @var string Foreign amount */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $foreign_amount = '0';
|
public $foreign_amount = '0';
|
||||||
|
/** @var string Transaction type */
|
||||||
/**
|
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $transaction_type;
|
public $transaction_type;
|
||||||
|
/** @var string Asset account ID */
|
||||||
/**
|
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $asset_account_id;
|
public $asset_account_id;
|
||||||
/**
|
/** @var string Asset account name */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $asset_account_name;
|
public $asset_account_name;
|
||||||
/**
|
/** @var string Asset account IBAN */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $asset_account_iban;
|
public $asset_account_iban;
|
||||||
/**
|
/** @var string Asset account BIC */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $asset_account_bic;
|
public $asset_account_bic;
|
||||||
/**
|
/** @var string Asset account number */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $asset_account_number;
|
public $asset_account_number;
|
||||||
/**
|
/** @var string Asset account currency code */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $asset_currency_code;
|
public $asset_currency_code;
|
||||||
|
/** @var string Opposing account ID */
|
||||||
/**
|
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $opposing_account_id;
|
public $opposing_account_id;
|
||||||
/**
|
/** @var string Opposing account name */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $opposing_account_name;
|
public $opposing_account_name;
|
||||||
/**
|
/** @var string Opposing account IBAN */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $opposing_account_iban;
|
public $opposing_account_iban;
|
||||||
/**
|
/** @var string Opposing account BIC */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $opposing_account_bic;
|
public $opposing_account_bic;
|
||||||
/**
|
/** @var string Opposing account number */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $opposing_account_number;
|
public $opposing_account_number;
|
||||||
/**
|
/** @var string Opposing account code */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $opposing_currency_code;
|
public $opposing_currency_code;
|
||||||
|
/** @var string Budget ID */
|
||||||
/**
|
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $budget_id;
|
public $budget_id;
|
||||||
/**
|
/** @var string Budget name */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $budget_name;
|
public $budget_name;
|
||||||
|
/** @var string Category ID */
|
||||||
/**
|
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $category_id;
|
public $category_id;
|
||||||
/**
|
/** @var string Category name */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $category_name;
|
public $category_name;
|
||||||
|
/** @var string Bill ID */
|
||||||
/**
|
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $bill_id;
|
public $bill_id;
|
||||||
/**
|
/** @var string Bill name */
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $bill_name;
|
public $bill_name;
|
||||||
|
/** @var string Notes */
|
||||||
/**
|
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $notes;
|
public $notes;
|
||||||
|
/** @var string Tags */
|
||||||
/**
|
|
||||||
* @var string
|
|
||||||
*/
|
|
||||||
public $tags;
|
public $tags;
|
||||||
|
|
||||||
|
|
||||||
// @formatter:on
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Entry constructor.
|
* Entry constructor.
|
||||||
*/
|
*/
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* ExpandedProcessor.php
|
* ExpandedProcessor.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -20,6 +19,8 @@
|
|||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection PhpDynamicAsStaticMethodCallInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Export;
|
namespace FireflyIII\Export;
|
||||||
@@ -50,23 +51,23 @@ use ZipArchive;
|
|||||||
*/
|
*/
|
||||||
class ExpandedProcessor implements ProcessorInterface
|
class ExpandedProcessor implements ProcessorInterface
|
||||||
{
|
{
|
||||||
/** @var Collection */
|
/** @var Collection All accounts */
|
||||||
public $accounts;
|
public $accounts;
|
||||||
/** @var string */
|
/** @var string The export format*/
|
||||||
public $exportFormat;
|
public $exportFormat;
|
||||||
/** @var bool */
|
/** @var bool Should include attachments */
|
||||||
public $includeAttachments;
|
public $includeAttachments;
|
||||||
/** @var bool */
|
/** @var bool Should include old uploads */
|
||||||
public $includeOldUploads;
|
public $includeOldUploads;
|
||||||
/** @var ExportJob */
|
/** @var ExportJob The export job itself */
|
||||||
public $job;
|
public $job;
|
||||||
/** @var array */
|
/** @var array The settings*/
|
||||||
public $settings;
|
public $settings;
|
||||||
/** @var Collection */
|
/** @var Collection The entries to export. */
|
||||||
private $exportEntries;
|
private $exportEntries;
|
||||||
/** @var Collection */
|
/** @var Collection The files to export */
|
||||||
private $files;
|
private $files;
|
||||||
/** @var Collection */
|
/** @var Collection The journals. */
|
||||||
private $journals;
|
private $journals;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -80,6 +81,8 @@ class ExpandedProcessor implements ProcessorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Collect all attachments
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function collectAttachments(): bool
|
public function collectAttachments(): bool
|
||||||
@@ -143,6 +146,8 @@ class ExpandedProcessor implements ProcessorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get old oploads.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function collectOldUploads(): bool
|
public function collectOldUploads(): bool
|
||||||
@@ -158,6 +163,8 @@ class ExpandedProcessor implements ProcessorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Convert journals to export objects.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function convertJournals(): bool
|
public function convertJournals(): bool
|
||||||
@@ -173,6 +180,8 @@ class ExpandedProcessor implements ProcessorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Create a ZIP file.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*
|
*
|
||||||
* @throws FireflyException
|
* @throws FireflyException
|
||||||
@@ -204,6 +213,8 @@ class ExpandedProcessor implements ProcessorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Export the journals.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function exportJournals(): bool
|
public function exportJournals(): bool
|
||||||
@@ -219,6 +230,8 @@ class ExpandedProcessor implements ProcessorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get files.
|
||||||
|
*
|
||||||
* @return Collection
|
* @return Collection
|
||||||
*/
|
*/
|
||||||
public function getFiles(): Collection
|
public function getFiles(): Collection
|
||||||
@@ -231,7 +244,7 @@ class ExpandedProcessor implements ProcessorInterface
|
|||||||
*
|
*
|
||||||
* @param array $settings
|
* @param array $settings
|
||||||
*/
|
*/
|
||||||
public function setSettings(array $settings)
|
public function setSettings(array $settings): void
|
||||||
{
|
{
|
||||||
// save settings
|
// save settings
|
||||||
$this->settings = $settings;
|
$this->settings = $settings;
|
||||||
@@ -243,9 +256,9 @@ class ExpandedProcessor implements ProcessorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
* Delete files.
|
||||||
*/
|
*/
|
||||||
private function deleteFiles()
|
private function deleteFiles():void
|
||||||
{
|
{
|
||||||
$disk = Storage::disk('export');
|
$disk = Storage::disk('export');
|
||||||
foreach ($this->getFiles() as $file) {
|
foreach ($this->getFiles() as $file) {
|
||||||
@@ -254,6 +267,8 @@ class ExpandedProcessor implements ProcessorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get currencies.
|
||||||
|
*
|
||||||
* @param array $array
|
* @param array $array
|
||||||
*
|
*
|
||||||
* @return array
|
* @return array
|
||||||
|
@@ -32,9 +32,9 @@ use Illuminate\Support\Collection;
|
|||||||
*/
|
*/
|
||||||
class BasicExporter
|
class BasicExporter
|
||||||
{
|
{
|
||||||
/** @var ExportJob */
|
/** @var ExportJob The export job */
|
||||||
protected $job;
|
protected $job;
|
||||||
/** @var Collection */
|
/** @var Collection The entries */
|
||||||
private $entries;
|
private $entries;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -46,6 +46,8 @@ class BasicExporter
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all entries.
|
||||||
|
*
|
||||||
* @return Collection
|
* @return Collection
|
||||||
*/
|
*/
|
||||||
public function getEntries(): Collection
|
public function getEntries(): Collection
|
||||||
@@ -54,17 +56,21 @@ class BasicExporter
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set all entries.
|
||||||
|
*
|
||||||
* @param Collection $entries
|
* @param Collection $entries
|
||||||
*/
|
*/
|
||||||
public function setEntries(Collection $entries)
|
public function setEntries(Collection $entries): void
|
||||||
{
|
{
|
||||||
$this->entries = $entries;
|
$this->entries = $entries;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the job.
|
||||||
|
*
|
||||||
* @param ExportJob $job
|
* @param ExportJob $job
|
||||||
*/
|
*/
|
||||||
public function setJob(ExportJob $job)
|
public function setJob(ExportJob $job): void
|
||||||
{
|
{
|
||||||
$this->job = $job;
|
$this->job = $job;
|
||||||
}
|
}
|
||||||
|
@@ -33,10 +33,12 @@ use Storage;
|
|||||||
*/
|
*/
|
||||||
class CsvExporter extends BasicExporter implements ExporterInterface
|
class CsvExporter extends BasicExporter implements ExporterInterface
|
||||||
{
|
{
|
||||||
/** @var string */
|
/** @var string Filename */
|
||||||
private $fileName;
|
private $fileName;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get file name.
|
||||||
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function getFileName(): string
|
public function getFileName(): string
|
||||||
@@ -45,6 +47,8 @@ class CsvExporter extends BasicExporter implements ExporterInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Run collector.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
@@ -83,6 +87,9 @@ class CsvExporter extends BasicExporter implements ExporterInterface
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Make a temp file.
|
||||||
|
*/
|
||||||
private function tempFile()
|
private function tempFile()
|
||||||
{
|
{
|
||||||
$this->fileName = $this->job->key . '-records.csv';
|
$this->fileName = $this->job->key . '-records.csv';
|
||||||
|
@@ -33,26 +33,36 @@ use Illuminate\Support\Collection;
|
|||||||
interface ExporterInterface
|
interface ExporterInterface
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
* Get entries.
|
||||||
|
*
|
||||||
* @return Collection
|
* @return Collection
|
||||||
*/
|
*/
|
||||||
public function getEntries(): Collection;
|
public function getEntries(): Collection;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get file name.
|
||||||
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function getFileName(): string;
|
public function getFileName(): string;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Run exporter.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function run(): bool;
|
public function run(): bool;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set entries.
|
||||||
|
*
|
||||||
* @param Collection $entries
|
* @param Collection $entries
|
||||||
*/
|
*/
|
||||||
public function setEntries(Collection $entries);
|
public function setEntries(Collection $entries);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set job.
|
||||||
|
*
|
||||||
* @param ExportJob $job
|
* @param ExportJob $job
|
||||||
*/
|
*/
|
||||||
public function setJob(ExportJob $job);
|
public function setJob(ExportJob $job);
|
||||||
|
@@ -37,41 +37,57 @@ interface ProcessorInterface
|
|||||||
public function __construct();
|
public function __construct();
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Collect all attachments.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function collectAttachments(): bool;
|
public function collectAttachments(): bool;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Collect all journals.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function collectJournals(): bool;
|
public function collectJournals(): bool;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Collect old uploads.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function collectOldUploads(): bool;
|
public function collectOldUploads(): bool;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Convert all journals.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function convertJournals(): bool;
|
public function convertJournals(): bool;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Create a zip file.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function createZipFile(): bool;
|
public function createZipFile(): bool;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Export journals.
|
||||||
|
*
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function exportJournals(): bool;
|
public function exportJournals(): bool;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get all files.
|
||||||
|
*
|
||||||
* @return Collection
|
* @return Collection
|
||||||
*/
|
*/
|
||||||
public function getFiles(): Collection;
|
public function getFiles(): Collection;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the settings.
|
||||||
|
*
|
||||||
* @param array $settings
|
* @param array $settings
|
||||||
*/
|
*/
|
||||||
public function setSettings(array $settings);
|
public function setSettings(array $settings);
|
||||||
|
@@ -20,10 +20,14 @@
|
|||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection PhpDynamicAsStaticMethodCallInspection */
|
||||||
|
/** @noinspection PhpUndefinedMethodInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Factory;
|
namespace FireflyIII\Factory;
|
||||||
|
|
||||||
|
use FireflyIII\Exceptions\FireflyException;
|
||||||
use FireflyIII\Models\Account;
|
use FireflyIII\Models\Account;
|
||||||
use FireflyIII\Models\AccountType;
|
use FireflyIII\Models\AccountType;
|
||||||
use FireflyIII\Services\Internal\Support\AccountServiceTrait;
|
use FireflyIII\Services\Internal\Support\AccountServiceTrait;
|
||||||
@@ -44,56 +48,63 @@ class AccountFactory
|
|||||||
* @param array $data
|
* @param array $data
|
||||||
*
|
*
|
||||||
* @return Account
|
* @return Account
|
||||||
|
* @throws FireflyException
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
*/
|
*/
|
||||||
public function create(array $data): Account
|
public function create(array $data): Account
|
||||||
{
|
{
|
||||||
$type = $this->getAccountType($data['account_type_id'], $data['accountType']);
|
$type = $this->getAccountType($data['account_type_id'], $data['accountType']);
|
||||||
|
|
||||||
|
if (null === $type) {
|
||||||
|
throw new FireflyException(
|
||||||
|
sprintf('AccountFactory::create() was unable to find account type #%d ("%s").', $data['account_type_id'], $data['accountType'])
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
$data['iban'] = $this->filterIban($data['iban']);
|
$data['iban'] = $this->filterIban($data['iban']);
|
||||||
|
|
||||||
|
|
||||||
// account may exist already:
|
// account may exist already:
|
||||||
$existingAccount = $this->find($data['name'], $type->type);
|
$return = $this->find($data['name'], $type->type);
|
||||||
if (null !== $existingAccount) {
|
|
||||||
return $existingAccount;
|
|
||||||
|
if (null === $return) {
|
||||||
|
// create it:
|
||||||
|
$databaseData
|
||||||
|
= [
|
||||||
|
'user_id' => $this->user->id,
|
||||||
|
'account_type_id' => $type->id,
|
||||||
|
'name' => $data['name'],
|
||||||
|
'virtual_balance' => $data['virtualBalance'] ?? '0',
|
||||||
|
'active' => true === $data['active'],
|
||||||
|
'iban' => $data['iban'],
|
||||||
|
];
|
||||||
|
|
||||||
|
// remove virtual balance when not an asset account:
|
||||||
|
if ($type->type !== AccountType::ASSET) {
|
||||||
|
$databaseData['virtual_balance'] = '0';
|
||||||
|
}
|
||||||
|
|
||||||
|
// fix virtual balance when it's empty
|
||||||
|
if ('' === $databaseData['virtual_balance']) {
|
||||||
|
$databaseData['virtual_balance'] = '0';
|
||||||
|
}
|
||||||
|
|
||||||
|
$return = Account::create($databaseData);
|
||||||
|
$this->updateMetaData($return, $data);
|
||||||
|
|
||||||
|
if ($type->type === AccountType::ASSET) {
|
||||||
|
if ($this->validIBData($data)) {
|
||||||
|
$this->updateIB($return, $data);
|
||||||
|
}
|
||||||
|
if (!$this->validIBData($data)) {
|
||||||
|
$this->deleteIB($return);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
$this->updateNote($return, $data['notes'] ?? '');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return $return;
|
||||||
// create it:
|
|
||||||
$databaseData
|
|
||||||
= [
|
|
||||||
'user_id' => $this->user->id,
|
|
||||||
'account_type_id' => $type->id,
|
|
||||||
'name' => $data['name'],
|
|
||||||
'virtual_balance' => $data['virtualBalance'] ?? '0',
|
|
||||||
'active' => true === $data['active'],
|
|
||||||
'iban' => $data['iban'],
|
|
||||||
];
|
|
||||||
|
|
||||||
// remove virtual balance when not an asset account:
|
|
||||||
if ($type->type !== AccountType::ASSET) {
|
|
||||||
$databaseData['virtual_balance'] = '0';
|
|
||||||
}
|
|
||||||
|
|
||||||
// fix virtual balance when it's empty
|
|
||||||
if ($databaseData['virtual_balance'] === '') {
|
|
||||||
$databaseData['virtual_balance'] = '0';
|
|
||||||
}
|
|
||||||
|
|
||||||
$newAccount = Account::create($databaseData);
|
|
||||||
$this->updateMetaData($newAccount, $data);
|
|
||||||
|
|
||||||
if ($this->validIBData($data) && $type->type === AccountType::ASSET) {
|
|
||||||
$this->updateIB($newAccount, $data);
|
|
||||||
}
|
|
||||||
if (!$this->validIBData($data) && $type->type === AccountType::ASSET) {
|
|
||||||
$this->deleteIB($newAccount);
|
|
||||||
}
|
|
||||||
// update note:
|
|
||||||
if (isset($data['notes'])) {
|
|
||||||
$this->updateNote($newAccount, $data['notes']);
|
|
||||||
}
|
|
||||||
|
|
||||||
return $newAccount;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -106,15 +117,16 @@ class AccountFactory
|
|||||||
{
|
{
|
||||||
$type = AccountType::whereType($accountType)->first();
|
$type = AccountType::whereType($accountType)->first();
|
||||||
$accounts = $this->user->accounts()->where('account_type_id', $type->id)->get(['accounts.*']);
|
$accounts = $this->user->accounts()->where('account_type_id', $type->id)->get(['accounts.*']);
|
||||||
|
$return = null;
|
||||||
/** @var Account $object */
|
/** @var Account $object */
|
||||||
foreach ($accounts as $object) {
|
foreach ($accounts as $object) {
|
||||||
if ($object->name === $accountName) {
|
if ($object->name === $accountName) {
|
||||||
return $object;
|
$return = $object;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return null;
|
return $return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -122,30 +134,35 @@ class AccountFactory
|
|||||||
* @param string $accountType
|
* @param string $accountType
|
||||||
*
|
*
|
||||||
* @return Account
|
* @return Account
|
||||||
|
* @throws FireflyException
|
||||||
*/
|
*/
|
||||||
public function findOrCreate(string $accountName, string $accountType): Account
|
public function findOrCreate(string $accountName, string $accountType): Account
|
||||||
{
|
{
|
||||||
$type = AccountType::whereType($accountType)->first();
|
$type = AccountType::whereType($accountType)->first();
|
||||||
$accounts = $this->user->accounts()->where('account_type_id', $type->id)->get(['accounts.*']);
|
$accounts = $this->user->accounts()->where('account_type_id', $type->id)->get(['accounts.*']);
|
||||||
|
$return = null;
|
||||||
/** @var Account $object */
|
/** @var Account $object */
|
||||||
foreach ($accounts as $object) {
|
foreach ($accounts as $object) {
|
||||||
if ($object->name === $accountName) {
|
if ($object->name === $accountName) {
|
||||||
return $object;
|
$return = $object;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
if (null === $return) {
|
||||||
|
$return = $this->create(
|
||||||
|
[
|
||||||
|
'user_id' => $this->user->id,
|
||||||
|
'name' => $accountName,
|
||||||
|
'account_type_id' => $type->id,
|
||||||
|
'accountType' => null,
|
||||||
|
'virtualBalance' => '0',
|
||||||
|
'iban' => null,
|
||||||
|
'active' => true,
|
||||||
|
]
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
return $this->create(
|
return $return;
|
||||||
[
|
|
||||||
'user_id' => $this->user->id,
|
|
||||||
'name' => $accountName,
|
|
||||||
'account_type_id' => $type->id,
|
|
||||||
'accountType' => null,
|
|
||||||
'virtualBalance' => '0',
|
|
||||||
'iban' => null,
|
|
||||||
'active' => true,
|
|
||||||
]
|
|
||||||
);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -161,18 +178,23 @@ class AccountFactory
|
|||||||
* @param null|string $accountType
|
* @param null|string $accountType
|
||||||
*
|
*
|
||||||
* @return AccountType|null
|
* @return AccountType|null
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
protected function getAccountType(?int $accountTypeId, ?string $accountType): ?AccountType
|
protected function getAccountType(?int $accountTypeId, ?string $accountType): ?AccountType
|
||||||
{
|
{
|
||||||
$accountTypeId = (int)$accountTypeId;
|
$accountTypeId = (int)$accountTypeId;
|
||||||
|
$result = null;
|
||||||
if ($accountTypeId > 0) {
|
if ($accountTypeId > 0) {
|
||||||
return AccountType::find($accountTypeId);
|
$result = AccountType::find($accountTypeId);
|
||||||
}
|
}
|
||||||
$type = config('firefly.accountTypeByIdentifier.' . (string)$accountType);
|
if (null === $result) {
|
||||||
$result = AccountType::whereType($type)->first();
|
/** @var string $type */
|
||||||
if (null === $result && null !== $accountType) {
|
$type = (string)config('firefly.accountTypeByIdentifier.' . (string)$accountType);
|
||||||
// try as full name:
|
$result = AccountType::whereType($type)->first();
|
||||||
$result = AccountType::whereType($accountType)->first();
|
if (null === $result && null !== $accountType) {
|
||||||
|
// try as full name:
|
||||||
|
$result = AccountType::whereType($accountType)->first();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return $result;
|
return $result;
|
||||||
|
@@ -81,25 +81,19 @@ class BillFactory
|
|||||||
{
|
{
|
||||||
$billId = (int)$billId;
|
$billId = (int)$billId;
|
||||||
$billName = (string)$billName;
|
$billName = (string)$billName;
|
||||||
|
$bill = null;
|
||||||
// first find by ID:
|
// first find by ID:
|
||||||
if ($billId > 0) {
|
if ($billId > 0) {
|
||||||
/** @var Bill $bill */
|
/** @var Bill $bill */
|
||||||
$bill = $this->user->bills()->find($billId);
|
$bill = $this->user->bills()->find($billId);
|
||||||
if (null !== $bill) {
|
|
||||||
return $bill;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// then find by name:
|
// then find by name:
|
||||||
if (\strlen($billName) > 0) {
|
if (null === $bill && \strlen($billName) > 0) {
|
||||||
$bill = $this->findByName($billName);
|
$bill = $this->findByName($billName);
|
||||||
if (null !== $bill) {
|
|
||||||
return $bill;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return null;
|
return $bill;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -112,22 +106,24 @@ class BillFactory
|
|||||||
{
|
{
|
||||||
/** @var Collection $collection */
|
/** @var Collection $collection */
|
||||||
$collection = $this->user->bills()->get();
|
$collection = $this->user->bills()->get();
|
||||||
|
$return = null;
|
||||||
/** @var Bill $bill */
|
/** @var Bill $bill */
|
||||||
foreach ($collection as $bill) {
|
foreach ($collection as $bill) {
|
||||||
Log::debug(sprintf('"%s" vs. "%s"', $bill->name, $name));
|
Log::debug(sprintf('"%s" vs. "%s"', $bill->name, $name));
|
||||||
if ($bill->name === $name) {
|
if ($bill->name === $name) {
|
||||||
return $bill;
|
$return = $bill;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
Log::debug(sprintf('Bill::Find by name returns NULL based on "%s"', $name));
|
Log::debug(sprintf('Bill::find("%s") by name returns null? %s', $name, var_export($return, true)));
|
||||||
|
|
||||||
return null;
|
return $return;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param User $user
|
* @param User $user
|
||||||
*/
|
*/
|
||||||
public function setUser(User $user)
|
public function setUser(User $user): void
|
||||||
{
|
{
|
||||||
$this->user = $user;
|
$this->user = $user;
|
||||||
}
|
}
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* BudgetFactory.php
|
* BudgetFactory.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -19,7 +18,7 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
|
|
||||||
@@ -30,7 +29,7 @@ use FireflyIII\User;
|
|||||||
use Illuminate\Support\Collection;
|
use Illuminate\Support\Collection;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class BudgetFactory
|
* Class BudgetFactory.
|
||||||
*/
|
*/
|
||||||
class BudgetFactory
|
class BudgetFactory
|
||||||
{
|
{
|
||||||
@@ -43,13 +42,14 @@ class BudgetFactory
|
|||||||
* @param null|string $budgetName
|
* @param null|string $budgetName
|
||||||
*
|
*
|
||||||
* @return Budget|null
|
* @return Budget|null
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
public function find(?int $budgetId, ?string $budgetName): ?Budget
|
public function find(?int $budgetId, ?string $budgetName): ?Budget
|
||||||
{
|
{
|
||||||
$budgetId = (int)$budgetId;
|
$budgetId = (int)$budgetId;
|
||||||
$budgetName = (string)$budgetName;
|
$budgetName = (string)$budgetName;
|
||||||
|
|
||||||
if (\strlen($budgetName) === 0 && $budgetId === 0) {
|
if (0 === $budgetId && '' === $budgetName) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -62,7 +62,7 @@ class BudgetFactory
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (\strlen($budgetName) > 0) {
|
if ('' !== $budgetName) {
|
||||||
$budget = $this->findByName($budgetName);
|
$budget = $this->findByName($budgetName);
|
||||||
if (null !== $budget) {
|
if (null !== $budget) {
|
||||||
return $budget;
|
return $budget;
|
||||||
@@ -94,7 +94,7 @@ class BudgetFactory
|
|||||||
/**
|
/**
|
||||||
* @param User $user
|
* @param User $user
|
||||||
*/
|
*/
|
||||||
public function setUser(User $user)
|
public function setUser(User $user): void
|
||||||
{
|
{
|
||||||
$this->user = $user;
|
$this->user = $user;
|
||||||
}
|
}
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* CategoryFactory.php
|
* CategoryFactory.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -19,7 +18,7 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Factory;
|
namespace FireflyIII\Factory;
|
||||||
@@ -64,6 +63,7 @@ class CategoryFactory
|
|||||||
* @param null|string $categoryName
|
* @param null|string $categoryName
|
||||||
*
|
*
|
||||||
* @return Category|null
|
* @return Category|null
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
public function findOrCreate(?int $categoryId, ?string $categoryName): ?Category
|
public function findOrCreate(?int $categoryId, ?string $categoryName): ?Category
|
||||||
{
|
{
|
||||||
@@ -72,7 +72,7 @@ class CategoryFactory
|
|||||||
|
|
||||||
Log::debug(sprintf('Going to find category with ID %d and name "%s"', $categoryId, $categoryName));
|
Log::debug(sprintf('Going to find category with ID %d and name "%s"', $categoryId, $categoryName));
|
||||||
|
|
||||||
if ('' === $categoryName && $categoryId === 0) {
|
if ('' === $categoryName && 0 === $categoryId) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
// first by ID:
|
// first by ID:
|
||||||
@@ -104,7 +104,7 @@ class CategoryFactory
|
|||||||
/**
|
/**
|
||||||
* @param User $user
|
* @param User $user
|
||||||
*/
|
*/
|
||||||
public function setUser(User $user)
|
public function setUser(User $user): void
|
||||||
{
|
{
|
||||||
$this->user = $user;
|
$this->user = $user;
|
||||||
}
|
}
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* PiggyBankEventFactory.php
|
* PiggyBankEventFactory.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -19,7 +18,7 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Factory;
|
namespace FireflyIII\Factory;
|
||||||
@@ -43,6 +42,7 @@ class PiggyBankEventFactory
|
|||||||
* @param PiggyBank|null $piggyBank
|
* @param PiggyBank|null $piggyBank
|
||||||
*
|
*
|
||||||
* @return PiggyBankEvent|null
|
* @return PiggyBankEvent|null
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
public function create(TransactionJournal $journal, ?PiggyBank $piggyBank): ?PiggyBankEvent
|
public function create(TransactionJournal $journal, ?PiggyBank $piggyBank): ?PiggyBankEvent
|
||||||
{
|
{
|
||||||
@@ -51,7 +51,6 @@ class PiggyBankEventFactory
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
// is a transfer?
|
|
||||||
if (!(TransactionType::TRANSFER === $journal->transactionType->type)) {
|
if (!(TransactionType::TRANSFER === $journal->transactionType->type)) {
|
||||||
Log::info(sprintf('Will not connect %s #%d to a piggy bank.', $journal->transactionType->type, $journal->id));
|
Log::info(sprintf('Will not connect %s #%d to a piggy bank.', $journal->transactionType->type, $journal->id));
|
||||||
|
|
||||||
@@ -62,7 +61,6 @@ class PiggyBankEventFactory
|
|||||||
$piggyRepos = app(PiggyBankRepositoryInterface::class);
|
$piggyRepos = app(PiggyBankRepositoryInterface::class);
|
||||||
$piggyRepos->setUser($journal->user);
|
$piggyRepos->setUser($journal->user);
|
||||||
|
|
||||||
// repetition exists?
|
|
||||||
$repetition = $piggyRepos->getRepetition($piggyBank);
|
$repetition = $piggyRepos->getRepetition($piggyBank);
|
||||||
if (null === $repetition) {
|
if (null === $repetition) {
|
||||||
Log::error(sprintf('No piggy bank repetition on %s!', $journal->date->format('Y-m-d')));
|
Log::error(sprintf('No piggy bank repetition on %s!', $journal->date->format('Y-m-d')));
|
||||||
@@ -70,7 +68,6 @@ class PiggyBankEventFactory
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
// get the amount
|
|
||||||
$amount = $piggyRepos->getExactAmount($piggyBank, $repetition, $journal);
|
$amount = $piggyRepos->getExactAmount($piggyBank, $repetition, $journal);
|
||||||
if (0 === bccomp($amount, '0')) {
|
if (0 === bccomp($amount, '0')) {
|
||||||
Log::debug('Amount is zero, will not create event.');
|
Log::debug('Amount is zero, will not create event.');
|
||||||
@@ -78,10 +75,8 @@ class PiggyBankEventFactory
|
|||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
// update amount
|
|
||||||
$piggyRepos->addAmountToRepetition($repetition, $amount);
|
$piggyRepos->addAmountToRepetition($repetition, $amount);
|
||||||
$event = $piggyRepos->createEventWithJournal($piggyBank, $amount, $journal);
|
$event = $piggyRepos->createEventWithJournal($piggyBank, $amount, $journal);
|
||||||
|
|
||||||
Log::debug(sprintf('Created piggy bank event #%d', $event->id));
|
Log::debug(sprintf('Created piggy bank event #%d', $event->id));
|
||||||
|
|
||||||
return $event;
|
return $event;
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* PiggyBankFactory.php
|
* PiggyBankFactory.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -19,7 +18,7 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Factory;
|
namespace FireflyIII\Factory;
|
||||||
@@ -41,12 +40,13 @@ class PiggyBankFactory
|
|||||||
* @param null|string $piggyBankName
|
* @param null|string $piggyBankName
|
||||||
*
|
*
|
||||||
* @return PiggyBank|null
|
* @return PiggyBank|null
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
public function find(?int $piggyBankId, ?string $piggyBankName): ?PiggyBank
|
public function find(?int $piggyBankId, ?string $piggyBankName): ?PiggyBank
|
||||||
{
|
{
|
||||||
$piggyBankId = (int)$piggyBankId;
|
$piggyBankId = (int)$piggyBankId;
|
||||||
$piggyBankName = (string)$piggyBankName;
|
$piggyBankName = (string)$piggyBankName;
|
||||||
if (\strlen($piggyBankName) === 0 && $piggyBankId === 0) {
|
if ('' === $piggyBankName && 0 === $piggyBankId) {
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
// first find by ID:
|
// first find by ID:
|
||||||
@@ -92,7 +92,7 @@ class PiggyBankFactory
|
|||||||
/**
|
/**
|
||||||
* @param User $user
|
* @param User $user
|
||||||
*/
|
*/
|
||||||
public function setUser(User $user)
|
public function setUser(User $user): void
|
||||||
{
|
{
|
||||||
$this->user = $user;
|
$this->user = $user;
|
||||||
|
|
||||||
|
@@ -18,12 +18,14 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Factory;
|
namespace FireflyIII\Factory;
|
||||||
|
|
||||||
|
|
||||||
|
use Carbon\Carbon;
|
||||||
use FireflyIII\Exceptions\FireflyException;
|
use FireflyIII\Exceptions\FireflyException;
|
||||||
use FireflyIII\Models\Recurrence;
|
use FireflyIII\Models\Recurrence;
|
||||||
use FireflyIII\Services\Internal\Support\RecurringTransactionTrait;
|
use FireflyIII\Services\Internal\Support\RecurringTransactionTrait;
|
||||||
@@ -56,6 +58,9 @@ class RecurrenceFactory
|
|||||||
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
/** @var Carbon $firstDate */
|
||||||
|
$firstDate = $data['recurrence']['first_date'];
|
||||||
|
|
||||||
$repetitions = (int)$data['recurrence']['repetitions'];
|
$repetitions = (int)$data['recurrence']['repetitions'];
|
||||||
$recurrence = new Recurrence(
|
$recurrence = new Recurrence(
|
||||||
[
|
[
|
||||||
@@ -63,7 +68,7 @@ class RecurrenceFactory
|
|||||||
'transaction_type_id' => $type->id,
|
'transaction_type_id' => $type->id,
|
||||||
'title' => $data['recurrence']['title'],
|
'title' => $data['recurrence']['title'],
|
||||||
'description' => $data['recurrence']['description'],
|
'description' => $data['recurrence']['description'],
|
||||||
'first_date' => $data['recurrence']['first_date']->format('Y-m-d'),
|
'first_date' => $firstDate->format('Y-m-d'),
|
||||||
'repeat_until' => $repetitions > 0 ? null : $data['recurrence']['repeat_until'],
|
'repeat_until' => $repetitions > 0 ? null : $data['recurrence']['repeat_until'],
|
||||||
'latest_date' => null,
|
'latest_date' => null,
|
||||||
'repetitions' => $data['recurrence']['repetitions'],
|
'repetitions' => $data['recurrence']['repetitions'],
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* TagFactory.php
|
* TagFactory.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -19,6 +18,7 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* TransactionCurrencyFactory.php
|
* TransactionCurrencyFactory.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -20,6 +19,10 @@
|
|||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection PhpDynamicAsStaticMethodCallInspection */
|
||||||
|
/** @noinspection PhpUndefinedMethodInspection */
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Factory;
|
namespace FireflyIII\Factory;
|
||||||
@@ -63,13 +66,14 @@ class TransactionCurrencyFactory
|
|||||||
* @param null|string $currencyCode
|
* @param null|string $currencyCode
|
||||||
*
|
*
|
||||||
* @return TransactionCurrency|null
|
* @return TransactionCurrency|null
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
public function find(?int $currencyId, ?string $currencyCode): ?TransactionCurrency
|
public function find(?int $currencyId, ?string $currencyCode): ?TransactionCurrency
|
||||||
{
|
{
|
||||||
$currencyCode = (string)$currencyCode;
|
$currencyCode = (string)$currencyCode;
|
||||||
$currencyId = (int)$currencyId;
|
$currencyId = (int)$currencyId;
|
||||||
|
|
||||||
if ('' === $currencyCode && $currencyId === 0) {
|
if ('' === $currencyCode && 0 === $currencyId) {
|
||||||
Log::warning('Cannot find anything on empty currency code and empty currency ID!');
|
Log::warning('Cannot find anything on empty currency code and empty currency ID!');
|
||||||
|
|
||||||
return null;
|
return null;
|
||||||
|
@@ -50,6 +50,7 @@ class TransactionFactory
|
|||||||
*
|
*
|
||||||
* @return Transaction
|
* @return Transaction
|
||||||
* @throws FireflyException
|
* @throws FireflyException
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
*/
|
*/
|
||||||
public function create(array $data): ?Transaction
|
public function create(array $data): ?Transaction
|
||||||
{
|
{
|
||||||
@@ -89,37 +90,41 @@ class TransactionFactory
|
|||||||
*
|
*
|
||||||
* @return Collection
|
* @return Collection
|
||||||
* @throws FireflyException
|
* @throws FireflyException
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.NPathComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
*/
|
*/
|
||||||
public function createPair(TransactionJournal $journal, array $data): Collection
|
public function createPair(TransactionJournal $journal, array $data): Collection
|
||||||
{
|
{
|
||||||
Log::debug('Start of TransactionFactory::createPair()');
|
Log::debug('Start of TransactionFactory::createPair()', $data);
|
||||||
// all this data is the same for both transactions:
|
// all this data is the same for both transactions:
|
||||||
$currency = $this->findCurrency($data['currency_id'], $data['currency_code']);
|
$currency = $this->findCurrency($data['currency_id'], $data['currency_code']);
|
||||||
$description = $journal->description === $data['description'] ? null : $data['description'];
|
$description = $journal->description === $data['description'] ? null : $data['description'];
|
||||||
|
|
||||||
// type of source account depends on journal type:
|
// type of source account and destination account depends on journal type:
|
||||||
$sourceType = $this->accountType($journal, 'source');
|
$sourceType = $this->accountType($journal, 'source');
|
||||||
Log::debug(sprintf('Expect source account to be of type %s', $sourceType));
|
|
||||||
$sourceAccount = $this->findAccount($sourceType, $data['source_id'], $data['source_name']);
|
|
||||||
|
|
||||||
// same for destination account:
|
|
||||||
$destinationType = $this->accountType($journal, 'destination');
|
$destinationType = $this->accountType($journal, 'destination');
|
||||||
Log::debug(sprintf('Expect source destination to be of type %s', $destinationType));
|
|
||||||
|
Log::debug(sprintf('Expect source account to be of type "%s"', $sourceType));
|
||||||
|
Log::debug(sprintf('Expect source destination to be of type "%s"', $destinationType));
|
||||||
|
|
||||||
|
// find source and destination account:
|
||||||
|
$sourceAccount = $this->findAccount($sourceType, $data['source_id'], $data['source_name']);
|
||||||
$destinationAccount = $this->findAccount($destinationType, $data['destination_id'], $data['destination_name']);
|
$destinationAccount = $this->findAccount($destinationType, $data['destination_id'], $data['destination_name']);
|
||||||
|
|
||||||
|
if (null === $sourceAccount || null === $destinationAccount) {
|
||||||
|
throw new FireflyException('Could not determine source or destination account.');
|
||||||
|
}
|
||||||
|
|
||||||
Log::debug(sprintf('Source type is "%s", destination type is "%s"', $sourceAccount->accountType->type, $destinationAccount->accountType->type));
|
Log::debug(sprintf('Source type is "%s", destination type is "%s"', $sourceAccount->accountType->type, $destinationAccount->accountType->type));
|
||||||
// throw big fat error when source type === dest type
|
// throw big fat error when source type === dest type and it's not a transfer or reconciliation.
|
||||||
if ($sourceAccount->accountType->type === $destinationAccount->accountType->type
|
if ($sourceAccount->accountType->type === $destinationAccount->accountType->type && $journal->transactionType->type !== TransactionType::TRANSFER) {
|
||||||
&& ($journal->transactionType->type !== TransactionType::TRANSFER
|
|
||||||
&& $journal->transactionType->type !== TransactionType::RECONCILIATION)
|
|
||||||
) {
|
|
||||||
throw new FireflyException(sprintf('Source and destination account cannot be both of the type "%s"', $destinationAccount->accountType->type));
|
throw new FireflyException(sprintf('Source and destination account cannot be both of the type "%s"', $destinationAccount->accountType->type));
|
||||||
}
|
}
|
||||||
if ($sourceAccount->accountType->type !== AccountType::ASSET && $destinationAccount->accountType->type !== AccountType::ASSET) {
|
if ($sourceAccount->accountType->type !== AccountType::ASSET && $destinationAccount->accountType->type !== AccountType::ASSET) {
|
||||||
throw new FireflyException('At least one of the accounts must be an asset account.');
|
throw new FireflyException('At least one of the accounts must be an asset account.');
|
||||||
}
|
}
|
||||||
|
|
||||||
// first make a "negative" (source) transaction based on the data in the array.
|
|
||||||
$source = $this->create(
|
$source = $this->create(
|
||||||
[
|
[
|
||||||
'description' => $description,
|
'description' => $description,
|
||||||
@@ -132,8 +137,7 @@ class TransactionFactory
|
|||||||
'identifier' => $data['identifier'],
|
'identifier' => $data['identifier'],
|
||||||
]
|
]
|
||||||
);
|
);
|
||||||
// then make a "positive" transaction based on the data in the array.
|
$dest = $this->create(
|
||||||
$dest = $this->create(
|
|
||||||
[
|
[
|
||||||
'description' => $description,
|
'description' => $description,
|
||||||
'amount' => app('steam')->positive((string)$data['amount']),
|
'amount' => app('steam')->positive((string)$data['amount']),
|
||||||
@@ -145,6 +149,9 @@ class TransactionFactory
|
|||||||
'identifier' => $data['identifier'],
|
'identifier' => $data['identifier'],
|
||||||
]
|
]
|
||||||
);
|
);
|
||||||
|
if (null === $source || null === $dest) {
|
||||||
|
throw new FireflyException('Could not create transactions.');
|
||||||
|
}
|
||||||
|
|
||||||
// set foreign currency
|
// set foreign currency
|
||||||
$foreign = $this->findCurrency($data['foreign_currency_id'], $data['foreign_currency_code']);
|
$foreign = $this->findCurrency($data['foreign_currency_id'], $data['foreign_currency_code']);
|
||||||
@@ -178,7 +185,7 @@ class TransactionFactory
|
|||||||
/**
|
/**
|
||||||
* @param User $user
|
* @param User $user
|
||||||
*/
|
*/
|
||||||
public function setUser(User $user)
|
public function setUser(User $user): void
|
||||||
{
|
{
|
||||||
$this->user = $user;
|
$this->user = $user;
|
||||||
}
|
}
|
||||||
|
@@ -37,14 +37,18 @@ use Log;
|
|||||||
class TransactionJournalFactory
|
class TransactionJournalFactory
|
||||||
{
|
{
|
||||||
use JournalServiceTrait, TransactionTypeTrait;
|
use JournalServiceTrait, TransactionTypeTrait;
|
||||||
/** @var User */
|
/** @var User The user */
|
||||||
private $user;
|
private $user;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Store a new transaction journal.
|
||||||
|
*
|
||||||
* @param array $data
|
* @param array $data
|
||||||
*
|
*
|
||||||
* @return TransactionJournal
|
* @return TransactionJournal
|
||||||
* @throws FireflyException
|
* @throws FireflyException
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
*/
|
*/
|
||||||
public function create(array $data): TransactionJournal
|
public function create(array $data): TransactionJournal
|
||||||
{
|
{
|
||||||
@@ -124,6 +128,8 @@ class TransactionJournalFactory
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Link a piggy bank to this journal.
|
||||||
|
*
|
||||||
* @param TransactionJournal $journal
|
* @param TransactionJournal $journal
|
||||||
* @param array $data
|
* @param array $data
|
||||||
*/
|
*/
|
||||||
|
@@ -1,5 +1,4 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* TransactionJournalMetaFactory.php
|
* TransactionJournalMetaFactory.php
|
||||||
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
* Copyright (c) 2018 thegrumpydictator@gmail.com
|
||||||
@@ -19,6 +18,7 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
@@ -38,6 +38,8 @@ class TransactionJournalMetaFactory
|
|||||||
* @param array $data
|
* @param array $data
|
||||||
*
|
*
|
||||||
* @return TransactionJournalMeta|null
|
* @return TransactionJournalMeta|null
|
||||||
|
* @SuppressWarnings(PHPMD.CyclomaticComplexity)
|
||||||
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength)
|
||||||
*/
|
*/
|
||||||
public function updateOrCreate(array $data): ?TransactionJournalMeta
|
public function updateOrCreate(array $data): ?TransactionJournalMeta
|
||||||
{
|
{
|
||||||
@@ -57,7 +59,7 @@ class TransactionJournalMetaFactory
|
|||||||
if ($data['data'] instanceof Carbon) {
|
if ($data['data'] instanceof Carbon) {
|
||||||
$value = $data['data']->toW3cString();
|
$value = $data['data']->toW3cString();
|
||||||
}
|
}
|
||||||
if ((string)$value === '') {
|
if ('' === (string)$value) {
|
||||||
// don't store blank strings.
|
// don't store blank strings.
|
||||||
if (null !== $entry) {
|
if (null !== $entry) {
|
||||||
try {
|
try {
|
||||||
|
@@ -19,6 +19,7 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
/** @noinspection PhpUndefinedMethodInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
|
@@ -23,7 +23,6 @@ declare(strict_types=1);
|
|||||||
namespace FireflyIII\Generator\Chart\Basic;
|
namespace FireflyIII\Generator\Chart\Basic;
|
||||||
|
|
||||||
use FireflyIII\Support\ChartColour;
|
use FireflyIII\Support\ChartColour;
|
||||||
use Steam;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class ChartJsGenerator.
|
* Class ChartJsGenerator.
|
||||||
@@ -90,7 +89,7 @@ class ChartJsGenerator implements GeneratorInterface
|
|||||||
if (isset($set['currency_symbol'])) {
|
if (isset($set['currency_symbol'])) {
|
||||||
$currentSet['currency_symbol'] = $set['currency_symbol'];
|
$currentSet['currency_symbol'] = $set['currency_symbol'];
|
||||||
}
|
}
|
||||||
if(isset($set['backgroundColor'])) {
|
if (isset($set['backgroundColor'])) {
|
||||||
$currentSet['backgroundColor'] = $set['backgroundColor'];
|
$currentSet['backgroundColor'] = $set['backgroundColor'];
|
||||||
}
|
}
|
||||||
$chartData['datasets'][] = $currentSet;
|
$chartData['datasets'][] = $currentSet;
|
||||||
@@ -130,7 +129,7 @@ class ChartJsGenerator implements GeneratorInterface
|
|||||||
$index = 0;
|
$index = 0;
|
||||||
foreach ($data as $key => $value) {
|
foreach ($data as $key => $value) {
|
||||||
// make larger than 0
|
// make larger than 0
|
||||||
$chartData['datasets'][0]['data'][] = (float)Steam::positive($value);
|
$chartData['datasets'][0]['data'][] = (float)app('steam')->positive($value);
|
||||||
$chartData['datasets'][0]['backgroundColor'][] = ChartColour::getColour($index);
|
$chartData['datasets'][0]['backgroundColor'][] = ChartColour::getColour($index);
|
||||||
$chartData['labels'][] = $key;
|
$chartData['labels'][] = $key;
|
||||||
++$index;
|
++$index;
|
||||||
|
@@ -31,17 +31,20 @@ use Illuminate\Support\Collection;
|
|||||||
*/
|
*/
|
||||||
class MonthReportGenerator implements ReportGeneratorInterface
|
class MonthReportGenerator implements ReportGeneratorInterface
|
||||||
{
|
{
|
||||||
/** @var Collection */
|
/** @var Collection The accounts involved in the report. */
|
||||||
private $accounts;
|
private $accounts;
|
||||||
/** @var Carbon */
|
/** @var Carbon The end date */
|
||||||
private $end;
|
private $end;
|
||||||
/** @var Collection */
|
/** @var Collection The expense accounts. */
|
||||||
private $expense;
|
private $expense;
|
||||||
/** @var Carbon */
|
/** @var Carbon The start date. */
|
||||||
private $start;
|
private $start;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Generate the report.
|
||||||
|
*
|
||||||
* @return string
|
* @return string
|
||||||
|
* @throws \Throwable
|
||||||
*/
|
*/
|
||||||
public function generate(): string
|
public function generate(): string
|
||||||
{
|
{
|
||||||
@@ -57,6 +60,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set accounts.
|
||||||
|
*
|
||||||
* @param Collection $accounts
|
* @param Collection $accounts
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -69,6 +74,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set budgets.
|
||||||
|
*
|
||||||
* @param Collection $budgets
|
* @param Collection $budgets
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -79,6 +86,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set categories.
|
||||||
|
*
|
||||||
* @param Collection $categories
|
* @param Collection $categories
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -89,6 +98,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set end date.
|
||||||
|
*
|
||||||
* @param Carbon $date
|
* @param Carbon $date
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -101,6 +112,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set expense collection.
|
||||||
|
*
|
||||||
* @param Collection $expense
|
* @param Collection $expense
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -113,6 +126,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set start date.
|
||||||
|
*
|
||||||
* @param Carbon $date
|
* @param Carbon $date
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -125,6 +140,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set collection of tags.
|
||||||
|
*
|
||||||
* @param Collection $tags
|
* @param Collection $tags
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -135,6 +152,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Return the preferred period.
|
||||||
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
protected function preferredPeriod(): string
|
protected function preferredPeriod(): string
|
||||||
|
@@ -27,9 +27,9 @@ namespace FireflyIII\Generator\Report\Account;
|
|||||||
*/
|
*/
|
||||||
class MultiYearReportGenerator extends MonthReportGenerator
|
class MultiYearReportGenerator extends MonthReportGenerator
|
||||||
{
|
{
|
||||||
// Doesn't do anything different.
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Returns the preferred period.
|
||||||
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
protected function preferredPeriod(): string
|
protected function preferredPeriod(): string
|
||||||
|
@@ -27,9 +27,9 @@ namespace FireflyIII\Generator\Report\Account;
|
|||||||
*/
|
*/
|
||||||
class YearReportGenerator extends MonthReportGenerator
|
class YearReportGenerator extends MonthReportGenerator
|
||||||
{
|
{
|
||||||
// Doesn't do anything different.
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Returns the preferred period.
|
||||||
|
*
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
protected function preferredPeriod(): string
|
protected function preferredPeriod(): string
|
||||||
|
@@ -18,33 +18,40 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
/** @noinspection PhpUndefinedMethodInspection */
|
||||||
|
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Generator\Report\Audit;
|
namespace FireflyIII\Generator\Report\Audit;
|
||||||
|
|
||||||
use Carbon\Carbon;
|
use Carbon\Carbon;
|
||||||
|
use FireflyIII\Exceptions\FireflyException;
|
||||||
use FireflyIII\Generator\Report\ReportGeneratorInterface;
|
use FireflyIII\Generator\Report\ReportGeneratorInterface;
|
||||||
use FireflyIII\Helpers\Collector\JournalCollectorInterface;
|
use FireflyIII\Helpers\Collector\JournalCollectorInterface;
|
||||||
use FireflyIII\Models\Account;
|
use FireflyIII\Models\Account;
|
||||||
use FireflyIII\Models\Transaction;
|
use FireflyIII\Models\Transaction;
|
||||||
|
use FireflyIII\Repositories\Account\AccountRepositoryInterface;
|
||||||
use FireflyIII\Repositories\Currency\CurrencyRepositoryInterface;
|
use FireflyIII\Repositories\Currency\CurrencyRepositoryInterface;
|
||||||
use Illuminate\Support\Collection;
|
use Illuminate\Support\Collection;
|
||||||
use Steam;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class MonthReportGenerator.
|
* Class MonthReportGenerator.
|
||||||
*/
|
*/
|
||||||
class MonthReportGenerator implements ReportGeneratorInterface
|
class MonthReportGenerator implements ReportGeneratorInterface
|
||||||
{
|
{
|
||||||
/** @var Collection */
|
/** @var Collection The accounts used. */
|
||||||
private $accounts;
|
private $accounts;
|
||||||
/** @var Carbon */
|
/** @var Carbon End date of the report. */
|
||||||
private $end;
|
private $end;
|
||||||
/** @var Carbon */
|
/** @var Carbon Start date of the report. */
|
||||||
private $start;
|
private $start;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Generates the report.
|
||||||
|
*
|
||||||
* @return string
|
* @return string
|
||||||
|
* @throws \Throwable
|
||||||
*/
|
*/
|
||||||
public function generate(): string
|
public function generate(): string
|
||||||
{
|
{
|
||||||
@@ -77,6 +84,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Account collection setter.
|
||||||
|
*
|
||||||
* @param Collection $accounts
|
* @param Collection $accounts
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -89,6 +98,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Budget collection setter.
|
||||||
|
*
|
||||||
* @param Collection $budgets
|
* @param Collection $budgets
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -99,6 +110,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Category collection setter.
|
||||||
|
*
|
||||||
* @param Collection $categories
|
* @param Collection $categories
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -109,6 +122,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* End date setter.
|
||||||
|
*
|
||||||
* @param Carbon $date
|
* @param Carbon $date
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -121,6 +136,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Expenses collection setter.
|
||||||
|
*
|
||||||
* @param Collection $expense
|
* @param Collection $expense
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -131,6 +148,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Start date collection setter.
|
||||||
|
*
|
||||||
* @param Carbon $date
|
* @param Carbon $date
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -143,6 +162,8 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Tags collection setter.
|
||||||
|
*
|
||||||
* @param Collection $tags
|
* @param Collection $tags
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -153,26 +174,37 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get the audit report.
|
||||||
|
*
|
||||||
* @param Account $account
|
* @param Account $account
|
||||||
* @param Carbon $date
|
* @param Carbon $date
|
||||||
*
|
*
|
||||||
* @return array
|
* @return array
|
||||||
*
|
*
|
||||||
* @SuppressWarnings(PHPMD.ExcessiveMethodLength) // not that long
|
* @SuppressWarnings(PHPMD.ExcessiveMethodLength) // not that long
|
||||||
|
* @throws FireflyException
|
||||||
*/
|
*/
|
||||||
private function getAuditReport(Account $account, Carbon $date): array
|
private function getAuditReport(Account $account, Carbon $date): array
|
||||||
{
|
{
|
||||||
/** @var CurrencyRepositoryInterface $currencyRepos */
|
/** @var CurrencyRepositoryInterface $currencyRepos */
|
||||||
$currencyRepos = app(CurrencyRepositoryInterface::class);
|
$currencyRepos = app(CurrencyRepositoryInterface::class);
|
||||||
|
|
||||||
|
/** @var AccountRepositoryInterface $accountRepository */
|
||||||
|
$accountRepository = app(AccountRepositoryInterface::class);
|
||||||
|
$accountRepository->setUser($account->user);
|
||||||
|
|
||||||
/** @var JournalCollectorInterface $collector */
|
/** @var JournalCollectorInterface $collector */
|
||||||
$collector = app(JournalCollectorInterface::class);
|
$collector = app(JournalCollectorInterface::class);
|
||||||
$collector->setAccounts(new Collection([$account]))->setRange($this->start, $this->end);
|
$collector->setAccounts(new Collection([$account]))->setRange($this->start, $this->end);
|
||||||
$journals = $collector->getJournals();
|
$journals = $collector->getJournals();
|
||||||
$journals = $journals->reverse();
|
$journals = $journals->reverse();
|
||||||
$dayBeforeBalance = Steam::balance($account, $date);
|
$dayBeforeBalance = app('steam')->balance($account, $date);
|
||||||
$startBalance = $dayBeforeBalance;
|
$startBalance = $dayBeforeBalance;
|
||||||
$currency = $currencyRepos->find((int)$account->getMeta('currency_id'));
|
$currency = $currencyRepos->findNull((int)$accountRepository->getMetaValue($account, 'currency_id'));
|
||||||
|
|
||||||
|
if (null === $currency) {
|
||||||
|
throw new FireflyException('Unexpected NULL value in account currency preference.');
|
||||||
|
}
|
||||||
|
|
||||||
/** @var Transaction $transaction */
|
/** @var Transaction $transaction */
|
||||||
foreach ($journals as $transaction) {
|
foreach ($journals as $transaction) {
|
||||||
@@ -183,17 +215,16 @@ class MonthReportGenerator implements ReportGeneratorInterface
|
|||||||
$transactionAmount = $transaction->transaction_foreign_amount;
|
$transactionAmount = $transaction->transaction_foreign_amount;
|
||||||
}
|
}
|
||||||
|
|
||||||
$newBalance = bcadd($startBalance, $transactionAmount);
|
$newBalance = bcadd($startBalance, $transactionAmount);
|
||||||
$transaction->after = $newBalance;
|
$transaction->after = $newBalance;
|
||||||
$startBalance = $newBalance;
|
$startBalance = $newBalance;
|
||||||
$transaction->currency = $currency;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
$return = [
|
$return = [
|
||||||
'journals' => $journals->reverse(),
|
'journals' => $journals->reverse(),
|
||||||
'exists' => $journals->count() > 0,
|
'exists' => $journals->count() > 0,
|
||||||
'end' => $this->end->formatLocalized((string)trans('config.month_and_day')),
|
'end' => $this->end->formatLocalized((string)trans('config.month_and_day')),
|
||||||
'endBalance' => Steam::balance($account, $this->end),
|
'endBalance' => app('steam')->balance($account, $this->end),
|
||||||
'dayBefore' => $date->formatLocalized((string)trans('config.month_and_day')),
|
'dayBefore' => $date->formatLocalized((string)trans('config.month_and_day')),
|
||||||
'dayBeforeBalance' => $dayBeforeBalance,
|
'dayBeforeBalance' => $dayBeforeBalance,
|
||||||
];
|
];
|
||||||
|
@@ -27,5 +27,4 @@ namespace FireflyIII\Generator\Report\Audit;
|
|||||||
*/
|
*/
|
||||||
class MultiYearReportGenerator extends MonthReportGenerator
|
class MultiYearReportGenerator extends MonthReportGenerator
|
||||||
{
|
{
|
||||||
// Doesn't do anything different.
|
|
||||||
}
|
}
|
||||||
|
@@ -27,5 +27,4 @@ namespace FireflyIII\Generator\Report\Audit;
|
|||||||
*/
|
*/
|
||||||
class YearReportGenerator extends MonthReportGenerator
|
class YearReportGenerator extends MonthReportGenerator
|
||||||
{
|
{
|
||||||
// Doesn't do anything different.
|
|
||||||
}
|
}
|
||||||
|
@@ -18,6 +18,8 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
/** @noinspection PhpUndefinedMethodInspection */
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Generator\Report\Budget;
|
namespace FireflyIII\Generator\Report\Budget;
|
||||||
@@ -39,17 +41,15 @@ use Log;
|
|||||||
*/
|
*/
|
||||||
class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
||||||
{
|
{
|
||||||
/** @var Collection */
|
/** @var Collection The accounts in the report. */
|
||||||
private $accounts;
|
private $accounts;
|
||||||
/** @var Collection */
|
/** @var Collection The budgets in the report. */
|
||||||
private $budgets;
|
private $budgets;
|
||||||
/** @var Carbon */
|
/** @var Carbon The end date. */
|
||||||
private $end;
|
private $end;
|
||||||
/** @var Collection */
|
/** @var Collection The expenses in the report. */
|
||||||
private $expenses;
|
private $expenses;
|
||||||
/** @var Collection */
|
/** @var Carbon The start date. */
|
||||||
private $income;
|
|
||||||
/** @var Carbon */
|
|
||||||
private $start;
|
private $start;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -57,12 +57,14 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
*/
|
*/
|
||||||
public function __construct()
|
public function __construct()
|
||||||
{
|
{
|
||||||
$this->income = new Collection;
|
|
||||||
$this->expenses = new Collection;
|
$this->expenses = new Collection;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Generates the report.
|
||||||
|
*
|
||||||
* @return string
|
* @return string
|
||||||
|
* @throws \Throwable
|
||||||
*/
|
*/
|
||||||
public function generate(): string
|
public function generate(): string
|
||||||
{
|
{
|
||||||
@@ -83,6 +85,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the involved accounts.
|
||||||
|
*
|
||||||
* @param Collection $accounts
|
* @param Collection $accounts
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -95,6 +99,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the involved budgets.
|
||||||
|
*
|
||||||
* @param Collection $budgets
|
* @param Collection $budgets
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -107,6 +113,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Unused category setter.
|
||||||
|
*
|
||||||
* @param Collection $categories
|
* @param Collection $categories
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -117,6 +125,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the end date of the report.
|
||||||
|
*
|
||||||
* @param Carbon $date
|
* @param Carbon $date
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -129,6 +139,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Unused expense setter.
|
||||||
|
*
|
||||||
* @param Collection $expense
|
* @param Collection $expense
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -139,6 +151,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the start date of the report.
|
||||||
|
*
|
||||||
* @param Carbon $date
|
* @param Carbon $date
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -151,6 +165,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Unused tags setter.
|
||||||
|
*
|
||||||
* @param Collection $tags
|
* @param Collection $tags
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -161,6 +177,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get the expenses.
|
||||||
|
*
|
||||||
* @return Collection
|
* @return Collection
|
||||||
*/
|
*/
|
||||||
protected function getExpenses(): Collection
|
protected function getExpenses(): Collection
|
||||||
@@ -188,6 +206,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Summarize a collection by its budget.
|
||||||
|
*
|
||||||
* @param Collection $collection
|
* @param Collection $collection
|
||||||
*
|
*
|
||||||
* @return array
|
* @return array
|
||||||
|
@@ -27,5 +27,4 @@ namespace FireflyIII\Generator\Report\Budget;
|
|||||||
*/
|
*/
|
||||||
class MultiYearReportGenerator extends MonthReportGenerator
|
class MultiYearReportGenerator extends MonthReportGenerator
|
||||||
{
|
{
|
||||||
// Doesn't do anything different.
|
|
||||||
}
|
}
|
||||||
|
@@ -27,5 +27,4 @@ namespace FireflyIII\Generator\Report\Budget;
|
|||||||
*/
|
*/
|
||||||
class YearReportGenerator extends MonthReportGenerator
|
class YearReportGenerator extends MonthReportGenerator
|
||||||
{
|
{
|
||||||
// Doesn't do anything different.
|
|
||||||
}
|
}
|
||||||
|
@@ -18,6 +18,8 @@
|
|||||||
* You should have received a copy of the GNU General Public License
|
* You should have received a copy of the GNU General Public License
|
||||||
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
* along with Firefly III. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
/** @noinspection MultipleReturnStatementsInspection */
|
||||||
|
/** @noinspection PhpUndefinedMethodInspection */
|
||||||
declare(strict_types=1);
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace FireflyIII\Generator\Report\Category;
|
namespace FireflyIII\Generator\Report\Category;
|
||||||
@@ -40,17 +42,17 @@ use Log;
|
|||||||
*/
|
*/
|
||||||
class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
||||||
{
|
{
|
||||||
/** @var Collection */
|
/** @var Collection The included accounts */
|
||||||
private $accounts;
|
private $accounts;
|
||||||
/** @var Collection */
|
/** @var Collection The included categories */
|
||||||
private $categories;
|
private $categories;
|
||||||
/** @var Carbon */
|
/** @var Carbon The end date */
|
||||||
private $end;
|
private $end;
|
||||||
/** @var Collection */
|
/** @var Collection The expenses */
|
||||||
private $expenses;
|
private $expenses;
|
||||||
/** @var Collection */
|
/** @var Collection The income in the report. */
|
||||||
private $income;
|
private $income;
|
||||||
/** @var Carbon */
|
/** @var Carbon The start date. */
|
||||||
private $start;
|
private $start;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -63,7 +65,10 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Generates the report.
|
||||||
|
*
|
||||||
* @return string
|
* @return string
|
||||||
|
* @throws \Throwable
|
||||||
*/
|
*/
|
||||||
public function generate(): string
|
public function generate(): string
|
||||||
{
|
{
|
||||||
@@ -101,6 +106,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the involved accounts.
|
||||||
|
*
|
||||||
* @param Collection $accounts
|
* @param Collection $accounts
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -113,6 +120,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Empty budget setter.
|
||||||
|
*
|
||||||
* @param Collection $budgets
|
* @param Collection $budgets
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -123,6 +132,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the categories involved in this report.
|
||||||
|
*
|
||||||
* @param Collection $categories
|
* @param Collection $categories
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -135,6 +146,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the end date for this report.
|
||||||
|
*
|
||||||
* @param Carbon $date
|
* @param Carbon $date
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -147,6 +160,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the expenses involved in this report.
|
||||||
|
*
|
||||||
* @param Collection $expense
|
* @param Collection $expense
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -157,6 +172,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Set the start date for this report.
|
||||||
|
*
|
||||||
* @param Carbon $date
|
* @param Carbon $date
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -169,6 +186,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Unused tag setter.
|
||||||
|
*
|
||||||
* @param Collection $tags
|
* @param Collection $tags
|
||||||
*
|
*
|
||||||
* @return ReportGeneratorInterface
|
* @return ReportGeneratorInterface
|
||||||
@@ -179,6 +198,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get the expenses for this report.
|
||||||
|
*
|
||||||
* @return Collection
|
* @return Collection
|
||||||
*/
|
*/
|
||||||
protected function getExpenses(): Collection
|
protected function getExpenses(): Collection
|
||||||
@@ -206,6 +227,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Get the income for this report.
|
||||||
|
*
|
||||||
* @return Collection
|
* @return Collection
|
||||||
*/
|
*/
|
||||||
protected function getIncome(): Collection
|
protected function getIncome(): Collection
|
||||||
@@ -230,6 +253,8 @@ class MonthReportGenerator extends Support implements ReportGeneratorInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
* Summarize the category.
|
||||||
|
*
|
||||||
* @param Collection $collection
|
* @param Collection $collection
|
||||||
*
|
*
|
||||||
* @return array
|
* @return array
|
||||||
|
@@ -27,5 +27,4 @@ namespace FireflyIII\Generator\Report\Category;
|
|||||||
*/
|
*/
|
||||||
class MultiYearReportGenerator extends MonthReportGenerator
|
class MultiYearReportGenerator extends MonthReportGenerator
|
||||||
{
|
{
|
||||||
// Doesn't do anything different.
|
|
||||||
}
|
}
|
||||||
|
@@ -27,5 +27,4 @@ namespace FireflyIII\Generator\Report\Category;
|
|||||||
*/
|
*/
|
||||||
class YearReportGenerator extends MonthReportGenerator
|
class YearReportGenerator extends MonthReportGenerator
|
||||||
{
|
{
|
||||||
// Doesn't do anything different.
|
|
||||||
}
|
}
|
||||||
|
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user