From 5c55521a2b8607a655b3eb421b3f986dd7b90391 Mon Sep 17 00:00:00 2001 From: Alex Sassmannshausen Date: Fri, 11 Mar 2016 15:00:01 +0100 Subject: [PATCH] Bug 6906 - show 'Borrower has previously issued... New feature: provide granular means to configure warnings about items that have been issued to a particular borrower before, according to their loan history. - Global syspref ('CheckPrevIssue'), set to 'hardno' by default, allows users to enable this feature library wide. - Per patron category pref allows libraries to create overrides per category, falling back on the global setting by default. - Per patron pref allows switching the functionality on at the level of patron. Fall-back to category settings by default. * Koha/Patron/CheckPrevIssue.pm: New file * C4/Circulation.pm (CanBookBeIssued): Introduce CheckPrevIssue check. * admin/categories.pl: Pass along checkprevissue. * koha-tmpl/intranet-tmpl/prog/en/modules/admin/categories.tt: Expose CheckPrevIssue per category setting. * koha-tmpl/intranet-tmpl/prog/en/modules/preferences/patrons.pref: Expose CheckPrevIssue syspref. * koha-tmpl/intranet-tmpl/prog/en/modules/members/memberentrygen.tt: Expose per patron CheckPrevIssue preference. * koha-tmpl/intranet-tmpl/prog/en/modules/members/moremember.tt: Expose per patron CheckPrevIssue preference. * koha-tmpl/intranet-tmpl/prog/en/modules/circ/circulation.tt: Add 'CHECKPREVISSUE' confirmation message. * installer/data/mysql/kohastructure.sql: Modify structure of 'categories', 'borrowers'. * installer/data/mysql/sysprefs.sql: Add 'CheckPrevIssue'. * installer/data/mysql/atomicupdate/checkPrevIssue.sql: New file. * t/db_dependent/Patron/CheckPrevIssue.t: New file with unit tests. Test plan: - Apply patch. - Run updatedatabase. - Regenerate Koha Schema files. - Run the unit tests. - Verify 'CheckPrevIssue' is visible in Patrons sysprefs and can be switched to 'hardyes', 'softyes', 'softno' and 'hardno'. + Check out previously issued items to a patron, checking the message appears as expected. - Verify no 'Check previous loans' setting appears on the borrower category pages if the syspref is set to a 'hard' option. - Verify 'Check previous loans' setting appears on the borrower category pages and can be modified per borrower category. + Issue previously issued items to a borrower, checking the message appears as expected (This setting should override the default setting if that is set to a 'soft' option). - Verify no 'Check previous loans' setting appears on the individual borrower pages if the syspref is set to a 'hard' option. - Verify 'Check previous loans' setting appears on individual borrower pages and can be modified. + Issue previously issued items to a borrower, checking the message appears as expected (This setting should override the category setting and the default setting if the latter is set to a 'soft' option). Signed-off-by: Nick Clemens --- C4/Circulation.pm | 10 + Koha/Patron/CheckPrevIssue.pm | 182 +++++++++++ admin/categories.pl | 3 + .../data/mysql/atomicupdate/checkPrevIssue.sql | 11 + installer/data/mysql/kohastructure.sql | 3 + installer/data/mysql/sysprefs.sql | 1 + .../prog/en/modules/admin/categories.tt | 53 +++ .../prog/en/modules/admin/preferences/patrons.pref | 9 + .../prog/en/modules/circ/circulation.tt | 4 + .../prog/en/modules/members/memberentrygen.tt | 21 +- .../prog/en/modules/members/moremember.tt | 11 + t/db_dependent/Patron/CheckPrevIssue.t | 354 +++++++++++++++++++++ 12 files changed, 661 insertions(+), 1 deletion(-) create mode 100644 Koha/Patron/CheckPrevIssue.pm create mode 100644 installer/data/mysql/atomicupdate/checkPrevIssue.sql create mode 100644 t/db_dependent/Patron/CheckPrevIssue.t diff --git a/C4/Circulation.pm b/C4/Circulation.pm index 70ae3fd..8ea651a 100644 --- a/C4/Circulation.pm +++ b/C4/Circulation.pm @@ -50,6 +50,7 @@ use Koha::Calendar; use Koha::Items; use Koha::Patrons; use Koha::Patron::Debarments; +use Koha::Patron::CheckPrevIssue qw(WantsCheckPrevIssue CheckPrevIssue); use Koha::Database; use Koha::Libraries; use Koha::Holds; @@ -909,6 +910,15 @@ sub CanBookBeIssued { } # + # CHECKPREVISSUE: CHECK IF ITEM HAS EVER BEEN LENT TO PATRON + # + my $wantsCheckPrevIssue = WantsCheckPrevIssue( + $borrower, C4::Context->preference("checkPrevIssue") + ); + $needsconfirmation{PREVISSUE} = 1 + if ($wantsCheckPrevIssue and CheckPrevIssue($borrower, $item)); + + # # ITEM CHECKING # if ( $item->{'notforloan'} ) diff --git a/Koha/Patron/CheckPrevIssue.pm b/Koha/Patron/CheckPrevIssue.pm new file mode 100644 index 0000000..6fa11f6 --- /dev/null +++ b/Koha/Patron/CheckPrevIssue.pm @@ -0,0 +1,182 @@ +package Koha::Patron::CheckPrevIssue; + +# This file is part of Koha. +# +# Copyright (C) 2014 PTFS Europe +# +# Koha is free software; you can redistribute it and/or modify it +# under the terms of the GNU General Public License as published by +# the Free Software Foundation; either version 3 of the License, or +# (at your option) any later version. +# +# Koha is distributed in the hope that it will be useful, but +# WITHOUT ANY WARRANTY; without even the implied warranty of +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +# GNU General Public License for more details. +# +# You should have received a copy of the GNU General Public License +# along with Koha; if not, see . + +use Modern::Perl; + +use C4::Context; +use Koha::Patron::Categories; +use Koha::Issues; +use Koha::OldIssues; + +use parent qw( Exporter ); + +our @EXPORT = qw( + WantsCheckPrevIssue + CheckPrevIssue +); + +=head1 NAME + +Koha::Patron::CheckPrevIssue - Manage Previous Issue preferences & searches. + +=head1 SYNOPSIS + +Provide a feature to check whether a patron has previously checked out items +associated with a a biblio. + +=head1 DESCRIPTION + +CheckPrevIssue is a feature that allows administrators of a Koha instance to +enable a warning when items are lent to patrons when they've already borrowed +it in the past. + +An example use case might be a housebound delivery service, where volunteers +pick stock for housebound patrons. The volunteers might not have an +exhaustive list of books borrowed in the past, so they would benefit from +being warned when they are about to check out such a book to that patron. + +The module introduces: + +=over + +=item a master syspref in the Patrons section: + +=over + +=item Do not + +=item Unless overridden, do not + +=item Unless overridden, do + +=item Do + +=back + +=item per patron category switches: + +=over + +=item Inherit from system preferences. + +=item Yes and try to override system preferences. + +=item No and try to override system preferences. + +=back + +=item per patron switches + +=over + +=item Inherit from wider settings. + +=item Yes and try to override settings. + +=item No and try to override settings. + +=back + +=back + +=head1 FUNCTIONS + +=cut + +=head2 WantsCheckPrevIssue + + $wantsCheckPrevIssue = WantsCheckPrevIssue($patron, $syspref); + +Return 1 if Koha needs to perform PrevIssue checking, else 0. + +$PATRON is used to determine patron and patron category checkPrevIssue level +setting. $SYSPREF conteins the system-wide checkPrevIssue level setting. + +=cut + +sub WantsCheckPrevIssue { + my ( $patron, $syspref ) = @_; + + # Simple cases + ## Hard syspref trumps all + return 1 if ($syspref eq 'hardyes'); + return 0 if ($syspref eq 'hardno'); + ## Now, patron pref trumps all + my $checkPrevIssueByBrw = $patron->{checkprevissue}; + return 1 if ($checkPrevIssueByBrw eq 'yes'); + return 0 if ($checkPrevIssueByBrw eq 'no'); + + # More complex: patron inherits -> determine category preference + my $checkPrevIssueByCat = + Koha::Patron::Categories->find($patron->{categorycode}) + ->checkprevissue; + return 1 if ($checkPrevIssueByCat eq 'yes'); + return 0 if ($checkPrevIssueByCat eq 'no'); + + # Finally: category preference is inherit, default to 0 + if ($syspref eq 'softyes') { + return 1; + } else { + return 0; + } +} + +=head2 CheckPrevIssue + + $checkPrevIssue = CheckPrevIssue($patron, $item); + +Return 1 if the bib associated with $ITEM has previously been checked out to +$PATRON, 0 otherwise. + +=cut + +sub CheckPrevIssue { + my ( $patron, $item ) = @_; + + # Find all items for bib and extract item numbers. + my @items = Koha::Items->search({biblionumber => $item->{biblionumber}}); + my @item_nos; + foreach my $item (@items) { + push @item_nos, $item->itemnumber; + } + + # Create (old)issues search criteria + my $criteria = { + borrowernumber => $patron->{borrowernumber}, + itemnumber => \@item_nos, + }; + + # Check current issues table + my $issues = Koha::Issues->search($criteria); + return 1 if $issues->count; # 0 || N + + # Check old issues table + my $old_issues = Koha::OldIssues->search($criteria); + return $old_issues->count; # 0 || N +} + +1; + +__END__ + +=head1 AUTHOR + +Alex Sassmannshausen + +=cut diff --git a/admin/categories.pl b/admin/categories.pl index e439a62..2cbff42 100755 --- a/admin/categories.pl +++ b/admin/categories.pl @@ -90,6 +90,7 @@ elsif ( $op eq 'add_validate' ) { my $overduenoticerequired = $input->param('overduenoticerequired'); my $category_type = $input->param('category_type'); my $BlockExpiredPatronOpacActions = $input->param('BlockExpiredPatronOpacActions'); + my $checkPrevIssue = $input->param('checkprevissue'); my $default_privacy = $input->param('default_privacy'); my @branches = grep { $_ ne q{} } $input->param('branches'); @@ -113,6 +114,7 @@ elsif ( $op eq 'add_validate' ) { $category->overduenoticerequired($overduenoticerequired); $category->category_type($category_type); $category->BlockExpiredPatronOpacActions($BlockExpiredPatronOpacActions); + $category->checkprevissue($checkPrevIssue); $category->default_privacy($default_privacy); eval { $category->store; @@ -138,6 +140,7 @@ elsif ( $op eq 'add_validate' ) { overduenoticerequired => $overduenoticerequired, category_type => $category_type, BlockExpiredPatronOpacActions => $BlockExpiredPatronOpacActions, + checkprevissue => $checkPrevIssue, default_privacy => $default_privacy, }); eval { diff --git a/installer/data/mysql/atomicupdate/checkPrevIssue.sql b/installer/data/mysql/atomicupdate/checkPrevIssue.sql new file mode 100644 index 0000000..17763d6 --- /dev/null +++ b/installer/data/mysql/atomicupdate/checkPrevIssue.sql @@ -0,0 +1,11 @@ +INSERT INTO systempreferences (variable,value,options,explanation,type) +VALUES('CheckPrevIssue','hardno','hardyes|softyes|softno|hardno','By default, for every item issued, should we warn if the patron has borrowed that item in the past?','Choice'); + +ALTER TABLE categories +ADD (`checkprevissue` varchar(7) NOT NULL default 'inherit'); + +ALTER TABLE borrowers +ADD (`checkprevissue` varchar(7) NOT NULL default 'inherit'); + +ALTER TABLE deletedborrowers +ADD (`checkprevissue` varchar(7) NOT NULL default 'inherit'); diff --git a/installer/data/mysql/kohastructure.sql b/installer/data/mysql/kohastructure.sql index e6e3142..8a571c7 100644 --- a/installer/data/mysql/kohastructure.sql +++ b/installer/data/mysql/kohastructure.sql @@ -266,6 +266,7 @@ CREATE TABLE `borrowers` ( -- this table includes information about your patrons `sms_provider_id` int(11) DEFAULT NULL, -- the provider of the mobile phone number defined in smsalertnumber `privacy` integer(11) DEFAULT '1' NOT NULL, -- patron/borrower's privacy settings related to their reading history `privacy_guarantor_checkouts` tinyint(1) NOT NULL DEFAULT '0', -- controls if relatives can see this patron's checkouts + `checkprevissue` varchar(7) NOT NULL default 'inherit', -- produce a warning for this patron if this item has previously been issued to this patron if 'yes', not if 'no', defer to category setting if 'inherit'. UNIQUE KEY `cardnumber` (`cardnumber`), PRIMARY KEY `borrowernumber` (`borrowernumber`), KEY `categorycode` (`categorycode`), @@ -505,6 +506,7 @@ CREATE TABLE `categories` ( -- this table shows information related to Koha patr `category_type` varchar(1) NOT NULL default 'A', -- type of Koha patron (Adult, Child, Professional, Organizational, Statistical, Staff) `BlockExpiredPatronOpacActions` tinyint(1) NOT NULL default '-1', -- wheither or not a patron of this category can renew books or place holds once their card has expired. 0 means they can, 1 means they cannot, -1 means use syspref BlockExpiredPatronOpacActions `default_privacy` ENUM( 'default', 'never', 'forever' ) NOT NULL DEFAULT 'default', -- Default privacy setting for this patron category + `checkprevissue` varchar(7) NOT NULL default 'inherit', -- produce a warning for this patron category if this item has previously been issued to this patron if 'yes', not if 'no', defer to syspref setting if 'inherit'. PRIMARY KEY (`categorycode`), UNIQUE KEY `categorycode` (`categorycode`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_unicode_ci; @@ -918,6 +920,7 @@ CREATE TABLE `deletedborrowers` ( -- stores data related to the patrons/borrower `sms_provider_id` int(11) DEFAULT NULL, -- the provider of the mobile phone number defined in smsalertnumber `privacy` integer(11) DEFAULT '1' NOT NULL, -- patron/borrower's privacy settings related to their reading history KEY `borrowernumber` (`borrowernumber`), `privacy_guarantor_checkouts` tinyint(1) NOT NULL DEFAULT '0', -- controls if relatives can see this patron's checkouts + `checkprevissue` varchar(7) NOT NULL default 'inherit', -- produce a warning for this patron if this item has previously been issued to this patron if 'yes', not if 'no', defer to category setting if 'inherit'. KEY borrowernumber (borrowernumber), KEY `cardnumber` (`cardnumber`), KEY `sms_provider_id` (`sms_provider_id`) diff --git a/installer/data/mysql/sysprefs.sql b/installer/data/mysql/sysprefs.sql index ef4c3f0..7956ec7 100644 --- a/installer/data/mysql/sysprefs.sql +++ b/installer/data/mysql/sysprefs.sql @@ -90,6 +90,7 @@ INSERT INTO systempreferences ( `variable`, `value`, `options`, `explanation`, ` ('CatalogModuleRelink','0',NULL,'If OFF the linker will never replace the authids that are set in the cataloging module.','YesNo'), ('CataloguingLog','1',NULL,'If ON, log edit/create/delete actions on bibliographic data. WARNING: this feature is very resource consuming.','YesNo'), ('checkdigit','none','none|katipo','If ON, enable checks on patron cardnumber: none or \"Katipo\" style checks','Choice'), +('CheckPrevIssue','hardno','hardyes|softyes|softno|hardno','By default, for every item issued, should we warn if the patron has borrowed that item in the past?','Choice'), ('CircAutocompl','1',NULL,'If ON, autocompletion is enabled for the Circulation input','YesNo'), ('CircAutoPrintQuickSlip','qslip',NULL,'Choose what should happen when an empty barcode field is submitted in circulation: Display a print quick slip window, Display a print slip window or Clear the screen.','Choice'), ('CircControl','ItemHomeLibrary','PickupLibrary|PatronLibrary|ItemHomeLibrary','Specify the agency that controls the circulation and fines policy','Choice'), diff --git a/koha-tmpl/intranet-tmpl/prog/en/modules/admin/categories.tt b/koha-tmpl/intranet-tmpl/prog/en/modules/admin/categories.tt index 1c2bf23..811c78a 100644 --- a/koha-tmpl/intranet-tmpl/prog/en/modules/admin/categories.tt +++ b/koha-tmpl/intranet-tmpl/prog/en/modules/admin/categories.tt @@ -276,6 +276,28 @@ Choose whether patrons of this category be blocked from public catalog actions such as renewing and placing holds when their cards have expired. + [% IF ( Koha.Preference('CheckPrevIssue') == 'softyes' || Koha.Preference('CheckPrevIssue') == 'softno' ) %] +
  • + + + Choose whether patrons of this category by default are reminded if they try to borrow an item they borrowed before. + +
  • + [% END %]
  • + [% IF ( checkprevissue == 'yes' ) %] + + + + [% ELSIF ( checkprevissue == 'no' ) %] + + + + [% ELSE %] + + + + [% END %] + +
  • + [% END %] + [% UNLESS nodateenrolled && noopacnote && noborrowernotes %]
    diff --git a/koha-tmpl/intranet-tmpl/prog/en/modules/members/moremember.tt b/koha-tmpl/intranet-tmpl/prog/en/modules/members/moremember.tt index 6a4add0..3f0b930 100644 --- a/koha-tmpl/intranet-tmpl/prog/en/modules/members/moremember.tt +++ b/koha-tmpl/intranet-tmpl/prog/en/modules/members/moremember.tt @@ -400,6 +400,17 @@ function validate1(date) {
  • Activate sync: No
  • [% END %] [% END %] + [% IF ( Koha.Preference('CheckPrevIssue') == 'softyes' || Koha.Preference('CheckPrevIssue') == 'softno' ) %] +
  • Check previous loans: + [% IF ( checkprevissue == 'yes' ) %] + Yes + [% ELSIF ( checkprevissue == 'no' ) %] + No + [% ELSE %] + Inherited + [% END %] +
  • + [% END %] diff --git a/t/db_dependent/Patron/CheckPrevIssue.t b/t/db_dependent/Patron/CheckPrevIssue.t new file mode 100644 index 0000000..32660c8 --- /dev/null +++ b/t/db_dependent/Patron/CheckPrevIssue.t @@ -0,0 +1,354 @@ +#!/usr/bin/perl +use Modern::Perl; + +use C4::Members; +use C4::Circulation; +use Koha::Patron::Categories; +use Koha::Patron::Category; +use Koha::Database; +use Koha::Patrons; +use Koha::Patron; +use Koha::Items; +use Koha::Item; + +use Test::More tests => 55; + +use_ok('Koha::Patron::CheckPrevIssue'); + +use Koha::Patron::CheckPrevIssue qw( WantsCheckPrevIssue CheckPrevIssue ); + +use t::lib::TestBuilder; + +my $schema = Koha::Database->new->schema; +$schema->storage->txn_begin; + +my $builder = t::lib::TestBuilder->new; +my $yesCatCode = $builder->build({ + source => 'Category', + value => { + categorycode => 'yesCat', + checkprevissue => 'yes', + }, +}); + +my $noCatCode = $builder->build({ + source => 'Category', + value => { + categorycode => 'noCat', + checkprevissue => 'no', + }, +}); + +my $inheritCatCode = $builder->build({ + source => 'Category', + value => { + categorycode => 'inheritCat', + checkprevissue => 'inherit', + }, +}); + +# WantsCheckPrevIssue + +# We expect the following result matrix: +# +# (1/0 indicates the return value of WantsCheckPrevIssue; i.e. 1 says we +# should check whether the item was previously issued) +# +# | System Preference | hardyes | softyes | softno | hardno | +# |-------------------+-----------------------------------+-----------------------------------+-----------------------------------+-----------------------------------| +# | Category Setting | yes | no | inherit | yes | no | inherit | yes | no | inherit | yes | no | inherit | +# |-------------------+-----------+-----------+-----------+-----------+-----------+-----------+-----------+-----------+-----------+-----------+-----------+-----------| +# | Patron Setting | y | n | i | y | n | i | y | n | i | y | n | i | y | n | i | y | n | i | y | n | i | y | n | i | y | n | i | y | n | i | y | n | i | y | n | i | +# |-------------------+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+---+ +# | Expected Result | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 1 | 0 | 1 | 1 | 0 | 0 | 1 | 0 | 1 | 1 | 0 | 1 | 1 | 0 | 0 | 1 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | 0 | + +my $mappings = [ + { + syspref => 'hardyes', + categories => [ + { + setting => 'yes', + borrowers => [ + {setting => 'yes', result => 1}, + {setting => 'no', result => 1}, + {setting => 'inherit', result => 1}, + ], + }, + { + setting => 'no', + borrowers => [ + {setting => 'yes', result => 1}, + {setting => 'no', result => 1}, + {setting => 'inherit', result => 1}, + ], + }, + { + setting => 'inherit', + borrowers => [ + {setting => 'yes', result => 1}, + {setting => 'no', result => 1}, + {setting => 'inherit', result => 1}, + ], + }, + ], + }, + { + syspref => 'softyes', + categories => [ + { + setting => 'yes', + borrowers => [ + {setting => 'yes', result => 1}, + {setting => 'no', result => 0}, + {setting => 'inherit', result => 1}, + ], + }, + { + setting => 'no', + borrowers => [ + {setting => 'yes', result => 1}, + {setting => 'no', result => 0}, + {setting => 'inherit', result => 0}, + ], + }, + { + setting => 'inherit', + borrowers => [ + {setting => 'yes', result => 1}, + {setting => 'no', result => 0}, + {setting => 'inherit', result => 1}, + ], + }, + ], + }, + { + syspref => 'softno', + categories => [ + { + setting => 'yes', + borrowers => [ + {setting => 'yes', result => 1}, + {setting => 'no', result => 0}, + {setting => 'inherit', result => 1}, + ], + }, + { + setting => 'no', + borrowers => [ + {setting => 'yes', result => 1}, + {setting => 'no', result => 0}, + {setting => 'inherit', result => 0}, + ], + }, + { + setting => 'inherit', + borrowers => [ + {setting => 'yes', result => 1}, + {setting => 'no', result => 0}, + {setting => 'inherit', result => 0}, + ], + }, + ], + }, + { + syspref => 'hardno', + categories => [ + { + setting => 'yes', + borrowers => [ + {setting => 'yes', result => 0}, + {setting => 'no', result => 0}, + {setting => 'inherit', result => 0}, + ], + }, + { + setting => 'no', + borrowers => [ + {setting => 'yes', result => 0}, + {setting => 'no', result => 0}, + {setting => 'inherit', result => 0}, + ], + }, + { + setting => 'inherit', + borrowers => [ + {setting => 'yes', result => 0}, + {setting => 'no', result => 0}, + {setting => 'inherit', result => 0}, + ], + }, + ], + }, +]; + +map { + my $syspref = $_->{syspref}; + map { + my $code = $_->{setting} . 'Cat'; + map { + my $brw = { + checkprevissue => $_->{setting}, + categorycode => $code, + }; + is( + WantsCheckPrevIssue($brw, $syspref), $_->{result}, + "Predicate with syspref " . $syspref . ", cat " . $code + . ", brw " . $_->{setting} + ); + } @{$_->{borrowers}}; + } @{$_->{categories}}; +} @{$mappings}; + +# CheckPrevIssue + +# We want to test: +# - DESCRIPTION [RETURNVALUE (0/1)] +## PreIssue (sanity checks) +# - Item, patron [0] +# - Diff item, same bib, same patron [0] +# - Diff item, diff bib, same patron [0] +# - Same item, diff patron [0] +# - Diff item, same bib, diff patron [0] +# - Diff item, diff bib, diff patron [0] +## PostIssue +# - Same item, same patron [1] +# - Diff item, same bib, same patron [1] +# - Diff item, diff bib, same patron [0] +# - Same item, diff patron [0] +# - Diff item, same bib, diff patron [0] +# - Diff item, diff bib, diff patron [0] +## PostReturn +# - Same item, same patron [1] +# - Diff item, same bib, same patron [1] +# - Diff item, diff bib, same patron [0] +# - Same item, diff patron [0] +# - Diff item, same bib, diff patron [0] +# - Diff item, diff bib, diff patron [0] + +# Requirements: +# $patron, $different_patron, $items (same bib number), $different_item +my $patron = $builder->build({source => 'Borrower'}); +my $patron_d = $builder->build({source => 'Borrower'}); +my $item_1 = $builder->build({source => 'Item'}); +my $item_2 = $builder->build({ + source => 'Item', + value => { biblionumber => $item_1->{biblionumber} }, +}); +my $item_d = $builder->build({source => 'Item'}); + +## Testing Sub +sub test_it { + my ($mapping, $stage) = @_; + map { + is(CheckPrevIssue( + $_->{patron}, $_->{item}), $_->{result}, $stage . ": " . $_->{msg} + ); + } @{$mapping}; +}; + +## Initial Mappings +my $cpvmappings = [ + { + msg => "Item, patron [0]", + item => $item_1, + patron => $patron, + result => 0, + }, + { + msg => "Diff item, same bib, same patron [0]", + item => $item_2, + patron => $patron, + result => 0, + }, + { + msg => "Diff item, diff bib, same patron [0]", + item => $item_d, + patron => $patron, + result => 0, + }, + { + msg => "Same item, diff patron [0]", + item => $item_1, + patron => $patron_d, + result => 0, + }, + { + msg => "Diff item, same bib, diff patron [0]", + item => $item_2, + patron => $patron_d, + result => 0, + }, + { + msg => "Diff item, diff bib, diff patron [0]", + item => $item_d, + patron => $patron_d, + result => 0, + }, +]; + +test_it($cpvmappings, "PreIssue"); + +# Issue item_1 to $patron: +my @USERENV = ( + $patron->{borrowernumber}, 'test', 'MASTERTEST', 'firstname', 'CPL', + 'CPL', 'email@example.org' +); +C4::Context->_new_userenv('DUMMY_SESSION_ID'); +C4::Context->set_userenv(@USERENV); +BAIL_OUT("No userenv") unless C4::Context->userenv; + +my $borrower = GetMember(%{{borrowernumber => $patron->{borrowernumber}}}); + +BAIL_OUT("Issue failed") unless AddIssue($borrower, $item_1->{barcode}); + +# Then test: +my $cpvPmappings = [ + { + msg => "Same item, same patron [1]", + item => $item_1, + patron => $patron, + result => 1, + }, + { + msg => "Diff item, same bib, same patron [1]", + item => $item_2, + patron => $patron, + result => 1, + }, + { + msg => "Diff item, diff bib, same patron [0]", + item => $item_d, + patron => $patron, + result => 0, + }, + { + msg => "Same item, diff patron [0]", + item => $item_1, + patron => $patron_d, + result => 0, + }, + { + msg => "Diff item, same bib, diff patron [0]", + item => $item_2, + patron => $patron_d, + result => 0, + }, + { + msg => "Diff item, diff bib, diff patron [0]", + item => $item_d, + patron => $patron_d, + result => 0, + }, +]; + +test_it($cpvPmappings, "PostIssue"); + +# Return item_1 from patron: +BAIL_OUT("Return Failed") unless AddReturn($item_1->{barcode}, $patron->{branchcode}); + +# Then: +test_it($cpvPmappings, "PostReturn"); + +$schema->storage->txn_rollback; + +1; -- 2.1.4