First pass at making ACH items auto-deposit. Things are really set up for a separate deposit transaction though, and I should just bite the bullet and do that instead. I don't want them to show up as Deposits though, but perhaps it would be easiest just to make a new type 'AUTO_DEPOSIT' or something.

git-svn-id: file:///svn-source/pmgr/branches/yafr_20090716@607 97e9348a-65ac-dc4b-aefc-98561f571b83
This commit is contained in:
abijah
2009-08-17 21:16:16 +00:00
parent 3eb989e03c
commit 709689b15b
4 changed files with 225 additions and 22 deletions

View File

@@ -50,7 +50,7 @@ class Transaction extends AppModel {
);
//var $default_log_level = array('log' => 30, 'show' => 15);
var $default_log_level = array('log' => 30, 'show' => 15);
//var $max_log_level = 10;
/**************************************************************************
@@ -121,23 +121,180 @@ class Transaction extends AppModel {
'lease_id' => $lease_id,
);
// Go through the statement entries and flag as disbursements
foreach ($data['Entry'] AS &$entry)
$entry += array('type' => 'DISBURSEMENT', // not used
'account_id' =>
(isset($entry['Tender']['tender_type_id'])
? ($this->LedgerEntry->Tender->TenderType->
accountID($entry['Tender']['tender_type_id']))
: null),
);
// Go through the statement entries, making sure the tender
// is recorded into the correct account, and then performing
// an auto-deposit if necessary.
$deposit = array();
foreach ($data['Entry'] AS &$entry) {
if (empty($entry['Tender']['tender_type_id']))
continue;
$ttype = $this->LedgerEntry->Tender->TenderType->find
('first', array('contain' => false,
'conditions' =>
array('id' => $entry['Tender']['tender_type_id'])));
$ttype = $ttype['TenderType'];
// Set the account for posting.
$entry += array('account_id' => $ttype['account_id']);
/* // Check for auto deposit */
/* if (!empty($ttype['auto_deposit'])) { */
/* $deposit[] = array('id' => 0, */
/* 'account_id' => $ttype['deposit_account_id']); */
/* } */
}
unset($entry); // prevent trouble since $entry is reference
$ids = $this->addTransaction($data['control'], $data['Transaction'], $data['Entry']);
if (isset($ids['transaction_id']))
$ids['receipt_id'] = $ids['transaction_id'];
if (!empty($ids['error']))
return $this->prReturn(array('error' => true) + $ids);
$tender_ids = array();
foreach ($ids['entries'] AS $entry) {
$entry1 = $entry['DoubleEntry']['Entry1'];
if (!empty($entry1['Tender']['tender_id']))
$tender_ids[] = $entry1['Tender']['tender_id'];
}
$deposit_tenders = $this->LedgerEntry->Tender->find
('all', array('contain' => array('TenderType' => array('fields' => array()),
'LedgerEntry' => array('fields' => array()),
),
'fields' => array('TenderType.deposit_account_id',
'TenderType.account_id',
'CONCAT("CREDIT") AS crdr',
'CONCAT("Auto Deposit") AS comment',
'SUM(LedgerEntry.amount) AS amount'),
'conditions' => array('Tender.id' => $tender_ids,
'TenderType.auto_deposit' => true,
),
'group' => 'TenderType.deposit_account_id',
));
if (!empty($deposit_tenders)) {
foreach ($deposit_tenders AS &$tender)
$tender = $tender[0] + array_diff_key($tender['TenderType'], array('id'=>1));
$this->pr(10, compact('tender_ids', 'deposit_tenders'));
// REVISIT <AP>: 20090817
// Multiple tenders could result in deposits to more than one
// account. We're already mucking with things by having a
// ledger entry that's not involved with the account_id of the
// transaction. We could handle this by not using the helper
// _splitEntries function, and just building or individual
// entries right here (which we should probably do anyway).
// However, I'm ignoring the issue for now...
if (count($deposit_tenders) > 1)
$this->INTERNAL_ERROR("Only expecting one tender type");
$deposit_ids = $this->addTransactionEntries
(array('include_ledger_entry' => true,
'include_statement_entry' => false,
),
array('id' => $ids['transaction_id'],
// REVISIT <AP>: 20090817
// This is an awful cheat, and we're going to
// get burned from it someday.
'type' => 'DEPOSIT',
'crdr' => 'DEBIT',
'account_id' => $deposit_tenders[0]['deposit_account_id'],
),
$deposit_tenders);
$ids['deposit'] = $deposit_ids;
if (!empty($deposit_ids['error']))
return $this->prReturn(array('error' => true) + $ids);
if (!empty($tender_ids))
$this->LedgerEntry->Tender->updateAll
(array('Tender.deposit_transaction_id' => $ids['transaction_id']),
array('Tender.id' => $tender_ids)
);
}
return $this->prReturn($ids);
}
// REVISIT <AP>: 20090817
// Delete after rolling up the old items
function temp_auto_deposit_old_ach_items() {
$all_tenders = $this->LedgerEntry->Tender->find
('all', array('link' => array('TenderType',
'LedgerEntry' =>
array('Transaction')),
'conditions' => array(array('TenderType.auto_deposit' => true),
array('Tender.deposit_transaction_id' => null)),
));
//$this->pr(10, compact('all_tenders'));
foreach ($all_tenders AS $cur_tender) {
$tender_ids = array($cur_tender['Tender']['id']);
$ids = array('transaction_id' => $cur_tender['Transaction']['id']);
$tenders = $this->LedgerEntry->Tender->find
('all', array('contain' => array('TenderType' => array('fields' => array()),
'LedgerEntry' => array('fields' => array()),
),
'fields' => array('TenderType.deposit_account_id',
'TenderType.account_id',
'CONCAT("CREDIT") AS crdr',
'CONCAT("Auto Deposit") AS comment',
'SUM(LedgerEntry.amount) AS amount'),
'conditions' => array('Tender.id' => $tender_ids,
'TenderType.auto_deposit' => true,
),
'group' => 'TenderType.deposit_account_id',
));
foreach ($tenders AS &$tender)
$tender = $tender[0] + array_diff_key($tender['TenderType'], array('id'=>1));
$this->pr(10, compact('tender_ids', 'tenders'));
// REVISIT <AP>: 20090817
// Multiple tenders could result in deposits to more than one
// account. We're already mucking with things by having a
// ledger entry that's not involved with the account_id of the
// transaction. We could handle this by not using the helper
// _splitEntries function, and just building or individual
// entries right here (which we should probably do anyway).
// However, I'm ignoring the issue for now...
if (count($tenders) > 1)
$this->INTERNAL_ERROR("Only expecting one tender type");
$deposit_ids = $this->addTransactionEntries
(array('include_ledger_entry' => true,
'include_statement_entry' => false,
),
array('id' => $ids['transaction_id'],
// REVISIT <AP>: 20090817
// This is an awful cheat, and we're going to
// get burned from it someday.
'type' => 'DEPOSIT',
'crdr' => 'DEBIT',
'account_id' => $tenders[0]['deposit_account_id'],
),
$tenders);
if (empty($deposit_ids['error'])) {
if (!empty($tender_ids))
$this->LedgerEntry->Tender->updateAll
(array('Tender.deposit_transaction_id' => $ids['transaction_id']),
array('Tender.id' => $tender_ids)
);
}
}
}
/**************************************************************************
**************************************************************************
@@ -279,6 +436,7 @@ class Transaction extends AppModel {
array('assign' => false,
'include_ledger_entry' => true,
'include_statement_entry' => false,
'allow_no_entries' => true,
);
// Establish the transaction as a close
@@ -656,7 +814,7 @@ class Transaction extends AppModel {
// Verify that we have a transaction and entries
if (empty($transaction) ||
($transaction['type'] !== 'CLOSE' && empty($entries)))
(empty($entries) && empty($control['allow_no_entries'])))
return $this->prReturn(array('error' => true));
// set ledger ID as the current ledger of the specified account
@@ -902,16 +1060,20 @@ class Transaction extends AppModel {
}
}
// Add the sole ledger entry for this transaction
$rollback['Entry'][] =
array('include_ledger_entry' => true,
'include_statement_entry' => false,
'amount' => $rollback['Transaction']['amount'],
'account_id' => $this->Account->accountReceivableAccountID(),
);
// Add the sole ledger entry for this transaction. If there
// is not a transaction amount, then there is no point in
// recording a ledger entry of $0.00
if (!empty($rollback['Transaction']['amount'])) {
$rollback['Entry'][] =
array('include_ledger_entry' => true,
'include_statement_entry' => false,
'amount' => $rollback['Transaction']['amount'],
'account_id' => $this->Account->accountReceivableAccountID(),
);
// Set the transaction amount to be negative
$rollback['Transaction']['amount'] *= -1;
// Set the transaction amount to be negative
$rollback['Transaction']['amount'] *= -1;
}
// Record the transaction, which will un-pay previously paid
// charges, void any credits, and other similar work.
@@ -966,8 +1128,12 @@ class Transaction extends AppModel {
}
}
}
if (empty($ret['rollback']['error']) && empty($ret['nsf_ledger_entry_id']))
$this->INTERNAL_ERROR("NSF LE ID not found under rollback entries");
if (empty($ret['rollback']['error']) && empty($ret['nsf_ledger_entry_id'])) {
//$this->INTERNAL_ERROR("NSF LE ID not found under rollback entries");
// Actually, this can happen if an item is NSF without having ever
// been applied to any charges.
$ret['nsf_ledger_entry_id'] = null;
}
$ret['nsf_transaction_id'] = $ret['bounce']['transaction_id'];
return $this->prReturn($ret + array('error' => false));