Commit | Line | Data |
---|---|---|
792ad554 TO |
1 | <?php |
2 | require_once 'CiviTest/CiviUnitTestCase.php'; | |
3 | require_once 'CiviTest/Contact.php'; | |
4 | require_once 'CiviTest/Custom.php'; | |
aba1cd8b EM |
5 | |
6 | /** | |
7 | * Class CRM_Core_TransactionTest | |
8 | */ | |
792ad554 TO |
9 | class CRM_Core_TransactionTest extends CiviUnitTestCase { |
10 | ||
5bb8417a TO |
11 | /** |
12 | * @var array | |
13 | */ | |
14 | private $callbackLog; | |
15 | ||
16 | /** | |
17 | * @var array (int $idx => int $contactId) list of contact IDs that have been created (in order of creation) | |
18 | * | |
19 | * Note that ID this is all IDs created by the test-case -- even if the creation was subsequently rolled back | |
20 | */ | |
21 | private $cids; | |
22 | ||
00be9182 | 23 | public function setUp() { |
792ad554 TO |
24 | parent::setUp(); |
25 | $this->quickCleanup(array('civicrm_contact', 'civicrm_activity')); | |
5bb8417a TO |
26 | $this->callbackLog = array(); |
27 | $this->cids = array(); | |
792ad554 TO |
28 | } |
29 | ||
7fe37828 EM |
30 | /** |
31 | * @return array | |
32 | */ | |
00be9182 | 33 | public function dataCreateStyle() { |
5bb8417a TO |
34 | return array( |
35 | array('sql-insert'), | |
36 | array('bao-create'), | |
37 | ); | |
792ad554 TO |
38 | } |
39 | ||
7fe37828 EM |
40 | /** |
41 | * @return array | |
42 | */ | |
00be9182 | 43 | public function dataCreateAndCommitStyles() { |
5bb8417a TO |
44 | return array( |
45 | array('sql-insert', 'implicit-commit'), | |
46 | array('sql-insert', 'explicit-commit'), | |
47 | array('bao-create', 'implicit-commit'), | |
48 | array('bao-create', 'explicit-commit'), | |
49 | ); | |
792ad554 TO |
50 | } |
51 | ||
5bb8417a | 52 | /** |
e16033b4 TO |
53 | * @param string $createStyle |
54 | * 'sql-insert'|'bao-create'. | |
55 | * @param string $commitStyle | |
56 | * 'implicit-commit'|'explicit-commit'. | |
5bb8417a TO |
57 | * @dataProvider dataCreateAndCommitStyles |
58 | */ | |
00be9182 | 59 | public function testBasicCommit($createStyle, $commitStyle) { |
5bb8417a TO |
60 | $this->createContactWithTransaction('reuse-tx', $createStyle, $commitStyle); |
61 | $this->assertCount(1, $this->cids); | |
62 | $this->assertContactsExistByOffset(array(0 => TRUE)); | |
63 | } | |
792ad554 | 64 | |
5bb8417a TO |
65 | /** |
66 | * @dataProvider dataCreateStyle | |
1e1fdcf6 | 67 | * @param $createStyle |
5bb8417a | 68 | */ |
00be9182 | 69 | public function testBasicRollback($createStyle) { |
5bb8417a TO |
70 | $this->createContactWithTransaction('reuse-tx', $createStyle, 'rollback'); |
71 | $this->assertCount(1, $this->cids); | |
72 | $this->assertContactsExistByOffset(array(0 => FALSE)); | |
73 | } | |
792ad554 | 74 | |
5bb8417a | 75 | /** |
eceb18cc | 76 | * Test in which an outer function makes multiple calls to inner functions. |
5bb8417a TO |
77 | * but then rolls back the entire set. |
78 | * | |
e16033b4 TO |
79 | * @param string $createStyle |
80 | * 'sql-insert'|'bao-create'. | |
81 | * @param string $commitStyle | |
82 | * 'implicit-commit'|'explicit-commit'. | |
5bb8417a TO |
83 | * @dataProvider dataCreateAndCommitStyles |
84 | */ | |
00be9182 | 85 | public function testBatchRollback($createStyle, $commitStyle) { |
5bb8417a TO |
86 | $this->runBatch( |
87 | 'reuse-tx', | |
88 | array( | |
89 | array('reuse-tx', $createStyle, $commitStyle), // cid 0 | |
90 | array('reuse-tx', $createStyle, $commitStyle), // cid 1 | |
91 | ), | |
92 | array(0 => TRUE, 1 => TRUE), | |
93 | 'rollback' | |
94 | ); | |
95 | $this->assertCount(2, $this->cids); | |
96 | $this->assertContactsExistByOffset(array(0 => FALSE, 1 => FALSE)); | |
97 | } | |
792ad554 | 98 | |
5bb8417a TO |
99 | /** |
100 | * Test in which runBatch makes multiple calls to | |
101 | * createContactWithTransaction using a mix of rollback/commit. | |
102 | * createContactWithTransaction use nesting (savepoints), so the | |
103 | * batch is able to commit. | |
104 | * | |
e16033b4 TO |
105 | * @param string $createStyle |
106 | * 'sql-insert'|'bao-create'. | |
107 | * @param string $commitStyle | |
108 | * 'implicit-commit'|'explicit-commit'. | |
5bb8417a TO |
109 | * @dataProvider dataCreateAndCommitStyles |
110 | */ | |
00be9182 | 111 | public function testMixedBatchCommit_nesting($createStyle, $commitStyle) { |
5bb8417a TO |
112 | $this->runBatch( |
113 | 'reuse-tx', | |
114 | array( | |
115 | array('nest-tx', $createStyle, $commitStyle), // cid 0 | |
116 | array('nest-tx', $createStyle, 'rollback'), // cid 1 | |
117 | array('nest-tx', $createStyle, $commitStyle), // cid 2 | |
118 | ), | |
119 | array(0 => TRUE, 1 => FALSE, 2 => TRUE), | |
120 | $commitStyle | |
121 | ); | |
122 | $this->assertCount(3, $this->cids); | |
123 | $this->assertContactsExistByOffset(array(0 => TRUE, 1 => FALSE, 2 => TRUE)); | |
792ad554 TO |
124 | } |
125 | ||
126 | /** | |
5bb8417a TO |
127 | * Test in which runBatch makes multiple calls to |
128 | * createContactWithTransaction using a mix of rollback/commit. | |
129 | * createContactWithTransaction reuses the main transaction, | |
130 | * so the overall batch must rollback. | |
131 | * | |
e16033b4 TO |
132 | * @param string $createStyle |
133 | * 'sql-insert'|'bao-create'. | |
134 | * @param string $commitStyle | |
135 | * 'implicit-commit'|'explicit-commit'. | |
5bb8417a | 136 | * @dataProvider dataCreateAndCommitStyles |
792ad554 | 137 | */ |
00be9182 | 138 | public function testMixedBatchCommit_reuse($createStyle, $commitStyle) { |
5bb8417a TO |
139 | $this->runBatch( |
140 | 'reuse-tx', | |
141 | array( | |
142 | array('reuse-tx', $createStyle, $commitStyle), // cid 0 | |
143 | array('reuse-tx', $createStyle, 'rollback'), // cid 1 | |
144 | array('reuse-tx', $createStyle, $commitStyle), // cid 2 | |
145 | ), | |
146 | array(0 => TRUE, 1 => TRUE, 2 => TRUE), | |
147 | $commitStyle | |
148 | ); | |
149 | $this->assertCount(3, $this->cids); | |
150 | $this->assertContactsExistByOffset(array(0 => FALSE, 1 => FALSE, 2 => FALSE)); | |
151 | } | |
792ad554 | 152 | |
5bb8417a TO |
153 | /** |
154 | * Test in which runBatch makes multiple calls to | |
155 | * createContactWithTransaction using a mix of rollback/commit. | |
156 | * The overall batch is rolled back. | |
157 | * | |
e16033b4 TO |
158 | * @param string $createStyle |
159 | * 'sql-insert'|'bao-create'. | |
160 | * @param string $commitStyle | |
161 | * 'implicit-commit'|'explicit-commit'. | |
5bb8417a TO |
162 | * @dataProvider dataCreateAndCommitStyles |
163 | */ | |
00be9182 | 164 | public function testMixedBatchRollback_nesting($createStyle, $commitStyle) { |
5bb8417a TO |
165 | $this->assertFalse(CRM_Core_Transaction::isActive()); |
166 | $this->runBatch( | |
167 | 'reuse-tx', | |
168 | array( | |
169 | array('nest-tx', $createStyle, $commitStyle), // cid 0 | |
170 | array('nest-tx', $createStyle, 'rollback'), // cid 1 | |
171 | array('nest-tx', $createStyle, $commitStyle), // cid 2 | |
172 | ), | |
173 | array(0 => TRUE, 1 => FALSE, 2 => TRUE), | |
174 | 'rollback' | |
175 | ); | |
176 | $this->assertFalse(CRM_Core_Transaction::isActive()); | |
177 | $this->assertCount(3, $this->cids); | |
178 | $this->assertContactsExistByOffset(array(0 => FALSE, 1 => FALSE, 2 => FALSE)); | |
179 | } | |
792ad554 | 180 | |
5bb8417a TO |
181 | public function testIsActive() { |
182 | $this->assertEquals(FALSE, CRM_Core_Transaction::isActive()); | |
183 | $this->assertEquals(TRUE, CRM_Core_Transaction::willCommit()); | |
184 | $tx = new CRM_Core_Transaction(); | |
185 | $this->assertEquals(TRUE, CRM_Core_Transaction::isActive()); | |
186 | $this->assertEquals(TRUE, CRM_Core_Transaction::willCommit()); | |
187 | $tx = NULL; | |
188 | $this->assertEquals(FALSE, CRM_Core_Transaction::isActive()); | |
189 | $this->assertEquals(TRUE, CRM_Core_Transaction::willCommit()); | |
190 | } | |
792ad554 | 191 | |
5bb8417a TO |
192 | public function testIsActive_rollback() { |
193 | $this->assertEquals(FALSE, CRM_Core_Transaction::isActive()); | |
194 | $this->assertEquals(TRUE, CRM_Core_Transaction::willCommit()); | |
792ad554 | 195 | |
5bb8417a TO |
196 | $tx = new CRM_Core_Transaction(); |
197 | $this->assertEquals(TRUE, CRM_Core_Transaction::isActive()); | |
198 | $this->assertEquals(TRUE, CRM_Core_Transaction::willCommit()); | |
792ad554 | 199 | |
5bb8417a TO |
200 | $tx->rollback(); |
201 | $this->assertEquals(TRUE, CRM_Core_Transaction::isActive()); | |
202 | $this->assertEquals(FALSE, CRM_Core_Transaction::willCommit()); | |
792ad554 | 203 | |
5bb8417a TO |
204 | $tx = NULL; |
205 | $this->assertEquals(FALSE, CRM_Core_Transaction::isActive()); | |
206 | $this->assertEquals(TRUE, CRM_Core_Transaction::willCommit()); | |
207 | } | |
792ad554 | 208 | |
5bb8417a TO |
209 | public function testCallback_commit() { |
210 | $tx = new CRM_Core_Transaction(); | |
792ad554 | 211 | |
92915c55 TO |
212 | CRM_Core_Transaction::addCallback(CRM_Core_Transaction::PHASE_PRE_COMMIT, array($this, '_preCommit'), array( |
213 | 'qwe', | |
608e6658 | 214 | 'rty', |
92915c55 TO |
215 | )); |
216 | CRM_Core_Transaction::addCallback(CRM_Core_Transaction::PHASE_POST_COMMIT, array($this, '_postCommit'), array( | |
217 | 'uio', | |
608e6658 | 218 | 'p[]', |
92915c55 TO |
219 | )); |
220 | CRM_Core_Transaction::addCallback(CRM_Core_Transaction::PHASE_PRE_ROLLBACK, array( | |
221 | $this, | |
608e6658 | 222 | '_preRollback', |
92915c55 TO |
223 | ), array('asd', 'fgh')); |
224 | CRM_Core_Transaction::addCallback(CRM_Core_Transaction::PHASE_POST_ROLLBACK, array( | |
225 | $this, | |
608e6658 | 226 | '_postRollback', |
92915c55 | 227 | ), array('jkl', ';')); |
792ad554 | 228 | |
5bb8417a | 229 | CRM_Core_DAO::executeQuery('UPDATE civicrm_contact SET id = 100 WHERE id = 100'); |
792ad554 | 230 | |
5bb8417a TO |
231 | $this->assertEquals(array(), $this->callbackLog); |
232 | $tx = NULL; | |
233 | $this->assertEquals(array('_preCommit', 'qwe', 'rty'), $this->callbackLog[0]); | |
234 | $this->assertEquals(array('_postCommit', 'uio', 'p[]'), $this->callbackLog[1]); | |
792ad554 TO |
235 | } |
236 | ||
5bb8417a TO |
237 | public function testCallback_rollback() { |
238 | $tx = new CRM_Core_Transaction(); | |
792ad554 | 239 | |
92915c55 TO |
240 | CRM_Core_Transaction::addCallback(CRM_Core_Transaction::PHASE_PRE_COMMIT, array($this, '_preCommit'), array( |
241 | 'ewq', | |
608e6658 | 242 | 'ytr', |
92915c55 TO |
243 | )); |
244 | CRM_Core_Transaction::addCallback(CRM_Core_Transaction::PHASE_POST_COMMIT, array($this, '_postCommit'), array( | |
245 | 'oiu', | |
608e6658 | 246 | '][p', |
92915c55 TO |
247 | )); |
248 | CRM_Core_Transaction::addCallback(CRM_Core_Transaction::PHASE_PRE_ROLLBACK, array( | |
249 | $this, | |
608e6658 | 250 | '_preRollback', |
92915c55 TO |
251 | ), array('dsa', 'hgf')); |
252 | CRM_Core_Transaction::addCallback(CRM_Core_Transaction::PHASE_POST_ROLLBACK, array( | |
253 | $this, | |
608e6658 | 254 | '_postRollback', |
92915c55 | 255 | ), array('lkj', ';')); |
792ad554 | 256 | |
5bb8417a TO |
257 | CRM_Core_DAO::executeQuery('UPDATE civicrm_contact SET id = 100 WHERE id = 100'); |
258 | $tx->rollback(); | |
792ad554 | 259 | |
5bb8417a TO |
260 | $this->assertEquals(array(), $this->callbackLog); |
261 | $tx = NULL; | |
262 | $this->assertEquals(array('_preRollback', 'dsa', 'hgf'), $this->callbackLog[0]); | |
263 | $this->assertEquals(array('_postRollback', 'lkj', ';'), $this->callbackLog[1]); | |
264 | } | |
792ad554 | 265 | |
5bb8417a | 266 | /** |
e16033b4 TO |
267 | * @param string $createStyle |
268 | * 'sql-insert'|'bao-create'. | |
269 | * @param string $commitStyle | |
270 | * 'implicit-commit'|'explicit-commit'. | |
5bb8417a TO |
271 | * @dataProvider dataCreateAndCommitStyles |
272 | */ | |
273 | public function testRun_ok($createStyle, $commitStyle) { | |
274 | $test = $this; | |
92915c55 | 275 | CRM_Core_Transaction::create(TRUE)->run(function ($tx) use (&$test, $createStyle, $commitStyle) { |
5bb8417a TO |
276 | $test->createContactWithTransaction('nest-tx', $createStyle, $commitStyle); |
277 | $test->assertContactsExistByOffset(array(0 => TRUE)); | |
278 | }); | |
279 | $this->assertContactsExistByOffset(array(0 => TRUE)); | |
280 | } | |
792ad554 | 281 | |
5bb8417a | 282 | /** |
e16033b4 TO |
283 | * @param string $createStyle |
284 | * 'sql-insert'|'bao-create'. | |
285 | * @param string $commitStyle | |
286 | * 'implicit-commit'|'explicit-commit'. | |
5bb8417a TO |
287 | * @dataProvider dataCreateAndCommitStyles |
288 | */ | |
289 | public function testRun_exception($createStyle, $commitStyle) { | |
290 | $tx = new CRM_Core_Transaction(); | |
291 | $test = $this; | |
292 | $e = NULL; // Exception | |
293 | try { | |
92915c55 | 294 | CRM_Core_Transaction::create(TRUE)->run(function ($tx) use (&$test, $createStyle, $commitStyle) { |
5bb8417a TO |
295 | $test->createContactWithTransaction('nest-tx', $createStyle, $commitStyle); |
296 | $test->assertContactsExistByOffset(array(0 => TRUE)); | |
297 | throw new Exception("Ruh-roh"); | |
298 | }); | |
0db6c3e1 TO |
299 | } |
300 | catch (Exception $ex) { | |
5bb8417a | 301 | $e = $ex; |
c0aa95b2 TO |
302 | if (get_class($e) != 'Exception' || $e->getMessage() != 'Ruh-roh') { |
303 | throw $e; | |
304 | } | |
5bb8417a TO |
305 | } |
306 | $this->assertTrue($e instanceof Exception); | |
5bb8417a TO |
307 | $this->assertContactsExistByOffset(array(0 => FALSE)); |
308 | } | |
792ad554 | 309 | |
5bb8417a TO |
310 | /** |
311 | * @param $cids | |
312 | * @param bool $exist | |
313 | */ | |
314 | public function assertContactsExist($cids, $exist = TRUE) { | |
315 | foreach ($cids as $cid) { | |
316 | $this->assertTrue(is_numeric($cid)); | |
317 | $this->assertDBQuery($exist ? 1 : 0, 'SELECT count(*) FROM civicrm_contact WHERE id = %1', array( | |
318 | 1 => array($cid, 'Integer'), | |
319 | )); | |
320 | } | |
321 | } | |
792ad554 | 322 | |
5bb8417a | 323 | /** |
e16033b4 TO |
324 | * @param array $existsByOffset |
325 | * Array(int $cidOffset => bool $expectExists). | |
5bb8417a TO |
326 | * @param int $generalOffset |
327 | */ | |
328 | public function assertContactsExistByOffset($existsByOffset, $generalOffset = 0) { | |
329 | foreach ($existsByOffset as $offset => $expectExists) { | |
330 | $this->assertTrue(isset($this->cids[$generalOffset + $offset]), "Find cid at offset($generalOffset + $offset)"); | |
331 | $cid = $this->cids[$generalOffset + $offset]; | |
332 | $this->assertTrue(is_numeric($cid)); | |
333 | $this->assertDBQuery($expectExists ? 1 : 0, 'SELECT count(*) FROM civicrm_contact WHERE id = %1', array( | |
334 | 1 => array($cid, 'Integer'), | |
335 | ), "Check contact at offset($generalOffset + $offset)"); | |
336 | } | |
792ad554 TO |
337 | } |
338 | ||
339 | /** | |
5bb8417a TO |
340 | * Use SQL to INSERT a contact and assert success. Perform |
341 | * work within a transaction. | |
342 | * | |
e16033b4 TO |
343 | * @param string $nesting |
344 | * 'reuse-tx'|'nest-tx' how to construct transaction. | |
345 | * @param string $insert | |
346 | * 'sql-insert'|'bao-create' how to add the example record. | |
347 | * @param string $outcome | |
348 | * 'rollback'|'implicit-commit'|'explicit-commit' how to finish transaction. | |
a6c01b45 CW |
349 | * @return int |
350 | * cid | |
792ad554 | 351 | */ |
5bb8417a TO |
352 | public function createContactWithTransaction($nesting, $insert, $outcome) { |
353 | if ($nesting != 'reuse-tx' && $nesting != 'nest-tx') { | |
354 | throw new RuntimeException('Bad test data: reuse=' . $nesting); | |
355 | } | |
356 | if ($insert != 'sql-insert' && $insert != 'bao-create') { | |
357 | throw new RuntimeException('Bad test data: insert=' . $insert); | |
358 | } | |
359 | if ($outcome != 'rollback' && $outcome != 'implicit-commit' && $outcome != 'explicit-commit') { | |
360 | throw new RuntimeException('Bad test data: outcome=' . $outcome); | |
361 | } | |
792ad554 | 362 | |
5bb8417a | 363 | $tx = new CRM_Core_Transaction($nesting === 'nest-tx'); |
792ad554 | 364 | |
5bb8417a TO |
365 | if ($insert == 'sql-insert') { |
366 | $r = CRM_Core_DAO::executeQuery("INSERT INTO civicrm_contact(first_name,last_name) VALUES ('ff', 'll')"); | |
367 | $cid = mysql_insert_id(); | |
0db6c3e1 TO |
368 | } |
369 | elseif ($insert == 'bao-create') { | |
792ad554 TO |
370 | $params = array( |
371 | 'contact_type' => 'Individual', | |
5bb8417a TO |
372 | 'first_name' => 'FF', |
373 | 'last_name' => 'LL', | |
792ad554 TO |
374 | ); |
375 | $r = CRM_Contact_BAO_Contact::create($params); | |
376 | $cid = $r->id; | |
5bb8417a | 377 | } |
792ad554 | 378 | |
5bb8417a | 379 | $this->cids[] = $cid; |
792ad554 | 380 | |
5bb8417a | 381 | $this->assertContactsExist(array($cid), TRUE); |
792ad554 | 382 | |
5bb8417a TO |
383 | if ($outcome == 'rollback') { |
384 | $tx->rollback(); | |
0db6c3e1 TO |
385 | } |
386 | elseif ($outcome == 'explicit-commit') { | |
5bb8417a TO |
387 | $tx->commit(); |
388 | } // else: implicit-commit | |
792ad554 | 389 | |
5bb8417a TO |
390 | return $cid; |
391 | } | |
792ad554 | 392 | |
5bb8417a | 393 | /** |
eceb18cc | 394 | * Perform a series of operations within smaller transactions. |
5bb8417a | 395 | * |
e16033b4 TO |
396 | * @param string $nesting |
397 | * 'reuse-tx'|'nest-tx' how to construct transaction. | |
398 | * @param array $callbacks | |
399 | * See createContactWithTransaction. | |
400 | * @param array $existsByOffset | |
401 | * See assertContactsMix. | |
402 | * @param string $outcome | |
403 | * 'rollback'|'implicit-commit'|'explicit-commit' how to finish transaction. | |
608e6658 | 404 | * @return void |
5bb8417a | 405 | */ |
2ffda55d | 406 | public function runBatch($nesting, $callbacks, $existsByOffset, $outcome) { |
5bb8417a TO |
407 | if ($nesting != 'reuse-tx' && $nesting != 'nest-tx') { |
408 | throw new RuntimeException('Bad test data: nesting=' . $nesting); | |
409 | } | |
410 | if ($outcome != 'rollback' && $outcome != 'implicit-commit' && $outcome != 'explicit-commit') { | |
411 | throw new RuntimeException('Bad test data: outcome=' . $nesting); | |
412 | } | |
792ad554 | 413 | |
5bb8417a | 414 | $tx = new CRM_Core_Transaction($nesting === 'reuse-tx'); |
792ad554 | 415 | |
5bb8417a TO |
416 | $generalOffset = count($this->cids); |
417 | foreach ($callbacks as $callback) { | |
418 | list ($cbNesting, $cbInsert, $cbOutcome) = $callback; | |
419 | $this->createContactWithTransaction($cbNesting, $cbInsert, $cbOutcome); | |
420 | } | |
792ad554 | 421 | |
5bb8417a | 422 | $this->assertContactsExistByOffset($existsByOffset, $generalOffset); |
792ad554 | 423 | |
5bb8417a TO |
424 | if ($outcome == 'rollback') { |
425 | $tx->rollback(); | |
0db6c3e1 TO |
426 | } |
427 | elseif ($outcome == 'explicit-commit') { | |
5bb8417a TO |
428 | $tx->commit(); |
429 | } // else: implicit-commit | |
792ad554 TO |
430 | } |
431 | ||
7fe37828 EM |
432 | /** |
433 | * @param $arg1 | |
434 | * @param $arg2 | |
435 | */ | |
00be9182 | 436 | public function _preCommit($arg1, $arg2) { |
5bb8417a TO |
437 | $this->callbackLog[] = array('_preCommit', $arg1, $arg2); |
438 | } | |
439 | ||
7fe37828 EM |
440 | /** |
441 | * @param $arg1 | |
442 | * @param $arg2 | |
443 | */ | |
00be9182 | 444 | public function _postCommit($arg1, $arg2) { |
5bb8417a TO |
445 | $this->callbackLog[] = array('_postCommit', $arg1, $arg2); |
446 | } | |
447 | ||
7fe37828 EM |
448 | /** |
449 | * @param $arg1 | |
450 | * @param $arg2 | |
451 | */ | |
00be9182 | 452 | public function _preRollback($arg1, $arg2) { |
5bb8417a TO |
453 | $this->callbackLog[] = array('_preRollback', $arg1, $arg2); |
454 | } | |
455 | ||
7fe37828 EM |
456 | /** |
457 | * @param $arg1 | |
458 | * @param $arg2 | |
459 | */ | |
00be9182 | 460 | public function _postRollback($arg1, $arg2) { |
5bb8417a | 461 | $this->callbackLog[] = array('_postRollback', $arg1, $arg2); |
792ad554 | 462 | } |
96025800 | 463 | |
4cbe18b8 | 464 | } |