Bug 28854: (QA follow-up) Remove duplicate key test
[koha.git] / t / db_dependent / Koha / Checkouts / ReturnClaim.t
1 #!/usr/bin/perl
2
3 # This file is part of Koha
4 #
5 # Koha is free software; you can redistribute it and/or modify it
6 # under the terms of the GNU General Public License as published by
7 # the Free Software Foundation; either version 3 of the License, or
8 # (at your option) any later version.
9 #
10 # Koha is distributed in the hope that it will be useful, but
11 # WITHOUT ANY WARRANTY; without even the implied warranty of
12 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 # GNU General Public License for more details.
14 #
15 # You should have received a copy of the GNU General Public License
16 # along with Koha; if not, see <http://www.gnu.org/licenses>.
17
18 use Modern::Perl;
19
20 use Test::More tests => 6;
21 use Test::Exception;
22
23 use Koha::Database;
24 use Koha::DateUtils qw( dt_from_string output_pref );
25 use Koha::Checkouts::ReturnClaims;
26
27 use t::lib::TestBuilder;
28
29 my $schema  = Koha::Database->new->schema;
30 my $builder = t::lib::TestBuilder->new;
31
32 subtest "store() tests" => sub {
33
34     plan tests => 11;
35
36     $schema->storage->txn_begin;
37
38     my $librarian = $builder->build_object({ class => 'Koha::Patrons' });
39     my $patron    = $builder->build_object({ class => 'Koha::Patrons' });
40     my $item      = $builder->build_sample_item;
41
42     my $checkout = $builder->build_object(
43         {
44             class => 'Koha::Checkouts',
45             value => {
46                 borrowernumber => $patron->borrowernumber,
47                 itemnumber     => $item->itemnumber,
48                 branchcode     => $patron->branchcode
49             }
50         }
51     );
52
53     throws_ok
54         { Koha::Checkouts::ReturnClaim->new(
55             {
56                 issue_id       => $checkout->id,
57                 itemnumber     => $checkout->itemnumber,
58                 borrowernumber => $checkout->borrowernumber,
59                 notes          => 'Some notes'
60             }
61           )->store }
62         'Koha::Exceptions::Checkouts::ReturnClaims::NoCreatedBy',
63         'Exception thrown if no created_by passed on creation';
64
65     my $old_checkout = $builder->build_object(
66         {
67             class => 'Koha::Old::Checkouts',
68             value => {
69                 borrowernumber => $patron->borrowernumber,
70                 itemnumber     => $item->itemnumber,
71                 branchcode     => $patron->branchcode
72             }
73         }
74     );
75
76     my $nullable_created_by = Koha::Checkouts::ReturnClaim->new(
77         {
78             issue_id       => $old_checkout->id,
79             itemnumber     => $old_checkout->itemnumber,
80             borrowernumber => $old_checkout->borrowernumber,
81             notes          => 'Some notes',
82             created_by     => $librarian->borrowernumber
83         }
84     )->store;
85     is( $nullable_created_by->created_by, $librarian->borrowernumber, 'Claim created with created_by set' );
86     ok( $nullable_created_by->in_storage, 'In storage' );
87
88     $nullable_created_by->created_by(undef)->store();
89     is( $nullable_created_by->created_by, undef, 'Deletion was deleted' );
90     ok( $nullable_created_by->in_storage, 'In storage' );
91     is(
92         ref($nullable_created_by->notes('Some other note')->store),
93         'Koha::Checkouts::ReturnClaim',
94         'Subsequent store succeeds after created_by has been unset'
95     );
96
97     is( Koha::Checkouts::ReturnClaims->search({ issue_id => $checkout->id })->count, 0, 'No claims stored' );
98
99     my $claim = Koha::Checkouts::ReturnClaim->new(
100         {
101             issue_id       => $checkout->id,
102             itemnumber     => $checkout->itemnumber,
103             borrowernumber => $checkout->borrowernumber,
104             notes          => 'Some notes',
105             created_by     => $librarian->borrowernumber
106         }
107     )->store;
108
109     is( ref($claim), 'Koha::Checkouts::ReturnClaim', 'Object type is correct' );
110     is( Koha::Checkouts::ReturnClaims->search( { issue_id => $checkout->id } )->count, 1, 'Claim stored on the DB');
111
112     {    # hide useless warnings
113         local *STDERR;
114         open STDERR, '>', '/dev/null';
115
116         my $another_checkout = $builder->build_object({ class => 'Koha::Checkouts' });
117         my $checkout_id = $another_checkout->id;
118         $another_checkout->delete;
119
120         my $THE_claim;
121
122         throws_ok {
123             $THE_claim = Koha::Checkouts::ReturnClaim->new(
124                 {
125                     issue_id       => $checkout_id,
126                     itemnumber     => $checkout->itemnumber,
127                     borrowernumber => $checkout->borrowernumber,
128                     notes          => 'Some notes',
129                     created_by     => $librarian->borrowernumber
130                 }
131             )->store;
132         }
133         'Koha::Exceptions::Object::FKConstraint',
134           'An exception is thrown on invalid issue_id';
135         close STDERR;
136
137         is( $@->broken_fk, 'issue_id', 'Exception field is correct' );
138     }
139
140     $schema->storage->txn_rollback;
141 };
142
143 subtest "resolve() tests" => sub {
144
145     plan tests => 9;
146
147     $schema->storage->txn_begin;
148
149     my $itemlost  = 1;
150     my $librarian = $builder->build_object({ class => 'Koha::Patrons' });
151     my $patron    = $builder->build_object({ class => 'Koha::Patrons' });
152     my $item      = $builder->build_sample_item({ itemlost => $itemlost });
153
154     my $checkout = $builder->build_object(
155         {
156             class => 'Koha::Checkouts',
157             value => {
158                 borrowernumber => $patron->borrowernumber,
159                 itemnumber     => $item->itemnumber,
160                 branchcode     => $patron->branchcode
161             }
162         }
163     );
164
165     my $claim = Koha::Checkouts::ReturnClaim->new(
166         {
167             issue_id       => $checkout->id,
168             itemnumber     => $checkout->itemnumber,
169             borrowernumber => $checkout->borrowernumber,
170             notes          => 'Some notes',
171             created_by     => $librarian->borrowernumber
172         }
173     )->store;
174
175     throws_ok
176         { $claim->resolve({ resolution => 1 }); }
177         'Koha::Exceptions::MissingParameter',
178         "Not passing 'resolved_by' makes it throw an exception";
179
180     throws_ok
181         { $claim->resolve({ resolved_by => 1 }); }
182         'Koha::Exceptions::MissingParameter',
183         "Not passing 'resolution' makes it throw an exception";
184
185     my $deleted_patron = $builder->build_object({ class => 'Koha::Patrons' });
186     my $deleted_patron_id = $deleted_patron->id;
187     $deleted_patron->delete;
188
189     {   # hide useless warnings
190         local *STDERR;
191         open STDERR, '>', '/dev/null';
192
193         throws_ok
194             { $claim->resolve({ resolution => "X", resolved_by => $deleted_patron_id }) }
195             'Koha::Exceptions::Object::FKConstraint',
196             "Exception thrown on invalid resolver";
197
198         close STDERR;
199     }
200
201     my $today    = dt_from_string;
202     my $tomorrow = dt_from_string->add( days => 1 );
203
204     $claim->resolve(
205         {
206             resolution  => "X",
207             resolved_by => $librarian->id,
208             resolved_on => $tomorrow,
209         }
210     )->discard_changes;
211
212     is( output_pref( { str => $claim->resolved_on } ), output_pref( { dt => $tomorrow } ), 'resolved_on set to the passed param' );
213     is( $claim->updated_by, $librarian->id, 'updated_by set to the passed resolved_by' );
214
215     # Make sure $item is refreshed
216     $item->discard_changes;
217     is( $item->itemlost, $itemlost, 'Item lost status remains unchanged' );
218
219     # New checkout and claim
220     $checkout->delete;
221     $checkout = $builder->build_object(
222         {
223             class => 'Koha::Checkouts',
224             value => {
225                 borrowernumber => $patron->borrowernumber,
226                 itemnumber     => $item->itemnumber,
227                 branchcode     => $patron->branchcode
228             }
229         }
230     );
231
232     $claim = Koha::Checkouts::ReturnClaim->new(
233         {
234             issue_id       => $checkout->id,
235             itemnumber     => $checkout->itemnumber,
236             borrowernumber => $checkout->borrowernumber,
237             notes          => 'Some notes',
238             created_by     => $librarian->borrowernumber
239         }
240     )->store;
241
242     my $new_lost_status = 2;
243
244     $claim->resolve(
245         {
246             resolution      => "X",
247             resolved_by     => $librarian->id,
248             resolved_on     => $tomorrow,
249             new_lost_status => $new_lost_status,
250         }
251     )->discard_changes;
252
253     is( output_pref( { str => $claim->resolved_on } ), output_pref( { dt => $tomorrow } ), 'resolved_on set to the passed param' );
254     is( $claim->updated_by, $librarian->id, 'updated_by set to the passed resolved_by' );
255
256     # Make sure $item is refreshed
257     $item->discard_changes;
258     is( $item->itemlost, $new_lost_status, 'Item lost status is updated' );
259
260     $schema->storage->txn_rollback;
261 };
262
263 subtest 'item() tests' => sub {
264
265     plan tests => 3;
266
267     $schema->storage->txn_begin;
268
269     my $librarian = $builder->build_object({ class => 'Koha::Patrons' });
270     my $patron    = $builder->build_object({ class => 'Koha::Patrons' });
271     my $item      = $builder->build_sample_item;
272     my $checkout = $builder->build_object(
273         {
274             class => 'Koha::Checkouts',
275             value => {
276                 borrowernumber => $patron->borrowernumber,
277                 itemnumber     => $item->itemnumber,
278                 branchcode     => $patron->branchcode
279             }
280         }
281     );
282
283     my $claim = Koha::Checkouts::ReturnClaim->new(
284         {
285             issue_id       => $checkout->id,
286             itemnumber     => $checkout->itemnumber,
287             borrowernumber => $checkout->borrowernumber,
288             notes          => 'Some notes',
289             created_by     => $librarian->borrowernumber
290         }
291     )->store;
292
293     my $return_claim_item = $claim->item;
294     is( ref( $return_claim_item ), 'Koha::Item', 'Koha::Checkouts::ReturnClaim->item should return a Koha::Item' );
295     is( $claim->itemnumber, $return_claim_item->itemnumber, 'Koha::Checkouts::ReturnClaim->item should return the correct item' );
296
297     my $itemnumber = $item->itemnumber;
298     $checkout->delete; # Required to allow deletion of item
299     $item->delete;
300
301     my $claims = Koha::Checkouts::ReturnClaims->search({ itemnumber => $itemnumber });
302     is( $claims->count, 0, 'Koha::Checkouts::ReturnClaim is deleted on item deletion' );
303
304     $schema->storage->txn_rollback;
305 };
306
307 subtest 'patron() tests' => sub {
308
309     plan tests => 3;
310
311     $schema->storage->txn_begin;
312
313     my $librarian = $builder->build_object({ class => 'Koha::Patrons' });
314     my $patron    = $builder->build_object({ class => 'Koha::Patrons' });
315     my $item      = $builder->build_sample_item;
316     my $checkout = $builder->build_object(
317         {
318             class => 'Koha::Checkouts',
319             value => {
320                 borrowernumber => $patron->borrowernumber,
321                 itemnumber     => $item->itemnumber,
322                 branchcode     => $patron->branchcode
323             }
324         }
325     );
326
327     my $claim = Koha::Checkouts::ReturnClaim->new(
328         {
329             issue_id       => $checkout->id,
330             itemnumber     => $checkout->itemnumber,
331             borrowernumber => $checkout->borrowernumber,
332             notes          => 'Some notes',
333             created_by     => $librarian->borrowernumber
334         }
335     )->store;
336
337     my $return_claim_patron = $claim->patron;
338     is( ref( $return_claim_patron ), 'Koha::Patron', 'Koha::Checkouts::ReturnClaim->patron should return a Koha::Patron' );
339     is( $claim->borrowernumber, $return_claim_patron->borrowernumber, 'Koha::Checkouts::ReturnClaim->patron should return the correct borrower' );
340
341     my $borrowernumber = $patron->borrowernumber;
342     $checkout->delete; # Required to allow deletion of patron
343     $patron->delete;
344
345     my $claims = Koha::Checkouts::ReturnClaims->search({ borrowernumber => $borrowernumber });
346     is( $claims->count, 0, 'Koha::Checkouts::ReturnClaim is deleted on borrower deletion' );
347
348     $schema->storage->txn_rollback;
349 };
350
351 subtest 'old_checkout() tests' => sub {
352
353     plan tests => 4;
354
355     $schema->storage->txn_begin;
356
357     my $librarian = $builder->build_object({ class => 'Koha::Patrons' });
358     my $patron    = $builder->build_object({ class => 'Koha::Patrons' });
359     my $item      = $builder->build_sample_item;
360     my $old_checkout = $builder->build_object(
361         {
362             class => 'Koha::Old::Checkouts',
363             value => {
364                 borrowernumber => $patron->borrowernumber,
365                 itemnumber     => $item->itemnumber,
366                 branchcode     => $patron->branchcode
367             }
368         }
369     );
370
371     my $claim = Koha::Checkouts::ReturnClaim->new(
372         {
373             issue_id       => $old_checkout->id,
374             itemnumber     => $old_checkout->itemnumber,
375             borrowernumber => $old_checkout->borrowernumber,
376             notes          => 'Some notes',
377             created_by     => $librarian->borrowernumber
378         }
379     )->store;
380
381     my $return_claim_old_checkout = $claim->old_checkout;
382     is( ref( $return_claim_old_checkout ), 'Koha::Old::Checkout', 'Koha::Checkouts::ReturnClaim->old_checkout should return a Koha::Old::Checkout' );
383     is( $claim->issue_id, $return_claim_old_checkout->issue_id, 'Koha::Checkouts::ReturnClaim->old_checkout should return the correct borrower' );
384
385     my $issue_id = $old_checkout->issue_id;
386     $old_checkout->delete;
387
388     my $claims = Koha::Checkouts::ReturnClaims->search({ issue_id => $issue_id });
389     is( $claims->count, 1, 'Koha::Checkouts::ReturnClaim remains on old_checkout deletion' );
390     # FIXME: Should we actually set null on OldCheckout deletion?
391
392     $claim->issue_id(undef)->store;
393     is( $claim->old_checkout, undef, 'Koha::Checkouts::ReturnClaim->old_checkout should return undef if no old_checkout linked' );
394
395     $schema->storage->txn_rollback;
396 };
397
398 subtest 'checkout() tests' => sub {
399
400     plan tests => 4;
401
402     $schema->storage->txn_begin;
403
404     my $librarian = $builder->build_object({ class => 'Koha::Patrons' });
405     my $patron    = $builder->build_object({ class => 'Koha::Patrons' });
406     my $item      = $builder->build_sample_item;
407     my $checkout = $builder->build_object(
408         {
409             class => 'Koha::Checkouts',
410             value => {
411                 borrowernumber => $patron->borrowernumber,
412                 itemnumber     => $item->itemnumber,
413                 branchcode     => $patron->branchcode
414             }
415         }
416     );
417
418     my $claim = Koha::Checkouts::ReturnClaim->new(
419         {
420             issue_id       => $checkout->id,
421             itemnumber     => $checkout->itemnumber,
422             borrowernumber => $checkout->borrowernumber,
423             notes          => 'Some notes',
424             created_by     => $librarian->borrowernumber
425         }
426     )->store;
427
428     my $return_claim_checkout = $claim->checkout;
429     is( ref( $return_claim_checkout ), 'Koha::Checkout', 'Koha::Checkouts::ReturnClaim->checkout should return a Koha::Checkout' );
430     is( $claim->issue_id, $return_claim_checkout->issue_id, 'Koha::Checkouts::ReturnClaim->checkout should return the correct borrower' );
431
432     my $issue_id = $checkout->issue_id;
433     $checkout->delete;
434
435     my $claims = Koha::Checkouts::ReturnClaims->search({ issue_id => $issue_id });
436     is( $claims->count, 1, 'Koha::Checkouts::ReturnClaim remains on checkout deletion' );
437
438     $claim->issue_id(undef)->store;
439     is( $claim->checkout, undef, 'Koha::Checkouts::ReturnClaim->checkout should return undef if no checkout linked' );
440
441     $schema->storage->txn_rollback;
442 };