Bug 14045: Add specific quotas to on-site checkouts
[srvgit] / t / db_dependent / Circulation / TooMany.t
1 #!/usr/bin/perl
2
3 use Modern::Perl;
4 use Test::More tests => 6;
5 use C4::Context;
6
7 use C4::Biblio;
8 use C4::Members;
9 use C4::Branch;
10 use C4::Circulation;
11 use C4::Items;
12 use C4::Context;
13
14 use Koha::DateUtils qw( dt_from_string );
15
16 use t::lib::TestBuilder;
17 use t::lib::Mocks;
18
19 our $dbh = C4::Context->dbh;
20 $dbh->{AutoCommit} = 0;
21 $dbh->{RaiseError} = 1;
22
23 $dbh->do(q|DELETE FROM issues|);
24 $dbh->do(q|DELETE FROM items|);
25 $dbh->do(q|DELETE FROM borrowers|);
26 $dbh->do(q|DELETE FROM branches|);
27 $dbh->do(q|DELETE FROM categories|);
28 $dbh->do(q|DELETE FROM accountlines|);
29 $dbh->do(q|DELETE FROM itemtypes|);
30 $dbh->do(q|DELETE FROM branch_item_rules|);
31 $dbh->do(q|DELETE FROM branch_borrower_circ_rules|);
32 $dbh->do(q|DELETE FROM default_branch_circ_rules|);
33 $dbh->do(q|DELETE FROM default_circ_rules|);
34 $dbh->do(q|DELETE FROM default_branch_item_rules|);
35
36 my $builder = t::lib::TestBuilder->new();
37
38 my $branch = $builder->build({
39     source => 'Branch',
40 });
41
42 my $category = $builder->build({
43     source => 'Category',
44 });
45
46 my $patron = $builder->build({
47     source => 'Borrower',
48     value => {
49         categorycode => $category->{categorycode},
50         branchcode => $branch->{branchcode},
51     },
52 });
53
54 my $biblio = $builder->build({
55     source => 'Biblio',
56     value => {
57         branchcode => $branch->{branchcode},
58     },
59 });
60 my $item = $builder->build({
61     source => 'Item',
62     value => {
63         biblionumber => $biblio->{biblionumber},
64         homebranch => $branch->{branchcode},
65         holdingbranch => $branch->{branchcode},
66     },
67 });
68
69 C4::Context->_new_userenv ('DUMMY_SESSION_ID');
70 C4::Context->set_userenv($patron->{borrowernumber}, $patron->{userid}, 'usercnum', 'First name', 'Surname', $branch->{branchcode}, 'My Library', 0);
71
72 # TooMany return ($current_loan_count, $max_loans_allowed) or undef
73 # CO = Checkout
74 # OSCO: On-site checkout
75
76 subtest 'no rules exist' => sub {
77     plan tests => 2;
78     is(
79         C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ),
80         undef,
81         'CO should be allowed, in any cases'
82     );
83     is(
84         C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ),
85         undef,
86         'OSCO should be allowed, in any cases'
87     );
88 };
89
90 subtest '1 Issuingrule exist 0 0: no issue allowed' => sub {
91     plan tests => 4;
92     my $issuingrule = $builder->build({
93         source => 'Issuingrule',
94         value => {
95             branchcode         => $branch->{branchcode},
96             categorycode       => $category->{categorycode},
97             itemtype           => '*',
98             maxissueqty        => 0,
99             maxonsiteissueqty  => 0,
100         },
101     });
102     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 0);
103     is_deeply(
104         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ) ],
105         [ 0, 0 ],
106         'CO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
107     );
108     is_deeply(
109         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ) ],
110         [ 0, 0 ],
111         'OSCO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
112     );
113
114     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 1);
115     is_deeply(
116         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ) ],
117         [ 0, 0 ],
118         'CO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
119     );
120     is_deeply(
121         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ) ],
122         [ 0, 0 ],
123         'OSCO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
124     );
125
126     teardown();
127 };
128
129 subtest '1 Issuingrule exist 1 1: issue is allowed' => sub {
130     plan tests => 4;
131     my $issuingrule = $builder->build({
132         source => 'Issuingrule',
133         value => {
134             branchcode         => $branch->{branchcode},
135             categorycode       => $category->{categorycode},
136             itemtype           => '*',
137             maxissueqty        => 1,
138             maxonsiteissueqty  => 1,
139         },
140     });
141     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 0);
142     is(
143         C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ),
144         undef,
145         'CO should be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
146     );
147     is(
148         C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ),
149         undef,
150         'OSCO should be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
151     );
152
153     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 1);
154     is(
155         C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ),
156         undef,
157         'CO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
158     );
159     is(
160         C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ),
161         undef,
162         'OSCO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
163     );
164
165     teardown();
166 };
167
168 subtest '1 Issuingrule exist: 1 CO allowed, 1 OSCO allowed. Do a CO' => sub {
169     plan tests => 5;
170     my $issuingrule = $builder->build({
171         source => 'Issuingrule',
172         value => {
173             branchcode         => $branch->{branchcode},
174             categorycode       => $category->{categorycode},
175             itemtype           => '*',
176             maxissueqty        => 1,
177             maxonsiteissueqty  => 1,
178         },
179     });
180
181     my $issue = C4::Circulation::AddIssue( $patron, $item->{barcode}, dt_from_string() );
182     like( $issue->issue_id, qr|^\d+$|, 'The issue should have been inserted' );
183
184     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 0);
185     is_deeply(
186         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ) ],
187         [ 1, 1 ],
188         'CO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
189     );
190     is(
191         C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ),
192         undef,
193         'OSCO should be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
194     );
195
196     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 1);
197     is_deeply(
198         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ) ],
199         [ 1, 1 ],
200         'CO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
201     );
202     is_deeply(
203         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ) ],
204         [ 1, 1 ],
205         'OSCO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
206     );
207
208     teardown();
209 };
210
211 subtest '1 Issuingrule exist: 1 CO allowed, 1 OSCO allowed, Do a OSCO' => sub {
212     plan tests => 5;
213     my $issuingrule = $builder->build({
214         source => 'Issuingrule',
215         value => {
216             branchcode         => $branch->{branchcode},
217             categorycode       => $category->{categorycode},
218             itemtype           => '*',
219             maxissueqty        => 1,
220             maxonsiteissueqty  => 1,
221         },
222     });
223
224     my $issue = C4::Circulation::AddIssue( $patron, $item->{barcode}, dt_from_string(), undef, undef, undef, { onsite_checkout => 1 } );
225     like( $issue->issue_id, qr|^\d+$|, 'The issue should have been inserted' );
226
227     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 0);
228     is(
229         C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ),
230         undef,
231         'CO should be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
232     );
233     is_deeply(
234         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ) ],
235         [ 1, 1 ],
236         'OSCO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
237     );
238
239     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 1);
240     is_deeply(
241         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ) ],
242         [ 1, 1 ],
243         'CO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
244     );
245     is_deeply(
246         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ) ],
247         [ 1, 1 ],
248         'OSCO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
249     );
250
251     teardown();
252 };
253
254 subtest '1 BranchBorrowerCircRule exist: 1 CO allowed, 1 OSCO allowed' => sub {
255     # Note: the same test coul be done for
256     # DefaultBorrowerCircRule, DefaultBranchCircRule, DefaultBranchItemRule ans DefaultCircRule.pm
257
258     plan tests => 10;
259     my $issuingrule = $builder->build({
260         source => 'BranchBorrowerCircRule',
261         value => {
262             branchcode         => $branch->{branchcode},
263             categorycode       => $category->{categorycode},
264             maxissueqty        => 1,
265             maxonsiteissueqty  => 1,
266         },
267     });
268
269     my $issue = C4::Circulation::AddIssue( $patron, $item->{barcode}, dt_from_string(), undef, undef, undef );
270     like( $issue->issue_id, qr|^\d+$|, 'The issue should have been inserted' );
271
272     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 0);
273     is_deeply(
274         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ) ],
275         [ 1, 1 ],
276         'CO should be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
277     );
278     is(
279         C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ),
280         undef,
281         'OSCO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
282     );
283
284     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 1);
285     is_deeply(
286         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ) ],
287         [ 1, 1 ],
288         'CO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
289     );
290     is_deeply(
291         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ) ],
292         [ 1, 1 ],
293         'OSCO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
294     );
295
296     teardown();
297
298     $issue = C4::Circulation::AddIssue( $patron, $item->{barcode}, dt_from_string(), undef, undef, undef, { onsite_checkout => 1 } );
299     like( $issue->issue_id, qr|^\d+$|, 'The issue should have been inserted' );
300
301     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 0);
302     is(
303         C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ),
304         undef,
305         'CO should be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
306     );
307     is_deeply(
308         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ) ],
309         [ 1, 1 ],
310         'OSCO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 0'
311     );
312
313     t::lib::Mocks::mock_preference('ConsiderOnSiteCheckoutsAsNormalCheckouts', 1);
314     is_deeply(
315         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item ) ],
316         [ 1, 1 ],
317         'CO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
318     );
319     is_deeply(
320         [ C4::Circulation::TooMany( $patron, $biblio->{biblionumber}, $item, { onsite_checkout => 1 } ) ],
321         [ 1, 1 ],
322         'OSCO should not be allowed if ConsiderOnSiteCheckoutsAsNormalCheckouts == 1'
323     );
324
325     teardown();
326 };
327
328 sub teardown {
329     $dbh->do(q|DELETE FROM issues|);
330     $dbh->do(q|DELETE FROM issuingrules|);
331 }