Checkout Fills Related Hold modifications
authorThomas Berezansky <tsbere@mvlc.org>
Mon, 25 Jul 2011 19:26:08 +0000 (15:26 -0400)
committerBill Erickson <berick@esilibrary.com>
Mon, 25 Jul 2011 21:25:00 +0000 (17:25 -0400)
Two changes:

1 - Check hold_copy_map for related holds

This removes the "Title or Volume hold only" restriction, allowing any hold type to fill.
This check happens first whenever the option is enabled.

2 - Add new option for *only* checking hold_copy_map.

This allows for non-holdable copies to not fill Title or Volume holds on checkout.

Signed-off-by: Thomas Berezansky <tsbere@mvlc.org>
Signed-off-by: Bill Erickson <berick@esilibrary.com>
Open-ILS/src/perlmods/lib/OpenILS/Application/Circ/Circulate.pm
Open-ILS/src/sql/Pg/950.data.seed-values.sql

index 793b7fd..d61f75e 100644 (file)
@@ -1681,8 +1681,17 @@ sub handle_checkout_holds {
 # ------------------------------------------------------------------------------
 # If the circ.checkout_fill_related_hold setting is turned on and no hold for
 # the patron directly targets the checked out item, see if there is another hold 
-# (with hold_type T or V) for the patron that could be fulfilled by the checked 
-# out item.  Fulfill the oldest hold and only fulfill 1 of them.
+# for the patron that could be fulfilled by the checked out item.  Fulfill the
+# oldest hold and only fulfill 1 of them.
+# 
+# For "another hold":
+#
+# First, check for one that the copy matches via hold_copy_map, ensuring that
+# *any* hold type that this copy could fill may end up filled.
+#
+# Then, if circ.checkout_fill_related_hold_exact_match_only is not enabled, look
+# for a Title (T) or Volume (V) hold that matches the item. This allows items
+# that are non-requestable to count as capturing those hold types.
 # ------------------------------------------------------------------------------
 sub find_related_user_hold {
     my($self, $copy, $patron) = @_;
@@ -1698,6 +1707,40 @@ sub find_related_user_hold {
         select => {ahr => ['id']}, 
         from => {
             ahr => {
+                ahcm => {
+                    field => 'hold',
+                    fkey => 'id'
+                }
+            }
+        }, 
+        where => {
+            '+ahr' => {
+                usr => $patron->id,
+                fulfillment_time => undef,
+                cancel_time => undef,
+               '-or' => [
+                    {expire_time => undef},
+                    {expire_time => {'>' => 'now'}}
+                ]
+            },
+            '+ahcm' => {
+                target_copy => $self->copy->id
+            },
+        },
+        order_by => {ahr => {request_time => {direction => 'asc'}}},
+        limit => 1
+    };
+
+    my $hold_info = $e->json_query($args)->[0];
+    return $e->retrieve_action_hold_request($hold_info->{id}) if $hold_info;
+    return undef if $U->ou_ancestor_setting_value(        
+        $self->circ_lib, 'circ.checkout_fills_related_hold_exact_match_only', $e);
+
+    # find the oldest unfulfilled hold that has not yet hit the holds shelf.
+    $args = {
+        select => {ahr => ['id']}, 
+        from => {
+            ahr => {
                 acp => {
                     field => 'id', 
                     fkey => 'current_copy',
@@ -1740,7 +1783,7 @@ sub find_related_user_hold {
         limit => 1
     };
 
-    my $hold_info = $e->json_query($args)->[0];
+    $hold_info = $e->json_query($args)->[0];
     return $e->retrieve_action_hold_request($hold_info->{id}) if $hold_info;
     return undef;
 }
index cd16dde..55bcc41 100644 (file)
@@ -2592,6 +2592,11 @@ INSERT into config.org_unit_setting_type
     oils_i18n_gettext('circ.checkout_fills_related_hold', 'When a patron checks out an item and they have no holds that directly target the item, the system will attempt to find a hold for the patron that could be fulfilled by the checked out item and fulfills it', 'coust', 'description'),
     'bool'),
 
+( 'circ.checkout_fills_related_hold_exact_match_only',
+    oils_i18n_gettext('circ.checkout_fills_related_hold_exact_match_only', 'Checkout Fills Related Hold On Valid Copy Only', 'coust', 'label'),
+    oils_i18n_gettext('circ.checkout_fills_related_hold_exact_match_only', 'When filling related holds on checkout only match on items that are valid for opportunistic capture for the hold. Without this set a Title or Volume hold could match when the item is not holdable. With this set only holdable items will match.', 'coust', 'description'),
+    'bool'),
+
 ( 'circ.selfcheck.auto_override_checkout_events',
     oils_i18n_gettext('circ.selfcheck.auto_override_checkout_events', 'Selfcheck override events list', 'coust', 'label'),
     oils_i18n_gettext('circ.selfcheck.auto_override_checkout_events', 'List of checkout/renewal events that the selfcheck interface should automatically override instead instead of alerting and stopping the transaction', 'coust', 'description'),