1
|
|
|
<?php |
2
|
|
|
|
3
|
|
|
namespace OfxParser; |
4
|
|
|
|
5
|
|
|
use SimpleXMLElement; |
6
|
|
|
use OfxParser\Utils; |
7
|
|
|
use OfxParser\Entities\AccountInfo; |
8
|
|
|
use OfxParser\Entities\BankAccount; |
9
|
|
|
use OfxParser\Entities\Institute; |
10
|
|
|
use OfxParser\Entities\SignOn; |
11
|
|
|
use OfxParser\Entities\Statement; |
12
|
|
|
use OfxParser\Entities\Status; |
13
|
|
|
use OfxParser\Entities\Transaction; |
14
|
|
|
|
15
|
|
|
/** |
16
|
|
|
* The OFX object |
17
|
|
|
* |
18
|
|
|
* Heavily refactored from Guillaume Bailleul's grimfor/ofxparser |
19
|
|
|
* |
20
|
|
|
* Second refactor by Oliver Lowe to unify the API across all |
21
|
|
|
* OFX data-types. |
22
|
|
|
* |
23
|
|
|
* Based on Andrew A Smith's Ruby ofx-parser |
24
|
|
|
* |
25
|
|
|
* @author Guillaume BAILLEUL <[email protected]> |
26
|
|
|
* @author James Titcumb <[email protected]> |
27
|
|
|
* @author Oliver Lowe <[email protected]> |
28
|
|
|
*/ |
29
|
|
|
class Ofx |
30
|
|
|
{ |
31
|
|
|
/** |
32
|
|
|
* @var Header[] |
33
|
|
|
*/ |
34
|
|
|
public $header = []; |
35
|
|
|
|
36
|
|
|
/** |
37
|
|
|
* @var SignOn |
38
|
|
|
*/ |
39
|
|
|
public $signOn; |
40
|
|
|
|
41
|
|
|
/** |
42
|
|
|
* @var AccountInfo[] |
43
|
|
|
*/ |
44
|
|
|
public $signupAccountInfo; |
45
|
|
|
|
46
|
|
|
/** |
47
|
|
|
* @var BankAccount[] |
48
|
|
|
*/ |
49
|
|
|
public $bankAccounts = []; |
50
|
|
|
|
51
|
|
|
/** |
52
|
|
|
* Only populated if there is only one bank account |
53
|
|
|
* @var BankAccount|null |
54
|
|
|
* @deprecated This will be removed in future versions |
55
|
|
|
*/ |
56
|
|
|
public $bankAccount; |
57
|
|
|
|
58
|
|
|
/** |
59
|
|
|
* @param SimpleXMLElement $xml |
60
|
|
|
* @throws \Exception |
61
|
|
|
*/ |
62
|
3 |
|
public function __construct(SimpleXMLElement $xml) |
63
|
|
|
{ |
64
|
3 |
|
$this->signOn = $this->buildSignOn($xml->SIGNONMSGSRSV1->SONRS); |
65
|
3 |
|
$this->signupAccountInfo = $this->buildAccountInfo($xml->SIGNUPMSGSRSV1->ACCTINFOTRNRS); |
66
|
|
|
|
67
|
3 |
|
if (isset($xml->BANKMSGSRSV1)) { |
68
|
3 |
|
$this->bankAccounts = $this->buildBankAccounts($xml); |
69
|
|
|
} elseif (isset($xml->CREDITCARDMSGSRSV1)) { |
70
|
|
|
$this->bankAccounts = $this->buildCreditAccounts($xml); |
71
|
|
|
} |
72
|
|
|
|
73
|
|
|
// Set a helper if only one bank account |
74
|
3 |
|
if (count($this->bankAccounts) === 1) { |
75
|
2 |
|
$this->bankAccount = $this->bankAccounts[0]; |
|
|
|
|
76
|
|
|
} |
77
|
3 |
|
} |
78
|
|
|
|
79
|
|
|
/** |
80
|
|
|
* Get the transactions that have been processed |
81
|
|
|
* |
82
|
|
|
* @return array |
83
|
|
|
* @deprecated This will be removed in future versions |
84
|
|
|
*/ |
85
|
|
|
public function getTransactions() |
86
|
|
|
{ |
87
|
|
|
return $this->bankAccount->statement->transactions; |
|
|
|
|
88
|
|
|
} |
89
|
|
|
|
90
|
|
|
/** |
91
|
|
|
* @param array $header |
92
|
|
|
* @return Ofx |
93
|
|
|
*/ |
94
|
|
|
public function buildHeader(array $header) |
95
|
|
|
{ |
96
|
|
|
$this->header = $header; |
97
|
|
|
|
98
|
|
|
return $this; |
99
|
|
|
} |
100
|
|
|
|
101
|
|
|
/** |
102
|
|
|
* @param SimpleXMLElement $xml |
103
|
|
|
* @return SignOn |
104
|
|
|
* @throws \Exception |
105
|
|
|
*/ |
106
|
3 |
|
protected function buildSignOn(SimpleXMLElement $xml) |
107
|
|
|
{ |
108
|
3 |
|
$signOn = new SignOn(); |
109
|
3 |
|
$signOn->status = $this->buildStatus($xml->STATUS); |
110
|
3 |
|
$signOn->date = Utils::createDateTimeFromStr($xml->DTSERVER, true); |
111
|
3 |
|
$signOn->language = $xml->LANGUAGE; |
112
|
|
|
|
113
|
3 |
|
$signOn->institute = new Institute(); |
114
|
3 |
|
$signOn->institute->name = $xml->FI->ORG; |
115
|
3 |
|
$signOn->institute->id = $xml->FI->FID; |
116
|
|
|
|
117
|
3 |
|
return $signOn; |
118
|
|
|
} |
119
|
|
|
|
120
|
|
|
/** |
121
|
|
|
* @param SimpleXMLElement|null $xml |
122
|
|
|
* @return array AccountInfo |
123
|
|
|
*/ |
124
|
3 |
|
private function buildAccountInfo(SimpleXMLElement $xml = null) |
125
|
|
|
{ |
126
|
3 |
|
if (null === $xml || !isset($xml->ACCTINFO)) { |
127
|
3 |
|
return []; |
128
|
|
|
} |
129
|
|
|
|
130
|
|
|
$accounts = []; |
131
|
|
|
foreach ($xml->ACCTINFO as $account) { |
132
|
|
|
$accountInfo = new AccountInfo(); |
133
|
|
|
$accountInfo->desc = $account->DESC; |
134
|
|
|
$accountInfo->number = $account->ACCTID; |
135
|
|
|
$accounts[] = $accountInfo; |
136
|
|
|
} |
137
|
|
|
|
138
|
|
|
return $accounts; |
139
|
|
|
} |
140
|
|
|
|
141
|
|
|
/** |
142
|
|
|
* @param SimpleXMLElement $xml |
143
|
|
|
* @return array |
144
|
|
|
* @throws \Exception |
145
|
|
|
*/ |
146
|
|
|
private function buildCreditAccounts(SimpleXMLElement $xml) |
147
|
|
|
{ |
148
|
|
|
// Loop through the bank accounts |
149
|
|
|
$bankAccounts = []; |
150
|
|
|
|
151
|
|
|
foreach ($xml->CREDITCARDMSGSRSV1->CCSTMTTRNRS as $accountStatement) { |
152
|
|
|
$bankAccounts[] = $this->buildCreditAccount($accountStatement); |
|
|
|
|
153
|
|
|
} |
154
|
|
|
return $bankAccounts; |
155
|
|
|
} |
156
|
|
|
|
157
|
|
|
/** |
158
|
|
|
* @param SimpleXMLElement $xml |
159
|
|
|
* @return array |
160
|
|
|
* @throws \Exception |
161
|
|
|
*/ |
162
|
3 |
|
private function buildBankAccounts(SimpleXMLElement $xml) |
163
|
|
|
{ |
164
|
|
|
// Loop through the bank accounts |
165
|
3 |
|
$bankAccounts = []; |
166
|
3 |
|
foreach ($xml->BANKMSGSRSV1->STMTTRNRS as $accountStatement) { |
167
|
3 |
|
foreach ($accountStatement->STMTRS as $statementResponse) { |
168
|
3 |
|
$bankAccounts[] = $this->buildBankAccount($accountStatement->TRNUID, $statementResponse); |
|
|
|
|
169
|
|
|
} |
170
|
|
|
} |
171
|
3 |
|
return $bankAccounts; |
172
|
|
|
} |
173
|
|
|
|
174
|
|
|
/** |
175
|
|
|
* @param string $transactionUid |
176
|
|
|
* @param SimpleXMLElement $statementResponse |
177
|
|
|
* @return BankAccount |
178
|
|
|
* @throws \Exception |
179
|
|
|
*/ |
180
|
3 |
|
private function buildBankAccount($transactionUid, SimpleXMLElement $statementResponse) |
181
|
|
|
{ |
182
|
3 |
|
$bankAccount = new BankAccount(); |
183
|
3 |
|
$bankAccount->transactionUid = $transactionUid; |
184
|
3 |
|
$bankAccount->agencyNumber = $statementResponse->BANKACCTFROM->BRANCHID; |
185
|
3 |
|
$bankAccount->accountNumber = $statementResponse->BANKACCTFROM->ACCTID; |
186
|
3 |
|
$bankAccount->routingNumber = $statementResponse->BANKACCTFROM->BANKID; |
187
|
3 |
|
$bankAccount->accountType = $statementResponse->BANKACCTFROM->ACCTTYPE; |
188
|
3 |
|
$bankAccount->balance = $statementResponse->LEDGERBAL->BALAMT; |
189
|
3 |
|
$bankAccount->balanceDate = Utils::createDateTimeFromStr( |
190
|
3 |
|
$statementResponse->LEDGERBAL->DTASOF, |
191
|
3 |
|
true |
192
|
|
|
); |
193
|
|
|
|
194
|
3 |
|
$bankAccount->statement = new Statement(); |
195
|
3 |
|
$bankAccount->statement->currency = $statementResponse->CURDEF; |
196
|
|
|
|
197
|
3 |
|
$bankAccount->statement->startDate = Utils::createDateTimeFromStr( |
198
|
3 |
|
$statementResponse->BANKTRANLIST->DTSTART |
199
|
|
|
); |
200
|
|
|
|
201
|
3 |
|
$bankAccount->statement->endDate = Utils::createDateTimeFromStr( |
202
|
3 |
|
$statementResponse->BANKTRANLIST->DTEND |
203
|
|
|
); |
204
|
|
|
|
205
|
3 |
|
$bankAccount->statement->transactions = $this->buildTransactions( |
206
|
3 |
|
$statementResponse->BANKTRANLIST->STMTTRN |
207
|
|
|
); |
208
|
|
|
|
209
|
3 |
|
return $bankAccount; |
210
|
|
|
} |
211
|
|
|
|
212
|
|
|
/** |
213
|
|
|
* @param SimpleXMLElement $xml |
214
|
|
|
* @return BankAccount |
215
|
|
|
* @throws \Exception |
216
|
|
|
*/ |
217
|
|
|
private function buildCreditAccount(SimpleXMLElement $xml) |
218
|
|
|
{ |
219
|
|
|
$nodeName = 'CCACCTFROM'; |
220
|
|
|
if (!isset($xml->CCSTMTRS->$nodeName)) { |
221
|
|
|
$nodeName = 'BANKACCTFROM'; |
222
|
|
|
} |
223
|
|
|
|
224
|
|
|
$creditAccount = new BankAccount(); |
225
|
|
|
$creditAccount->transactionUid = $xml->TRNUID; |
226
|
|
|
$creditAccount->agencyNumber = $xml->CCSTMTRS->$nodeName->BRANCHID; |
227
|
|
|
$creditAccount->accountNumber = $xml->CCSTMTRS->$nodeName->ACCTID; |
228
|
|
|
$creditAccount->routingNumber = $xml->CCSTMTRS->$nodeName->BANKID; |
229
|
|
|
$creditAccount->accountType = $xml->CCSTMTRS->$nodeName->ACCTTYPE; |
230
|
|
|
$creditAccount->balance = $xml->CCSTMTRS->LEDGERBAL->BALAMT; |
231
|
|
|
$creditAccount->balanceDate = Utils::createDateTimeFromStr($xml->CCSTMTRS->LEDGERBAL->DTASOF, true); |
232
|
|
|
|
233
|
|
|
$creditAccount->statement = new Statement(); |
234
|
|
|
$creditAccount->statement->currency = $xml->CCSTMTRS->CURDEF; |
235
|
|
|
$creditAccount->statement->startDate = Utils::createDateTimeFromStr($xml->CCSTMTRS->BANKTRANLIST->DTSTART); |
236
|
|
|
$creditAccount->statement->endDate = Utils::createDateTimeFromStr($xml->CCSTMTRS->BANKTRANLIST->DTEND); |
237
|
|
|
$creditAccount->statement->transactions = $this->buildTransactions($xml->CCSTMTRS->BANKTRANLIST->STMTTRN); |
238
|
|
|
|
239
|
|
|
return $creditAccount; |
240
|
|
|
} |
241
|
|
|
|
242
|
|
|
/** |
243
|
|
|
* @param SimpleXMLElement $transactions |
244
|
|
|
* @return array |
245
|
|
|
* @throws \Exception |
246
|
|
|
*/ |
247
|
3 |
|
private function buildTransactions(SimpleXMLElement $transactions) |
248
|
|
|
{ |
249
|
3 |
|
$return = []; |
250
|
3 |
|
foreach ($transactions as $t) { |
251
|
3 |
|
$transaction = new Transaction(); |
252
|
3 |
|
$transaction->type = (string)$t->TRNTYPE; |
253
|
3 |
|
$transaction->date = Utils::createDateTimeFromStr($t->DTPOSTED); |
254
|
3 |
|
if ('' !== (string)$t->DTUSER) { |
255
|
2 |
|
$transaction->userInitiatedDate = Utils::createDateTimeFromStr($t->DTUSER); |
256
|
|
|
} |
257
|
3 |
|
$transaction->amount = Utils::createAmountFromStr($t->TRNAMT); |
258
|
3 |
|
$transaction->uniqueId = (string)$t->FITID; |
259
|
3 |
|
$transaction->name = (string)$t->NAME; |
260
|
3 |
|
$transaction->memo = (string)$t->MEMO; |
261
|
3 |
|
$transaction->sic = $t->SIC; |
262
|
3 |
|
$transaction->checkNumber = $t->CHECKNUM; |
263
|
3 |
|
$return[] = $transaction; |
264
|
|
|
} |
265
|
|
|
|
266
|
3 |
|
return $return; |
267
|
|
|
} |
268
|
|
|
|
269
|
|
|
/** |
270
|
|
|
* @param SimpleXMLElement $xml |
271
|
|
|
* @return Status |
272
|
|
|
*/ |
273
|
3 |
|
private function buildStatus(SimpleXMLElement $xml) |
274
|
|
|
{ |
275
|
3 |
|
$status = new Status(); |
276
|
3 |
|
$status->code = $xml->CODE; |
277
|
3 |
|
$status->severity = $xml->SEVERITY; |
278
|
3 |
|
$status->message = $xml->MESSAGE; |
279
|
|
|
|
280
|
3 |
|
return $status; |
281
|
|
|
} |
282
|
|
|
} |
283
|
|
|
|
This property has been deprecated. The supplier of the class has supplied an explanatory message.
The explanatory message should give you some clue as to whether and when the property will be removed from the class and what other property to use instead.