Bug 18292: Remove return 1 statements in tests
[koha.git] / t / db_dependent / Serials.t
1 #!/usr/bin/perl
2 #
3 # This Koha test module is a stub!
4 # Add more tests here!!!
5
6 use Modern::Perl;
7 use YAML;
8
9 use CGI qw ( -utf8 );
10 use C4::Serials;
11 use C4::Serials::Frequency;
12 use C4::Serials::Numberpattern;
13 use C4::Debug;
14 use C4::Biblio;
15 use C4::Budgets;
16 use C4::Items;
17 use Koha::DateUtils;
18 use Koha::Acquisition::Booksellers;
19 use t::lib::Mocks;
20 use t::lib::TestBuilder;
21 use Test::More tests => 48;
22
23 BEGIN {
24     use_ok('C4::Serials');
25 }
26
27 my $dbh = C4::Context->dbh;
28
29 # Start transaction
30 $dbh->{AutoCommit} = 0;
31 $dbh->{RaiseError} = 1;
32
33 my $builder = t::lib::TestBuilder->new();
34
35 # This could/should be used for all untested methods
36 my @methods = ('updateClaim');
37 can_ok('C4::Serials', @methods);
38
39 $dbh->do(q|UPDATE marc_subfield_structure SET value_builder="callnumber.pl" where kohafield="items.itemcallnumber" and frameworkcode=''|);
40
41 my $bookseller = Koha::Acquisition::Bookseller->new(
42     {
43         name => "my vendor",
44         address1 => "bookseller's address",
45         phone => "0123456",
46         active => 1
47     }
48 );
49
50 my ($biblionumber, $biblioitemnumber) = AddBiblio(MARC::Record->new, '');
51
52 my $budgetid;
53 my $bpid = AddBudgetPeriod({
54     budget_period_startdate   => '01-01-2015',
55     budget_period_enddate     => '31-12-2015',
56     budget_period_description => "budget desc"
57 });
58
59 my $budget_id = AddBudget({
60     budget_code        => "ABCD",
61     budget_amount      => "123.132",
62     budget_name        => "Périodiques",
63     budget_notes       => "This is a note",
64     budget_period_id   => $bpid
65 });
66
67 my $frequency_id = AddSubscriptionFrequency({ description => "Test frequency 1" });
68 my $pattern_id = AddSubscriptionNumberpattern({
69     label => 'Test numberpattern 1',
70     numberingmethod => '{X}',
71     label1 => q{},
72     add1 => 1,
73     every1 => 1,
74     every1 => 1,
75     numbering1 => 1,
76     whenmorethan1 => 1,
77 });
78
79 my $notes = 'notes';
80 my $internalnotes = 'intnotes';
81 my $subscriptionid = NewSubscription(
82     undef,      "",     undef, undef, $budget_id, $biblionumber,
83     '2013-01-01', $frequency_id, undef, undef,  undef,
84     undef,      undef,  undef, undef, undef, undef,
85     1,          $notes,undef, '2013-01-01', undef, $pattern_id,
86     undef,       undef,  0,    $internalnotes,  0,
87     undef, undef, 0,          undef,         '2013-12-31', 0
88 );
89
90 my $subscriptioninformation = GetSubscription( $subscriptionid );
91
92 is( $subscriptioninformation->{notes}, $notes, 'NewSubscription should set notes' );
93 is( $subscriptioninformation->{internalnotes}, $internalnotes, 'NewSubscription should set internalnotes' );
94
95 my $subscription_history = C4::Serials::GetSubscriptionHistoryFromSubscriptionId($subscriptionid);
96 is( $subscription_history->{opacnote}, '', 'NewSubscription should not set subscriptionhistory opacnotes' );
97 is( $subscription_history->{librariannote}, '', 'NewSubscription should not set subscriptionhistory librariannotes' );
98
99 my @subscriptions = SearchSubscriptions({string => $subscriptioninformation->{bibliotitle}, orderby => 'title' });
100 isa_ok( \@subscriptions, 'ARRAY' );
101
102 @subscriptions = SearchSubscriptions({ issn => $subscriptioninformation->{issn}, orderby => 'title' });
103 isa_ok( \@subscriptions, 'ARRAY' );
104
105 @subscriptions = SearchSubscriptions({ ean => $subscriptioninformation->{ean}, orderby => 'title' });
106 isa_ok( \@subscriptions, 'ARRAY' );
107
108 @subscriptions = SearchSubscriptions({ biblionumber => $subscriptioninformation->{bibnum}, orderby => 'title' });
109 isa_ok( \@subscriptions, 'ARRAY' );
110
111 my $frequency = GetSubscriptionFrequency($subscriptioninformation->{periodicity});
112 my $old_frequency;
113 if (not $frequency->{unit}) {
114     $old_frequency = $frequency->{id};
115     $frequency->{unit} = "month";
116     $frequency->{unitsperissue} = 1;
117     $frequency->{issuesperunit} = 1;
118     $frequency->{description} = "Frequency created by t/db_dependant/Serials.t";
119     $subscriptioninformation->{periodicity} = AddSubscriptionFrequency($frequency);
120     $subscriptioninformation->{serialsadditems} = 1;
121
122     ModSubscription( @$subscriptioninformation{qw(
123         librarian branchcode aqbooksellerid cost aqbudgetid startdate
124         periodicity firstacquidate irregularity numberpattern locale
125         numberlength weeklength monthlength lastvalue1 innerloop1 lastvalue2
126         innerloop2 lastvalue3 innerloop3 status biblionumber callnumber notes
127         letter manualhistory internalnotes serialsadditems staffdisplaycount
128         opacdisplaycount graceperiod location enddate subscriptionid
129         skip_serialseq
130     )} );
131 }
132 my $expirationdate = GetExpirationDate($subscriptionid) ;
133 ok( $expirationdate, "expiration date is not NULL" );
134
135 ok(C4::Serials::GetSubscriptionHistoryFromSubscriptionId($subscriptionid), 'test getting history from sub-scription');
136
137 my ($serials_count, @serials) = GetSerials($subscriptionid);
138 ok($serials_count > 0, 'Subscription has at least one serial');
139 my $serial = $serials[0];
140
141 ok(C4::Serials::GetSerialStatusFromSerialId($serial->{serialid}), 'test getting Serial Status From Serial Id');
142
143 isa_ok(C4::Serials::GetSerialInformation($serial->{serialid}), 'HASH', 'test getting Serial Information');
144
145 subtest 'Values should not be erased on editing' => sub {
146
147     plan tests => 1;
148
149     ( $biblionumber, $biblioitemnumber ) = get_biblio();
150     my ( $icn_tag, $icn_sf ) = GetMarcFromKohaField( 'items.itemcallnumber', '' );
151     my ( $it_tag, $it_sf )   = GetMarcFromKohaField( 'items.itype', '' );
152
153     my $itemtype = $builder->build( { source => 'Itemtype' } )->{itemtype};
154     my $itemcallnumber = 'XXXmy itemcallnumberXXX';
155
156     my $item_record    = new MARC::Record;
157
158     $item_record->append_fields(
159         MARC::Field->new( '080', '', '', "a" => "default" ),
160         MARC::Field->new(
161             $icn_tag, '', '',
162             $icn_sf => $itemcallnumber,
163             $it_sf  => $itemtype
164         )
165     );
166     my ( undef, undef, $itemnumber ) = C4::Items::AddItemFromMarc( $item_record, $biblionumber );
167     my $serialid = C4::Serials::NewIssue( "serialseq", $subscriptionid, $biblionumber,
168                                           1, undef, undef, "publisheddatetext", "notes" );
169     C4::Serials::AddItem2Serial( $serialid, $itemnumber );
170     my $serial_info = C4::Serials::GetSerialInformation($serialid);
171     my ($itemcallnumber_info) = grep { $_->{kohafield} eq 'items.itemcallnumber' }
172                                      @{ $serial_info->{items}[0]->{iteminformation} };
173     like( $itemcallnumber_info->{marc_value}, qr|value="$itemcallnumber"| );
174 };
175
176 # Delete created frequency
177 if ($old_frequency) {
178     my $freq_to_delete = $subscriptioninformation->{periodicity};
179     $subscriptioninformation->{periodicity} = $old_frequency;
180
181     ModSubscription( @$subscriptioninformation{qw(
182         librarian branchcode aqbooksellerid cost aqbudgetid startdate
183         periodicity firstacquidate irregularity numberpattern locale
184         numberlength weeklength monthlength lastvalue1 innerloop1 lastvalue2
185         innerloop2 lastvalue3 innerloop3 status biblionumber callnumber notes
186         letter manualhistory internalnotes serialsadditems staffdisplaycount
187         opacdisplaycount graceperiod location enddate subscriptionid
188         skip_serialseq
189     )} );
190
191     DelSubscriptionFrequency($freq_to_delete);
192 }
193
194 # Test calling subs without parameters
195 is(C4::Serials::AddItem2Serial(), undef, 'test adding item to serial');
196 is(C4::Serials::GetFullSubscription(), undef, 'test getting full subscription');
197 is(C4::Serials::PrepareSerialsData(), undef, 'test preparing serial data');
198 is(C4::Serials::GetSubscriptionsFromBiblionumber(), undef, 'test getting subscriptions form biblio number');
199
200 is(C4::Serials::GetSerials(), undef, 'test getting serials when you enter nothing');
201 is(C4::Serials::GetSerials2(), undef, 'test getting serials when you enter nothing');
202
203 is(C4::Serials::GetLatestSerials(), undef, 'test getting lastest serials');
204
205 is(C4::Serials::GetDistributedTo(), undef, 'test getting distributed when nothing is entered');
206
207 is(C4::Serials::GetNextSeq(), undef, 'test getting next seq when you enter nothing');
208
209 is(C4::Serials::GetSeq(), undef, 'test getting seq when you enter nothing');
210
211 is(C4::Serials::CountSubscriptionFromBiblionumber(), undef, 'test counting subscription when nothing is entered');
212
213 is(C4::Serials::ModSubscriptionHistory(), undef, 'test modding subscription history');
214
215 is(C4::Serials::ModSerialStatus(),undef, 'test modding serials');
216
217 is(C4::Serials::findSerialsByStatus(), 0, 'test finding serial by status with no parameters');
218
219 is(C4::Serials::NewIssue(), undef, 'test getting 0 when nothing is entered');
220
221 is(C4::Serials::HasSubscriptionStrictlyExpired(), undef, 'test if the subscriptions has expired');
222 is(C4::Serials::HasSubscriptionExpired(), undef, 'test if the subscriptions has expired');
223
224 is(C4::Serials::GetLateOrMissingIssues(), undef, 'test getting last or missing issues');
225
226 subtest 'test_updateClaim' => sub {
227     plan tests => 11;
228
229     my $today = output_pref({ dt => dt_from_string, dateonly => 1 });
230     # Given ... nothing much
231     # When ... Then ...
232     my $result_0 = C4::Serials::updateClaim(undef);
233     is($result_0, undef, 'Got the expected undef from update claim with nothin');
234
235     # Given ... 3 serial. 2 of them updated.
236     my $serialids_1   = [90980, 90981];
237     my $claimdate_1   = dt_from_string('2001-01-13'); # arbitrary date some time in the past.
238     my $claim_count_1 = 5;
239     Koha::Serial->new( { serialid => $serialids_1->[0], serialseq => 'serialseq', subscriptionid => $subscriptionid, status => 3,
240                          biblionumber => 12345, claimdate => $claimdate_1, claims_count => $claim_count_1, } )->store();
241     Koha::Serial->new( { serialid => $serialids_1->[1], serialseq => 'serialseq', subscriptionid => $subscriptionid, status => 3,
242                          biblionumber => 12345, claimdate => $claimdate_1, claims_count => $claim_count_1,  } )->store();
243     Koha::Serial->new( { serialid => 90982, serialseq => 'serialseq', subscriptionid => $subscriptionid, status => 3,
244                          biblionumber => 12345, claimdate => $claimdate_1, claims_count => $claim_count_1,  } )->store();
245
246     # When ...
247     my $result_1 = C4::Serials::updateClaim($serialids_1);
248
249     # Then ...
250     is($result_1, 2, 'Got the expected 2 from update claim with 2 serial ids');
251
252     my @late_or_missing_issues_1_0 = C4::Serials::GetLateOrMissingIssues(undef, $serialids_1->[0]);
253     is($late_or_missing_issues_1_0[0]->{claimdate}, $today, 'Got the expected first different claim date from update claim');
254     is($late_or_missing_issues_1_0[0]->{claims_count}, $claim_count_1+1, 'Got the expected first claim count from update claim');
255     is($late_or_missing_issues_1_0[0]->{status}, 7, 'Got the expected first claim status from update claim');
256
257     my @late_or_missing_issues_1_1 = C4::Serials::GetLateOrMissingIssues(undef, $serialids_1->[1]);
258     is($late_or_missing_issues_1_1[0]->{claimdate}, $today, 'Got the expected second different claim date from update claim');
259     is($late_or_missing_issues_1_1[0]->{claims_count}, $claim_count_1+1, 'Got the expected second claim count from update claim');
260     is($late_or_missing_issues_1_1[0]->{status}, 7, 'Got the expected second claim status from update claim');
261
262     my @late_or_missing_issues_1_2 = C4::Serials::GetLateOrMissingIssues(undef, 90982);
263     is($late_or_missing_issues_1_2[0]->{claimdate}, output_pref({ dt => $claimdate_1, dateonly => 1}), 'Got the expected unchanged claim date from update claim');
264     is($late_or_missing_issues_1_2[0]->{claims_count}, $claim_count_1, 'Got the expected unchanged claim count from update claim');
265     is($late_or_missing_issues_1_2[0]->{status}, 3, 'Got the expected unchanged claim status from update claim');
266 };
267
268 is(C4::Serials::check_routing(), undef, 'test checking route');
269
270 is(C4::Serials::addroutingmember(),undef, 'test adding route member');
271
272
273 # Unit tests for statuses management (Bug 11689)
274 $subscriptionid = NewSubscription(
275     undef,      "",     undef, undef, $budget_id, $biblionumber,
276     '2013-01-01', $frequency_id, undef, undef,  undef,
277     undef,      undef,  undef, undef, undef, undef,
278     1,          $notes,undef, '2013-01-01', undef, $pattern_id,
279     undef,       undef,  0,    $internalnotes,  0,
280     undef, undef, 0,          undef,         '2013-12-31', 0
281 );
282 my $total_issues;
283 ( $total_issues, @serials ) = C4::Serials::GetSerials( $subscriptionid );
284 is( $total_issues, 1, "NewSubscription created a first serial" );
285 is( @serials, 1, "GetSerials returns the serial" );
286 my $subscription = C4::Serials::GetSubscription($subscriptionid);
287 my $pattern = C4::Serials::Numberpattern::GetSubscriptionNumberpattern($subscription->{numberpattern});
288 ( $total_issues, @serials ) = C4::Serials::GetSerials( $subscriptionid );
289 my $publisheddate = output_pref({ dt => dt_from_string, dateformat => 'iso', dateonly => 1 });
290 ( $total_issues, @serials ) = C4::Serials::GetSerials( $subscriptionid );
291 my $nextpublisheddate = C4::Serials::GetNextDate($subscription, $publisheddate, 1);
292 my @statuses = qw( 2 2 3 3 3 3 3 4 4 41 42 43 44 5 );
293 # Add 14 serials
294 my $counter = 0;
295 for my $status ( @statuses ) {
296     my $serialseq = "No.".$counter;
297     my ( $expected_serial ) = GetSerials2( $subscriptionid, [1] );
298     C4::Serials::ModSerialStatus( $expected_serial->{serialid}, $serialseq, $publisheddate, $publisheddate, $publisheddate, $statuses[$counter], 'an useless note' );
299     $counter++;
300 }
301 # Here we have 15 serials with statuses : 2*2 + 5*3 + 2*4 + 1*41 + 1*42 + 1*43 + 1*44 + 1*5 + 1*1
302 my @serialsByStatus = C4::Serials::findSerialsByStatus(2,$subscriptionid);
303 is(@serialsByStatus,2,"findSerialsByStatus returns all serials with chosen status");
304 ( $total_issues, @serials ) = C4::Serials::GetSerials( $subscriptionid );
305 is( $total_issues, @statuses + 1, "GetSerials returns total_issues" );
306 my @arrived_missing = map { my $status = $_->{status}; ( grep { /^$status$/ } qw( 2 4 41 42 43 44 5 ) ) ? $_ : () } @serials;
307 my @others = map { my $status = $_->{status}; ( grep { /^$status$/ } qw( 2 4 41 42 43 44 5 ) ) ? () : $_ } @serials;
308 is( @arrived_missing, 5, "GetSerials returns 5 arrived/missing by default" );
309 is( @others, 6, "GetSerials returns all serials not arrived and not missing" );
310
311 ( $total_issues, @serials ) = C4::Serials::GetSerials( $subscriptionid, 10 );
312 is( $total_issues, @statuses + 1, "GetSerials returns total_issues" );
313 @arrived_missing = map { my $status = $_->{status}; ( grep { /^$status$/ } qw( 2 4 41 42 43 44 5 ) ) ? $_ : () } @serials;
314 @others = map { my $status = $_->{status}; ( grep { /^$status$/ } qw( 2 4 41 42 43 44 5 ) ) ? () : $_ } @serials;
315 is( @arrived_missing, 9, "GetSerials returns all arrived/missing if count given" );
316 is( @others, 6, "GetSerials returns all serials not arrived and not missing if count given" );
317
318 $subscription = C4::Serials::GetSubscription($subscriptionid); # Retrieve the updated subscription
319
320 my @serialseqs;
321 for my $am ( @arrived_missing ) {
322     if ( grep {/^$am->{status}$/} qw( 4 41 42 43 44 ) ) {
323         push @serialseqs, $am->{serialseq}
324     } elsif ( grep {/^$am->{status}$/} qw( 5 ) ) {
325         push @serialseqs, 'not issued ' . $am->{serialseq};
326     }
327 }
328 is( $subscription->{missinglist}, join('; ', @serialseqs), "subscription missinglist is updated after ModSerialStatus" );
329
330 subtest "Do not generate an expected if one already exists" => sub {
331     plan tests => 2;
332     my ($expected_serial) = GetSerials2( $subscriptionid, [1] );
333
334     #Find serialid for serial with status Expected
335     my $serialexpected = ( C4::Serials::findSerialsByStatus( 1, $subscriptionid ) )[0];
336
337     #delete serial with status Expected
338     C4::Serials::ModSerialStatus( $serialexpected->{serialid}, $serialexpected->{serialseq}, $publisheddate, $publisheddate, $publisheddate, '1', 'an useless note' );
339     @serialsByStatus = C4::Serials::findSerialsByStatus( 1, $subscriptionid );
340     is( @serialsByStatus, 1, "ModSerialStatus delete corectly serial expected and create another if not exist" );
341
342     # add 1 serial with status=Expected 1
343     C4::Serials::ModSerialStatus( $expected_serial->{serialid}, 'NO.20', $publisheddate, $publisheddate, $publisheddate, '1', 'an useless note' );
344
345     #Now we have two serials it have status expected
346     #put status delete for last serial
347     C4::Serials::ModSerialStatus( $serialexpected->{serialid}, $serialexpected->{serialseq}, $publisheddate, $publisheddate, $publisheddate, '1', 'an useless note' );
348
349     #try if create or not another serial with status is expected
350     @serialsByStatus = C4::Serials::findSerialsByStatus( 1, $subscriptionid );
351     is( @serialsByStatus, 1, "ModSerialStatus delete corectly serial expected and not create another if exists" );
352 };
353
354 $dbh->rollback;
355
356 sub get_biblio {
357     my $bib = MARC::Record->new();
358     $bib->append_fields(
359         MARC::Field->new('100', ' ', ' ', a => 'Moffat, Steven'),
360         MARC::Field->new('245', ' ', ' ', a => 'Silence in the library'),
361     );
362     my ($bibnum, $bibitemnum) = AddBiblio($bib, '');
363     return ($bibnum, $bibitemnum);
364 }