More bug fixes, especially around reversals of charges that have been paid from something other than customer money (such as waivers). I suspect it still will not work correctly for concession, depending on your point of view. Either concession should not count as customer credit, since they never paid that money, or it should since they were told they would get $X off, and upon charge reversal, they no longer get the credit. It seems they would only get the credit when reversing a mistaken charge, in which case, the user can manually provide a new concession.

git-svn-id: file:///svn-source/pmgr/branches/surplus_account_20090815@588 97e9348a-65ac-dc4b-aefc-98561f571b83
This commit is contained in:
abijah
2009-08-16 22:35:02 +00:00
parent 1b02be19f0
commit 080c82fc10
2 changed files with 49 additions and 48 deletions

View File

@@ -400,7 +400,6 @@ class StatementEntry extends AppModel {
'LedgerEntry' =>
array('conditions' =>
array('LedgerEntry.account_id <> Transaction.account_id')
//$this->Account->accountReceivableAccountID()),
),
),
'conditions' => array('Transaction.id' => $receipt_id),

View File

@@ -467,7 +467,7 @@ class Transaction extends AppModel {
return $this->prReturn(array('error' => true));
// Make use of the work done by splitEntries
$transaction = array_filter($transaction) + $result['transaction'];
$transaction = $this->filter_null($transaction) + $result['transaction'];
$entries = $result['entries'];
extract($result['vars']);
@@ -496,16 +496,20 @@ class Transaction extends AppModel {
elseif (is_array($control['assign']))
$assign_ops = $control['assign'];
elseif (is_bool($control['assign']))
$assign_ops = array('assign', 'create');
$assign_ops = (empty($control['assign_receipt'])
? array('assign')
: array('assign', 'create'));
else
$this->INTERNAL_ERROR('Invalid control[assign] parameter');
$this->pr(17, compact('assign_ops'), 'Credit operations');
// Go through the requested assignment mechanisms
foreach ($assign_ops AS $method) {
if (!empty($ret['error']))
break;
$this->pr(17, compact('method'), 'Assigning credits');
$this->pr(17, compact('method'), 'Handling credits');
if ($method === 'assign') {
$result = $this->StatementEntry->assignCredits
@@ -518,33 +522,34 @@ class Transaction extends AppModel {
$transaction['lease_id']
);
}
elseif ($method === 'create') {
$stats = $this->stats($transaction['id']);
if ($stats['undisbursed'] < 0)
elseif ($method === 'create' || is_numeric($method)) {
if (is_numeric($method))
$credit_amount = $method;
else {
$stats = $this->stats($transaction['id']);
$credit_amount = $stats['undisbursed'];
}
if ($credit_amount < 0)
$this->INTERNAL_ERROR('Receipt has negative undisbursed balance');
if (empty($stats['undisbursed']))
if (empty($credit_amount))
continue;
$result = $this->addTransactionEntries
(array('include_ledger_entry' => true,
'include_statement_entry' => true),
array('crdr' => 'DEBIT') + $transaction,
array(array('type' => 'SURPLUS',
'account_id' => $this->Account->accountPayableAccountID(),
'amount' => $stats['undisbursed'],
array(array('type' => 'SURPLUS',
'account_id' => $this->Account->customerCreditAccountID(),
'amount' => $credit_amount,
),
));
// Verify the explicit credit worked.
$stats = $this->stats($transaction['id']);
if (!empty($stats['undisbursed']))
$this->INTERNAL_ERROR('Explicit credit did not resolve receipt balance');
}
else
$this->INTERNAL_ERROR('Invalid assign method');
$ret[$method] = $result;
$ret['credit'][$method] = $result;
if (!empty($result['error']))
$ret['error'] = true;
}
@@ -580,7 +585,7 @@ class Transaction extends AppModel {
return $this->prReturn(array('error' => true));
// Make use of the work done by splitEntries
$transaction = array_filter($transaction) + $result['transaction'];
$transaction = $this->filter_null($transaction) + $result['transaction'];
$entries = $result['entries'];
extract($result['vars']);
@@ -999,8 +1004,7 @@ class Transaction extends AppModel {
// These are all disbursements against the charge we're reversing
$rollback =
array('control' =>
array('assign' => array('create', 'assign'),
'include_ledger_entry' => false,
array('include_ledger_entry' => false,
'include_statement_entry' => true,
),
@@ -1009,7 +1013,7 @@ class Transaction extends AppModel {
'type' => 'CREDIT_NOTE',
'crdr' => 'CREDIT',
'account_id' => $this->Account->accountReceivableAccountID(),
//'amount' => $charge['StatementEntry']['amount'],
'amount' => $charge['StatementEntry']['amount'],
'customer_id' => $charge['StatementEntry']['customer_id'],
'lease_id' => null,
'comment' => $comment,
@@ -1029,7 +1033,7 @@ class Transaction extends AppModel {
'charge_entry_id' => $charge['StatementEntry']['id'],
);
$credit = 0;
$customer_credit = 0;
foreach ($disb_entries['DisbursementEntry'] AS $disbursement) {
$rollback['Entry'][] =
array(
@@ -1038,34 +1042,27 @@ class Transaction extends AppModel {
'force_positive' => true,
'type' => $disbursement['type'],
//'type' => 'REVERSAL',
'amount' => -1 * $disbursement['amount'],
'account_id' => $disbursement['account_id'],
'account_id' =>
($disbursement['type'] === 'DISBURSEMENT'
? $this->Account->customerCreditAccountID()
: $disbursement['account_id']),
'customer_id' => $disbursement['customer_id'],
'lease_id' => $disbursement['lease_id'],
'charge_entry_id' => $disbursement['charge_entry_id'],
);
if ($disbursement['type'] === 'DISBURSEMENT')
$credit += $disbursement['amount'];
$customer_credit += $disbursement['amount'];
}
// Add the customer surplus entry for this transaction
$rollback['Transaction']['amount'] = $credit;
if (0 && $credit > 0) {
$rollback['Entry'][] =
array('include_ledger_entry' => true,
'include_statement_entry' => true,
//'force_positive' => true,
'swap_crdr' => true,
'type' => 'SURPLUS',
'account_id' => $this->Account->accountPayableAccountID(),
'amount' => $credit,
'customer_id' => $charge['StatementEntry']['customer_id'],
//'lease_id' => $charge['StatementEntry']['lease_id'],
//'charge_entry_id' => $charge['StatementEntry']['id'],
);
}
// Create an explicit surplus entry for the customer credit.
// Do it BEFORE assigning credits to outstanding charges to
// ensure that those charges are paid from the customer surplus
// account thus and we don't end up with bizarre disbursements,
// like having Rent paid from Damage (or whatever account the
// reversed charge came from).
$rollback['control']['assign'] = array($customer_credit, 'assign');
// Record the transaction, which will un-disburse previously
// disbursed payments, and other similar work.
@@ -1167,7 +1164,14 @@ class Transaction extends AppModel {
if (empty($query['fields']))
$query['fields'] = array();
$stats = array();
// Get the overall total
$squery = $query;
$squery['fields'][] = "SUM(Transaction.amount) AS total";
$squery['fields'][] = "COUNT(Transaction.id) AS count";
$stats = $this->find('first', $squery);
$stats = $stats[0];
unset($stats[0]);
foreach ($this->hasMany AS $table => $association) {
// Only calculate stats for *Entry types
if (!preg_match("/Entry$/", $table) &&
@@ -1206,12 +1210,10 @@ class Transaction extends AppModel {
unset($stats[$table][0]);
}
if (!empty($id)) {
$this->id = $id;
$stats['total'] = $this->field('amount');
$stats['uncharged'] = $stats['total'] - $stats['StatementEntry']['charges'];
$stats['undisbursed'] = $stats['total'] - $stats['StatementEntry']['disbursements'];
}
// Add summary data, which may or may not be useful
// or even meaningful, depending on what the caller
// has queried (it's up to them to make that decision).
$stats['undisbursed'] = $stats['total'] - $stats['StatementEntry']['disbursements'];
return $this->prReturn($stats);
}