Bug 22600: Update Tests adding 'interface' as needed
[koha.git] / t / db_dependent / Koha / Account.t
1 #!/usr/bin/perl
2
3 # Copyright 2018 Koha Development team
4 #
5 # This file is part of Koha
6 #
7 # Koha is free software; you can redistribute it and/or modify it
8 # under the terms of the GNU General Public License as published by
9 # the Free Software Foundation; either version 3 of the License, or
10 # (at your option) any later version.
11 #
12 # Koha is distributed in the hope that it will be useful, but
13 # WITHOUT ANY WARRANTY; without even the implied warranty of
14 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15 # GNU General Public License for more details.
16 #
17 # You should have received a copy of the GNU General Public License
18 # along with Koha; if not, see <http://www.gnu.org/licenses>
19
20 use Modern::Perl;
21
22 use Test::More tests => 8;
23 use Test::MockModule;
24 use Test::Exception;
25
26 use Koha::Account;
27 use Koha::Account::Lines;
28 use Koha::Account::Offsets;
29
30
31 use t::lib::Mocks;
32 use t::lib::TestBuilder;
33
34 my $schema  = Koha::Database->new->schema;
35 my $builder = t::lib::TestBuilder->new;
36 C4::Context->interface('commandline');
37
38 subtest 'new' => sub {
39
40     plan tests => 2;
41
42     $schema->storage->txn_begin;
43
44     throws_ok { Koha::Account->new(); } qr/No patron id passed in!/, 'Croaked on bad call to new';
45
46     my $patron  = $builder->build_object({ class => 'Koha::Patrons' });
47     my $account = Koha::Account->new( { patron_id => $patron->borrowernumber } );
48     is( defined $account, 1, "Account is defined" );
49
50     $schema->storage->txn_rollback;
51 };
52
53 subtest 'outstanding_debits() tests' => sub {
54
55     plan tests => 22;
56
57     $schema->storage->txn_begin;
58
59     my $patron  = $builder->build_object({ class => 'Koha::Patrons' });
60     my $account = $patron->account;
61
62     my @generated_lines;
63     push @generated_lines, Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 1, amountoutstanding => 1, interface => 'commandline' })->store;
64     push @generated_lines, Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 2, amountoutstanding => 2, interface => 'commandline' })->store;
65     push @generated_lines, Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 3, amountoutstanding => 3, interface => 'commandline' })->store;
66     push @generated_lines, Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 4, amountoutstanding => 4, interface => 'commandline' })->store;
67
68     my $lines     = $account->outstanding_debits();
69     my @lines_arr = $account->outstanding_debits();
70
71     is( ref($lines), 'Koha::Account::Lines', 'Called in scalar context, outstanding_debits returns a Koha::Account::Lines object' );
72     is( $lines->total_outstanding, 10, 'Outstandig debits total is correctly calculated' );
73
74     my $i = 0;
75     foreach my $line ( @{ $lines->as_list } ) {
76         my $fetched_line = Koha::Account::Lines->find( $generated_lines[$i]->id );
77         is_deeply( $line->unblessed, $fetched_line->unblessed, "Fetched line matches the generated one ($i)" );
78         is_deeply( $lines_arr[$i]->unblessed, $fetched_line->unblessed, "Fetched line matches the generated one ($i)" );
79         is( ref($lines_arr[$i]), 'Koha::Account::Line', 'outstanding_debits returns a list of Koha::Account::Line objects in list context' );
80         $i++;
81     }
82     my $patron_2 = $builder->build_object({ class => 'Koha::Patrons' });
83     Koha::Account::Line->new({ borrowernumber => $patron_2->id, amountoutstanding => -2, interface => 'commandline' })->store;
84     my $just_one = Koha::Account::Line->new({ borrowernumber => $patron_2->id, amount => 3, amountoutstanding =>  3, interface => 'commandline' })->store;
85     Koha::Account::Line->new({ borrowernumber => $patron_2->id, amount => -6, amountoutstanding => -6, interface => 'commandline' })->store;
86     $lines = $patron_2->account->outstanding_debits();
87     is( $lines->total_outstanding, 3, "Total if some outstanding debits and some credits is only debits" );
88     is( $lines->count, 1, "With 1 outstanding debits, we get back a Lines object with 1 lines" );
89     my $the_line = Koha::Account::Lines->find( $just_one->id );
90     is_deeply( $the_line->unblessed, $lines->next->unblessed, "We get back the one correct line");
91
92     my $patron_3 = $builder->build_object({ class => 'Koha::Patrons' });
93     Koha::Account::Line->new({ borrowernumber => $patron_2->id, amount => -2,   amountoutstanding => -2, interface => 'commandline' })->store;
94     Koha::Account::Line->new({ borrowernumber => $patron_2->id, amount => -20,  amountoutstanding => -20, interface => 'commandline' })->store;
95     Koha::Account::Line->new({ borrowernumber => $patron_2->id, amount => -200, amountoutstanding => -200, interface => 'commandline' })->store;
96     $lines = $patron_3->account->outstanding_debits();
97     is( $lines->total_outstanding, 0, "Total if no outstanding debits total is 0" );
98     is( $lines->count, 0, "With 0 outstanding debits, we get back a Lines object with 0 lines" );
99
100     my $patron_4  = $builder->build_object({ class => 'Koha::Patrons' });
101     my $account_4 = $patron_4->account;
102     $lines = $account_4->outstanding_debits();
103     is( $lines->total_outstanding, 0, "Total if no outstanding debits is 0" );
104     is( $lines->count, 0, "With no outstanding debits, we get back a Lines object with 0 lines" );
105
106     # create a pathological credit with amountoutstanding > 0 (BZ 14591)
107     Koha::Account::Line->new({ borrowernumber => $patron_4->id, amount => -3, amountoutstanding => 3, interface => 'commandline' })->store();
108     $lines = $account_4->outstanding_debits();
109     is( $lines->count, 0, 'No credits are confused with debits because of the amountoutstanding value' );
110
111     $schema->storage->txn_rollback;
112 };
113
114 subtest 'outstanding_credits() tests' => sub {
115
116     plan tests => 17;
117
118     $schema->storage->txn_begin;
119
120     my $patron  = $builder->build_object({ class => 'Koha::Patrons' });
121     my $account = $patron->account;
122
123     my @generated_lines;
124     push @generated_lines, $account->add_credit({ amount => 1, interface => 'commandline' });
125     push @generated_lines, $account->add_credit({ amount => 2, interface => 'commandline' });
126     push @generated_lines, $account->add_credit({ amount => 3, interface => 'commandline' });
127     push @generated_lines, $account->add_credit({ amount => 4, interface => 'commandline' });
128
129     my $lines     = $account->outstanding_credits();
130     my @lines_arr = $account->outstanding_credits();
131
132     is( ref($lines), 'Koha::Account::Lines', 'Called in scalar context, outstanding_credits returns a Koha::Account::Lines object' );
133     is( $lines->total_outstanding, -10, 'Outstandig credits total is correctly calculated' );
134
135     my $i = 0;
136     foreach my $line ( @{ $lines->as_list } ) {
137         my $fetched_line = Koha::Account::Lines->find( $generated_lines[$i]->id );
138         is_deeply( $line->unblessed, $fetched_line->unblessed, "Fetched line matches the generated one ($i)" );
139         is_deeply( $lines_arr[$i]->unblessed, $fetched_line->unblessed, "Fetched line matches the generated one ($i)" );
140         is( ref($lines_arr[$i]), 'Koha::Account::Line', 'outstanding_debits returns a list of Koha::Account::Line objects in list context' );
141         $i++;
142     }
143
144     my $patron_2 = $builder->build_object({ class => 'Koha::Patrons' });
145     $account  = $patron_2->account;
146     $lines       = $account->outstanding_credits();
147     is( $lines->total_outstanding, 0, "Total if no outstanding credits is 0" );
148     is( $lines->count, 0, "With no outstanding credits, we get back a Lines object with 0 lines" );
149
150     # create a pathological debit with amountoutstanding < 0 (BZ 14591)
151     Koha::Account::Line->new({ borrowernumber => $patron_2->id, amount => 2, amountoutstanding => -3, interface => 'commandline' })->store();
152     $lines = $account->outstanding_credits();
153     is( $lines->count, 0, 'No debits are confused with credits because of the amountoutstanding value' );
154
155     $schema->storage->txn_rollback;
156 };
157
158 subtest 'add_credit() tests' => sub {
159
160     plan tests => 15;
161
162     $schema->storage->txn_begin;
163
164     # delete logs and statistics
165     my $action_logs = $schema->resultset('ActionLog')->search()->count;
166     my $statistics = $schema->resultset('Statistic')->search()->count;
167
168     my $patron  = $builder->build_object( { class => 'Koha::Patrons' } );
169     my $account = Koha::Account->new( { patron_id => $patron->borrowernumber } );
170
171     is( $account->balance, 0, 'Patron has no balance' );
172
173     # Disable logs
174     t::lib::Mocks::mock_preference( 'FinesLog', 0 );
175
176     my $line_1 = $account->add_credit(
177         {   amount      => 25,
178             description => 'Payment of 25',
179             library_id  => $patron->branchcode,
180             note        => 'not really important',
181             type        => 'payment',
182             user_id     => $patron->id,
183             interface   => 'commandline'
184         }
185     );
186
187     is( $account->balance, -25, 'Patron has a balance of -25' );
188     is( $schema->resultset('ActionLog')->count(), $action_logs + 0, 'No log was added' );
189     is( $schema->resultset('Statistic')->count(), $statistics + 1, 'Action added to statistics' );
190     is( $line_1->accounttype, $Koha::Account::account_type_credit->{'payment'}, 'Account type is correctly set' );
191
192     # Enable logs
193     t::lib::Mocks::mock_preference( 'FinesLog', 1 );
194
195     my $sip_code = "1";
196     my $line_2 = $account->add_credit(
197         {   amount      => 37,
198             description => 'Payment of 37',
199             library_id  => $patron->branchcode,
200             note        => 'not really important',
201             user_id     => $patron->id,
202             sip         => $sip_code,
203             interface   => 'commandline'
204         }
205     );
206
207     is( $account->balance, -62, 'Patron has a balance of -25' );
208     is( $schema->resultset('ActionLog')->count(), $action_logs + 1, 'Log was added' );
209     is( $schema->resultset('Statistic')->count(), $statistics + 2, 'Action added to statistics' );
210     is( $line_2->accounttype, $Koha::Account::account_type_credit->{'payment'} . $sip_code, 'Account type is correctly set' );
211
212     # offsets have the credit_id set to accountlines_id, and debit_id is undef
213     my $offset_1 = Koha::Account::Offsets->search({ credit_id => $line_1->id })->next;
214     my $offset_2 = Koha::Account::Offsets->search({ credit_id => $line_2->id })->next;
215
216     is( $offset_1->credit_id, $line_1->id, 'No debit_id is set for credits' );
217     is( $offset_1->debit_id, undef, 'No debit_id is set for credits' );
218     is( $offset_2->credit_id, $line_2->id, 'No debit_id is set for credits' );
219     is( $offset_2->debit_id, undef, 'No debit_id is set for credits' );
220
221     my $line_3 = $account->add_credit(
222         {   amount      => 20,
223             description => 'Manual credit applied',
224             library_id  => $patron->branchcode,
225             user_id     => $patron->id,
226             type        => 'forgiven',
227             interface   => 'commandline'
228         }
229     );
230
231     is( $schema->resultset('ActionLog')->count(), $action_logs + 2, 'Log was added' );
232     is( $schema->resultset('Statistic')->count(), $statistics + 2, 'No action added to statistics, because of credit type' );
233
234     $schema->storage->txn_rollback;
235 };
236
237 subtest 'add_debit() tests' => sub {
238
239     plan tests => 13;
240
241     $schema->storage->txn_begin;
242
243     # delete logs and statistics
244     my $action_logs = $schema->resultset('ActionLog')->search()->count;
245     my $statistics  = $schema->resultset('Statistic')->search()->count;
246
247     my $patron = $builder->build_object( { class => 'Koha::Patrons' } );
248     my $account =
249       Koha::Account->new( { patron_id => $patron->borrowernumber } );
250
251     is( $account->balance, 0, 'Patron has no balance' );
252
253     throws_ok {
254     $account->add_debit(
255         {
256             amount      => -5,
257             description => 'amount validation failure',
258             library_id  => $patron->branchcode,
259             note        => 'this should fail anyway',
260             type        => 'rent',
261             user_id     => $patron->id,
262             interface   => 'commandline'
263         }
264     ); } 'Koha::Exceptions::Account::AmountNotPositive', 'Expected validation exception thrown (amount)';
265
266     throws_ok {
267     $account->add_debit(
268         {
269             amount      => 5,
270             description => 'type validation failure',
271             library_id  => $patron->branchcode,
272             note        => 'this should fail anyway',
273             type        => 'failure',
274             user_id     => $patron->id,
275             interface   => 'commandline'
276         }
277     ); } 'Koha::Exceptions::Account::UnrecognisedType', 'Expected validation exception thrown (type)';
278
279     # Disable logs
280     t::lib::Mocks::mock_preference( 'FinesLog', 0 );
281
282     my $line_1 = $account->add_debit(
283         {
284             amount      => 25,
285             description => 'Rental charge of 25',
286             library_id  => $patron->branchcode,
287             note        => 'not really important',
288             type        => 'rent',
289             user_id     => $patron->id,
290             interface   => 'commandline'
291         }
292     );
293
294     is( $account->balance, 25, 'Patron has a balance of 25' );
295     is(
296         $schema->resultset('ActionLog')->count(),
297         $action_logs + 0,
298         'No log was added'
299     );
300     is(
301         $line_1->accounttype,
302         $Koha::Account::account_type_debit->{'rent'},
303         'Account type is correctly set'
304     );
305
306     # Enable logs
307     t::lib::Mocks::mock_preference( 'FinesLog', 1 );
308
309     my $sip_code = "1";
310     my $line_2   = $account->add_debit(
311         {
312             amount      => 37,
313             description => 'Rental charge of 37',
314             library_id  => $patron->branchcode,
315             note        => 'not really important',
316             type        => 'rent',
317             user_id     => $patron->id,
318             interface   => 'commandline'
319         }
320     );
321
322     is( $account->balance, 62, 'Patron has a balance of 62' );
323     is(
324         $schema->resultset('ActionLog')->count(),
325         $action_logs + 1,
326         'Log was added'
327     );
328     is(
329         $line_2->accounttype,
330         $Koha::Account::account_type_debit->{'rent'},
331         'Account type is correctly set'
332     );
333
334     # offsets have the debit_id set to accountlines_id, and credit_id is undef
335     my $offset_1 =
336       Koha::Account::Offsets->search( { debit_id => $line_1->id } )->next;
337     my $offset_2 =
338       Koha::Account::Offsets->search( { debit_id => $line_2->id } )->next;
339
340     is( $offset_1->debit_id,  $line_1->id, 'debit_id is set for debit 1' );
341     is( $offset_1->credit_id, undef,       'credit_id is not set for debit 1' );
342     is( $offset_2->debit_id,  $line_2->id, 'debit_id is set for debit 2' );
343     is( $offset_2->credit_id, undef,       'credit_id is not set for debit 2' );
344
345     $schema->storage->txn_rollback;
346 };
347
348 subtest 'lines() tests' => sub {
349
350     plan tests => 1;
351
352     $schema->storage->txn_begin;
353
354     my $patron  = $builder->build_object({ class => 'Koha::Patrons' });
355     my $account = $patron->account;
356
357     my @generated_lines;
358
359     # Add Credits
360     push @generated_lines, $account->add_credit({ amount => 1, interface => 'commandline' });
361     push @generated_lines, $account->add_credit({ amount => 2, interface => 'commandline' });
362     push @generated_lines, $account->add_credit({ amount => 3, interface => 'commandline' });
363     push @generated_lines, $account->add_credit({ amount => 4, interface => 'commandline' });
364
365     # Add Debits
366     push @generated_lines, Koha::Account::Line->new({ borrowernumber => $patron->id, amountoutstanding => 1, interface => 'commandline' })->store;
367     push @generated_lines, Koha::Account::Line->new({ borrowernumber => $patron->id, amountoutstanding => 2, interface => 'commandline' })->store;
368     push @generated_lines, Koha::Account::Line->new({ borrowernumber => $patron->id, amountoutstanding => 3, interface => 'commandline' })->store;
369     push @generated_lines, Koha::Account::Line->new({ borrowernumber => $patron->id, amountoutstanding => 4, interface => 'commandline' })->store;
370
371     # Paid Off
372     push @generated_lines, Koha::Account::Line->new({ borrowernumber => $patron->id, amountoutstanding => 0, interface => 'commandline' })->store;
373     push @generated_lines, Koha::Account::Line->new({ borrowernumber => $patron->id, amountoutstanding => 0, interface => 'commandline' })->store;
374
375     my $lines = $account->lines;
376     is( $lines->_resultset->count, 10, "All accountlines (debits, credits and paid off) were fetched");
377
378     $schema->storage->txn_rollback;
379 };
380
381 subtest 'reconcile_balance' => sub {
382
383     plan tests => 4;
384
385     subtest 'more credit than debit' => sub {
386
387         plan tests => 6;
388
389         $schema->storage->txn_begin;
390
391         my $patron  = $builder->build_object({ class => 'Koha::Patrons' });
392         my $account = $patron->account;
393
394         # Add Credits
395         $account->add_credit({ amount => 1, interface => 'commandline' });
396         $account->add_credit({ amount => 2, interface => 'commandline' });
397         $account->add_credit({ amount => 3, interface => 'commandline' });
398         $account->add_credit({ amount => 4, interface => 'commandline' });
399         $account->add_credit({ amount => 5, interface => 'commandline' });
400
401         # Add Debits TODO: replace for calls to add_debit when time comes
402         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 1, amountoutstanding => 1, interface => 'commandline' })->store;
403         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 2, amountoutstanding => 2, interface => 'commandline' })->store;
404         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 3, amountoutstanding => 3, interface => 'commandline' })->store;
405         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 4, amountoutstanding => 4, interface => 'commandline' })->store;
406
407         # Paid Off
408         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 1, amountoutstanding => 0, interface => 'commandline' })->store;
409         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 1, amountoutstanding => 0, interface => 'commandline' })->store;
410
411         is( $account->balance(), -5, "Account balance is -5" );
412         is( $account->outstanding_debits->total_outstanding, 10, 'Outstanding debits sum 10' );
413         is( $account->outstanding_credits->total_outstanding, -15, 'Outstanding credits sum -15' );
414
415         $account->reconcile_balance();
416
417         is( $account->balance(), -5, "Account balance is -5" );
418         is( $account->outstanding_debits->total_outstanding, 0, 'No outstanding debits' );
419         is( $account->outstanding_credits->total_outstanding, -5, 'Outstanding credits sum -5' );
420
421         $schema->storage->txn_rollback;
422     };
423
424     subtest 'same debit as credit' => sub {
425
426         plan tests => 6;
427
428         $schema->storage->txn_begin;
429
430         my $patron  = $builder->build_object({ class => 'Koha::Patrons' });
431         my $account = $patron->account;
432
433         # Add Credits
434         $account->add_credit({ amount => 1, interface => 'commandline' });
435         $account->add_credit({ amount => 2, interface => 'commandline' });
436         $account->add_credit({ amount => 3, interface => 'commandline' });
437         $account->add_credit({ amount => 4, interface => 'commandline' });
438
439         # Add Debits TODO: replace for calls to add_debit when time comes
440         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 1, amountoutstanding => 1, interface => 'commandline' })->store;
441         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 2, amountoutstanding => 2, interface => 'commandline' })->store;
442         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 3, amountoutstanding => 3, interface => 'commandline' })->store;
443         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 4, amountoutstanding => 4, interface => 'commandline' })->store;
444
445         # Paid Off
446         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 1, amountoutstanding => 0, interface => 'commandline' })->store;
447         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 1, amountoutstanding => 0, interface => 'commandline' })->store;
448
449         is( $account->balance(), 0, "Account balance is 0" );
450         is( $account->outstanding_debits->total_outstanding, 10, 'Outstanding debits sum 10' );
451         is( $account->outstanding_credits->total_outstanding, -10, 'Outstanding credits sum -10' );
452
453         $account->reconcile_balance();
454
455         is( $account->balance(), 0, "Account balance is 0" );
456         is( $account->outstanding_debits->total_outstanding, 0, 'No outstanding debits' );
457         is( $account->outstanding_credits->total_outstanding, 0, 'Outstanding credits sum 0' );
458
459         $schema->storage->txn_rollback;
460     };
461
462     subtest 'more debit than credit' => sub {
463
464         plan tests => 6;
465
466         $schema->storage->txn_begin;
467
468         my $patron  = $builder->build_object({ class => 'Koha::Patrons' });
469         my $account = $patron->account;
470
471         # Add Credits
472         $account->add_credit({ amount => 1, interface => 'commandline' });
473         $account->add_credit({ amount => 2, interface => 'commandline' });
474         $account->add_credit({ amount => 3, interface => 'commandline' });
475         $account->add_credit({ amount => 4, interface => 'commandline' });
476
477         # Add Debits TODO: replace for calls to add_debit when time comes
478         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 1, amountoutstanding => 1, interface => 'commandline' })->store;
479         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 2, amountoutstanding => 2, interface => 'commandline' })->store;
480         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 3, amountoutstanding => 3, interface => 'commandline' })->store;
481         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 4, amountoutstanding => 4, interface => 'commandline' })->store;
482         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 5, amountoutstanding => 5, interface => 'commandline' })->store;
483
484         # Paid Off
485         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 1, amountoutstanding => 0, interface => 'commandline' })->store;
486         Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 1, amountoutstanding => 0, interface => 'commandline' })->store;
487
488         is( $account->balance(), 5, "Account balance is 5" );
489         is( $account->outstanding_debits->total_outstanding, 15, 'Outstanding debits sum 15' );
490         is( $account->outstanding_credits->total_outstanding, -10, 'Outstanding credits sum -10' );
491
492         $account->reconcile_balance();
493
494         is( $account->balance(), 5, "Account balance is 5" );
495         is( $account->outstanding_debits->total_outstanding, 5, 'Outstanding debits sum 5' );
496         is( $account->outstanding_credits->total_outstanding, 0, 'Outstanding credits sum 0' );
497
498         $schema->storage->txn_rollback;
499     };
500
501     subtest 'credits are applied to older debits first' => sub {
502
503         plan tests => 9;
504
505         $schema->storage->txn_begin;
506
507         my $patron  = $builder->build_object({ class => 'Koha::Patrons' });
508         my $account = $patron->account;
509
510         # Add Credits
511         $account->add_credit({ amount => 1, interface => 'commandline' });
512         $account->add_credit({ amount => 3, interface => 'commandline' });
513
514         # Add Debits TODO: replace for calls to add_debit when time comes
515         my $debit_1 = Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 1, amountoutstanding => 1, interface => 'commandline' })->store;
516         my $debit_2 = Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 2, amountoutstanding => 2, interface => 'commandline' })->store;
517         my $debit_3 = Koha::Account::Line->new({ borrowernumber => $patron->id, amount => 3, amountoutstanding => 3, interface => 'commandline' })->store;
518
519         is( $account->balance(), 2, "Account balance is 2" );
520         is( $account->outstanding_debits->total_outstanding, 6, 'Outstanding debits sum 6' );
521         is( $account->outstanding_credits->total_outstanding, -4, 'Outstanding credits sum -4' );
522
523         $account->reconcile_balance();
524
525         is( $account->balance(), 2, "Account balance is 2" );
526         is( $account->outstanding_debits->total_outstanding, 2, 'Outstanding debits sum 2' );
527         is( $account->outstanding_credits->total_outstanding, 0, 'Outstanding credits sum 0' );
528
529         $debit_1->discard_changes;
530         is( $debit_1->amountoutstanding + 0, 0, 'Old debit payed' );
531         $debit_2->discard_changes;
532         is( $debit_2->amountoutstanding + 0, 0, 'Old debit payed' );
533         $debit_3->discard_changes;
534         is( $debit_3->amountoutstanding + 0, 2, 'Newest debit only partially payed' );
535
536         $schema->storage->txn_rollback;
537     };
538 };
539
540 subtest 'pay() tests' => sub {
541
542     plan tests => 2;
543
544     $schema->storage->txn_begin;
545
546     my $patron  = $builder->build_object({ class => 'Koha::Patrons' });
547     my $library = $builder->build_object({ class => 'Koha::Libraries' });
548     my $account = $patron->account;
549
550     my $context = Test::MockModule->new('C4::Context');
551     $context->mock( 'userenv', { branch => $library->id } );
552
553     my $credit_1_id = $account->pay({ amount => 200 });
554     my $credit_1    = Koha::Account::Lines->find( $credit_1_id );
555
556     is( $credit_1->branchcode, undef, 'No branchcode is set if library_id was not passed' );
557
558     my $credit_2_id = $account->pay({ amount => 150, library_id => $library->id });
559     my $credit_2    = Koha::Account::Lines->find( $credit_2_id );
560
561     is( $credit_2->branchcode, $library->id, 'branchcode set because library_id was passed' );
562
563     $schema->storage->txn_rollback;
564 };