Fixed a bug where the transaction list was a giant mess.

This commit is contained in:
James Cole
2014-11-12 21:19:31 +01:00
parent ab508a3d9e
commit 44d189d7d3
5 changed files with 180 additions and 139 deletions

View File

@@ -6,9 +6,9 @@ use Carbon\Carbon;
use FireflyIII\Database\Ifaces\AccountInterface;
use FireflyIII\Database\Ifaces\CommonDatabaseCalls;
use FireflyIII\Database\Ifaces\CUD;
use Illuminate\Support\Collection;
use Illuminate\Support\MessageBag;
use LaravelBook\Ardent\Ardent;
use Illuminate\Support\Collection;
/**
* Class Account
@@ -29,13 +29,13 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
/**
* @param Ardent $model
* @param array $data
* @param array $data
*
* @return bool
*/
public function update(Ardent $model, array $data)
{
$model->name = $data['name'];
$model->name = $data['name'];
$model->active = isset($data['active']) ? intval($data['active']) : 0;
$model->save();
@@ -58,6 +58,23 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
return true;
}
/**
* @param \Account $account
*
* @return \TransactionJournal|null
*/
public function openingBalanceTransaction(\Account $account)
{
return \TransactionJournal::withRelevantData()
->accountIs($account)
->leftJoin(
'transaction_types', 'transaction_types.id', '=',
'transaction_journals.transaction_type_id'
)
->where('transaction_types.type', 'Opening balance')
->first(['transaction_journals.*']);
}
/**
* Get all asset accounts. Optional JSON based parameters.
*
@@ -71,21 +88,6 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
}
/**
* @param \Account $account
*
* @return \Account|null
*/
public function findInitialBalanceAccount(\Account $account)
{
/** @var \FireflyIII\Database\AccountType $acctType */
$acctType = \App::make('FireflyIII\Database\AccountType');
$accountType = $acctType->findByWhat('initial');
return $this->getUser()->accounts()->where('account_type_id', $accountType->id)->where('name', 'LIKE', $account->name . '%')->first();
}
/**
* @param array $types
* @param array $parameters
@@ -146,19 +148,26 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
}
/**
* @return int
* @param \Account $account
*
* @return \Account|null
*/
public function countAssetAccounts()
public function findInitialBalanceAccount(\Account $account)
{
return $this->countAccountsByType(['Default account', 'Asset account']);
/** @var \FireflyIII\Database\AccountType $acctType */
$acctType = \App::make('FireflyIII\Database\AccountType');
$accountType = $acctType->findByWhat('initial');
return $this->getUser()->accounts()->where('account_type_id', $accountType->id)->where('name', 'LIKE', $account->name . '%')->first();
}
/**
* @return int
*/
public function countExpenseAccounts()
public function countAssetAccounts()
{
return $this->countAccountsByType(['Expense account', 'Beneficiary account']);
return $this->countAccountsByType(['Default account', 'Asset account']);
}
/**
@@ -171,6 +180,14 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
return $this->getUser()->accounts()->accountTypeIn($types)->count();
}
/**
* @return int
*/
public function countExpenseAccounts()
{
return $this->countAccountsByType(['Expense account', 'Beneficiary account']);
}
/**
* @param array $parameters
*
@@ -200,7 +217,24 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
*/
public function find($id)
{
// TODO: Implement find() method.
return $this->getUser()->accounts()->find($id);
}
public function firstExpenseAccountOrCreate($name)
{
/** @var \FireflyIII\Database\AccountType $accountTypeRepos */
$accountTypeRepos = \App::make('FireflyIII\Database\AccountType');
$accountType = $accountTypeRepos->findByWhat('expense');
$data = [
'user_id' => $this->getUser()->id,
'account_type_id' => $accountType->id,
'name' => $name,
'active' => 1
];
return \Account::firstOrCreate($data);
}
/**
@@ -247,23 +281,6 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
}
/**
* @param \Account $account
*
* @return \TransactionJournal|null
*/
public function openingBalanceTransaction(\Account $account)
{
return \TransactionJournal::withRelevantData()
->accountIs($account)
->leftJoin(
'transaction_types', 'transaction_types.id', '=',
'transaction_journals.transaction_type_id'
)
->where('transaction_types.type', 'Opening balance')
->first(['transaction_journals.*']);
}
/**
* Validates a model. Returns an array containing MessageBags
* errors/warnings/successes.
@@ -287,9 +304,9 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
*/
public function validate(array $model)
{
$warnings = new MessageBag;
$warnings = new MessageBag;
$successes = new MessageBag;
$errors = new MessageBag;
$errors = new MessageBag;
/*
* Name validation:
@@ -343,8 +360,8 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
$successes->add('openingbalancedate', 'OK');
}
return [
'errors' => $errors,
'warnings' => $warnings,
'errors' => $errors,
'warnings' => $warnings,
'successes' => $successes
];
}
@@ -365,12 +382,12 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
$accountType = $acctType->findByWhat($data['what']);
$data['user_id'] = $this->getUser()->id;
$data['user_id'] = $this->getUser()->id;
$data['account_type_id'] = $accountType->id;
$data['active'] = isset($data['active']) && $data['active'] === '1' ? 1 : 0;
$data['active'] = isset($data['active']) && $data['active'] === '1' ? 1 : 0;
$data = array_except($data, array('_token', 'what'));
$data = array_except($data, array('_token', 'what'));
$account = new \Account($data);
if (!$account->validate()) {
var_dump($account->errors()->all());
@@ -391,16 +408,16 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
/**
* @param \Account $account
* @param array $data
* @param array $data
*
* @return bool
*/
public function storeInitialBalance(\Account $account, array $data)
{
$opposingData = [
'name' => $account->name . ' Initial Balance',
$opposingData = [
'name' => $account->name . ' Initial Balance',
'active' => 0,
'what' => 'initial'
'what' => 'initial'
];
$opposingAccount = $this->store($opposingData);
@@ -408,28 +425,28 @@ class Account implements CUD, CommonDatabaseCalls, AccountInterface
* Create a journal from opposing to account or vice versa.
*/
$balance = floatval($data['openingbalance']);
$date = new Carbon($data['openingbalancedate']);
$date = new Carbon($data['openingbalancedate']);
/** @var \FireflyIII\Database\TransactionJournal $tj */
$tj = \App::make('FireflyIII\Database\TransactionJournal');
if ($balance < 0) {
// first transaction draws money from the new account to the opposing
$from = $account;
$to = $opposingAccount;
$to = $opposingAccount;
} else {
// first transaction puts money into account
$from = $opposingAccount;
$to = $account;
$to = $account;
}
// data for transaction journal:
$balance = $balance < 0 ? $balance * -1 : $balance;
$opening = [
'what' => 'opening',
'currency' => 'EUR',
'amount' => $balance,
'from' => $from,
'to' => $to,
'date' => $date,
'what' => 'opening',
'currency' => 'EUR',
'amount' => $balance,
'from' => $from,
'to' => $to,
'date' => $date,
'description' => 'Opening balance for new account ' . $account->name,
];

View File

@@ -240,7 +240,7 @@ class TransactionJournal implements TransactionJournalInterface, CUD, CommonData
$errors->add('account_to_id', 'Invalid account selected.');
} else {
if (intval($model['account_from_id']) == intval($model['account_from_id'])) {
if (intval($model['account_from_id']) == intval($model['account_to_id'])) {
$errors->add('account_to_id', 'Cannot be the same as "from" account.');
$errors->add('account_from_id', 'Cannot be the same as "to" account.');
} else {
@@ -319,6 +319,9 @@ class TransactionJournal implements TransactionJournalInterface, CUD, CommonData
/** @var \FireflyIII\Database\TransactionType $typeRepository */
$typeRepository = \App::make('FireflyIII\Database\TransactionType');
/** @var \FireflyIII\Database\Account $accountRepository */
$accountRepository = \App::make('FireflyIII\Database\Account');
/** @var \FireflyIII\Database\TransactionCurrency $currencyRepository */
$currencyRepository = \App::make('FireflyIII\Database\TransactionCurrency');
@@ -335,17 +338,33 @@ class TransactionJournal implements TransactionJournalInterface, CUD, CommonData
$journal->description = $data['description'];
$journal->date = $data['date'];
$journal->completed = 0;
//$journal->user_id = $this->getUser()->id;
/*
* This must be enough to store the journal:
*/
if (!$journal->validate()) {
\Log::error($journal->errors()->all());
throw new FireflyException('store() transactionjournal failed, but it should not!');
throw new FireflyException('store() transaction journal failed, but it should not!');
}
$journal->save();
/*
* Still need to find the accounts related to the transactions.
* This depends on the type of transaction.
*/
switch ($data['what']) {
case 'withdrawal':
$data['from'] = $accountRepository->find($data['account_id']);
$data['to'] = $accountRepository->firstExpenseAccountOrCreate($data['expense_account']);
break;
case 'opening':
break;
default:
throw new FireflyException('Cannot save transaction journal with accounts based on $what "' . $data['what'] . '".');
break;
}
/*
* Then store both transactions.
*/

View File

@@ -3,11 +3,12 @@
namespace FireflyIII\Database;
use Illuminate\Support\Collection;
use LaravelBook\Ardent\Ardent;
use FireflyIII\Database\Ifaces\CommonDatabaseCalls;
use FireflyIII\Database\Ifaces\CUD;
use FireflyIII\Database\Ifaces\TransactionTypeInterface;
use FireflyIII\Exception\FireflyException;
use Illuminate\Support\Collection;
use LaravelBook\Ardent\Ardent;
/**
* Class TransactionType
@@ -98,10 +99,17 @@ class TransactionType implements TransactionTypeInterface, CUD, CommonDatabaseCa
case 'opening':
return \TransactionType::whereType('Opening balance')->first();
break;
case 'transfer':
return \TransactionType::whereType('Transfer')->first();
break;
case 'withdrawal':
return \TransactionType::whereType('Withdrawal')->first();
break;
default:
throw new FireflyException('Cannot find transaction type described as "' . e($what) . '".');
break;
}
return null;
}
@@ -118,7 +126,7 @@ class TransactionType implements TransactionTypeInterface, CUD, CommonDatabaseCa
/**
* @param Ardent $model
* @param array $data
* @param array $data
*
* @return bool
*/