From 304383eb1faa145cea8526f0325cb482b7fa9d08 Mon Sep 17 00:00:00 2001 From: Alex Buckley Date: Thu, 20 Jun 2019 23:24:16 +0000 Subject: [PATCH] Bug 23172: When returning items check issuingrules When iterating over every reserve on a biblio when it is being returned retrieve the issuingrule reserveallowed and holds_per_record values for the reserves requester borrower category and returned item type. If the issuingrule defines that reservesallowed or holds_per_record is 0 then skip allocating that item to the current bib-level reserve. Test plan: 1. Find/make a biblio record with two items: one with item type of 'BK' (book) and the other with the itemtype of 'CR' (Continuing Resource) 2. In Administration > Circulation and fine rules define 2 new rules: Patron category: 'B' (Board)/ item type: 'BK'/ holds allowed (total): 0/ hold allowed (daily): 0 / holds per record: 0 Patron category: 'P' (Patron)/Item type: 'BK' / holds allowed (total): 1/ holds allowed (daily): 1 / holds per record 1 3. On the biblio record place a biblio-level hold for patron A (who has patron category of 'B') and patron B (who has patron category of 'P') 4. Return the 'BK' item (item with item type of 'BK') 5. Notice a popup asking you to confirm the hold by patron A (even though patrons of category 'B' cannot hold items of item type 'BK') 6. Apply patch and restart memcached and plack 7. Remove both holds on biblio 8. Repeat steps 3-5 but notice instead of a popup for patron A appearing, a popup asking you to confirm patron B appears i.e. patron A's bib-level hold is skipped as the issuingrules has been checked when the item was returned and it has been found that they cannot reserve an item with that specific itemtype Sponsored-By: Brimbank Library, Australia --- C4/Reserves.pm | 6 +++++- Koha/Hold.pm | 40 ++++++++++++++++++++++++++++++++++++++++ 2 files changed, 45 insertions(+), 1 deletion(-) diff --git a/C4/Reserves.pm b/C4/Reserves.pm index 097a5c0..a8ab4db 100644 --- a/C4/Reserves.pm +++ b/C4/Reserves.pm @@ -741,7 +741,6 @@ sub CheckReserves { return if ( $damaged && !C4::Context->preference('AllowHoldsOnDamagedItems') ); return unless $itemnumber; # bail if we got nothing. - # if item is not for loan it cannot be reserved either..... # except where items.notforloan < 0 : This indicates the item is holdable. return if ( $notforloan_per_item > 0 ) or $notforloan_per_itemtype; @@ -761,6 +760,11 @@ sub CheckReserves { my $priority = 10000000; foreach my $res (@reserves) { + + #Before allocating to bib-level hold check if reserve respects hold rule, i.e. can patron category/item type combination allow reserves + my $checkreserve = Koha::Hold->check_if_existing_hold_matches_issuingrules( $res->{'borrowernumber'}, $itemnumber ); + next unless ($checkreserve eq 'OK'); + if ( $res->{'itemnumber'} == $itemnumber && $res->{'priority'} == 0) { if ($res->{'found'} eq 'W') { return ( "Waiting", $res, \@reserves ); # Found it, it is waiting diff --git a/Koha/Hold.pm b/Koha/Hold.pm index bfd3434..6fe8462 100644 --- a/Koha/Hold.pm +++ b/Koha/Hold.pm @@ -337,6 +337,46 @@ sub is_suspended { return $self->suspend(); } +=head3 check_if_existing_hold_matches_issuingrules + +my $checkreserve = Koha::Hold->check_if_existing_hold_matches_issuingrules($res->{'borrowernumber'}, $itemnumber ); + +Upon checking in an item of a bibliographic record with a biblio-level hold on it, check if a bib-level hold can be allocated to a patron based on the current values in the issuingrules table + +=cut + +sub check_if_existing_hold_matches_issuingrules { + my ( $self, $borrowernumber, $itemnumber ) = @_; + + #Get patron and item objects + my $patron = Koha::Patrons->find( $borrowernumber ); + my $item = Koha::Items->find( $itemnumber ); + $item = $item->unblessed(); + + #Get branchcode + my $branchcode; + my $controlbranch = C4::Context->preference('ReservesControlBranch'); + + if ( $controlbranch eq "ItemHomeLibrary" ) { + $branchcode = $item->{homebranch}; + } + elsif ( $controlbranch eq "PatronLibrary" ) { + $branchcode = $patron->{branchcode}; + } + + my $issuingrule = Koha::IssuingRules->get_effective_issuing_rule({ + branchcode => $branchcode, + categorycode => $patron->categorycode, + itemtype => $item->{itype}, + }); + + #Check if the patron catgeory/item type combination is valid + if ( ($issuingrule->reservesallowed || $issuingrule->holds_per_record) == 0 ) { + return 'InvalidHold'; + } else { + return 'OK'; + } +} =head3 cancel -- 2.1.4