From 961434b2aec9a6d56607434ebc173e903e3e0397 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Bj=C3=B6rn=20Nyl=C3=A9n?= Date: Fri, 3 Dec 2021 08:50:33 +0100 Subject: [PATCH 1/4] Bug 27208: Add a user specified delay before sending pickup notices. This bug adds the ability to delay sending a notice until a set timestamp. It also adds a user selectable time on the returns page to delay sending of the pickup notice. The notice delay will also be visible in the patron notice log. To test: 1. Apply patch and run updatedatabase.pl to add new column to message_queue. 2. Check in an item with a hold to produce a pickup notice. 3. Select a time for pickup notice delay. Note the warning about the delay. 4. Check in another item with hold to produce a pickup notice. 5. Check the patron notice logs, the one with a delay should read "pending, delayed until ...". 6. Run process_message_queue.pl before and after the selected time above. The delayed message should not be sent until after the set time. --- C4/Letters.pm | 8 +-- C4/Reserves.pm | 12 +++-- circ/returns.pl | 8 ++- .../prog/en/includes/calendar.inc | 49 +++++++++++++++++++ .../prog/en/modules/circ/returns.tt | 30 +++++++++++- .../prog/en/modules/members/notices.tt | 2 +- 6 files changed, 97 insertions(+), 12 deletions(-) diff --git a/C4/Letters.pm b/C4/Letters.pm index c36553ac9a..5a2420652d 100644 --- a/C4/Letters.pm +++ b/C4/Letters.pm @@ -963,9 +963,9 @@ sub EnqueueLetter { my $dbh = C4::Context->dbh(); my $statement = << 'ENDSQL'; INSERT INTO message_queue -( borrowernumber, subject, content, metadata, letter_code, message_transport_type, status, time_queued, to_address, from_address, reply_address, content_type, failure_code ) +( borrowernumber, subject, content, metadata, letter_code, message_transport_type, status, time_queued, to_address, from_address, reply_address, content_type, failure_code, delay_until ) VALUES -( ?, ?, ?, ?, ?, ?, ?, CAST(NOW() AS DATETIME), ?, ?, ?, ?, ? ) +( ?, ?, ?, ?, ?, ?, ?, CAST(NOW() AS DATETIME), ?, ?, ?, ?, ?, ?) ENDSQL my $sth = $dbh->prepare($statement); @@ -982,6 +982,7 @@ ENDSQL $params->{'reply_address'}, # reply_address $params->{'letter'}->{'content-type'}, # content_type $params->{'failure_code'} || '', # failure_code + $params->{'delay_until'} || undef, # delay_until ); return $dbh->last_insert_id(undef,undef,'message_queue', undef); } @@ -1124,7 +1125,7 @@ sub GetQueuedMessages { my $dbh = C4::Context->dbh(); my $statement = << 'ENDSQL'; -SELECT message_id, borrowernumber, subject, content, message_transport_type, status, time_queued, updated_on, failure_code +SELECT message_id, borrowernumber, subject, content, message_transport_type, status, time_queued, updated_on, failure_code, delay_until FROM message_queue ENDSQL @@ -1292,6 +1293,7 @@ sub _get_unsent_messages { FROM message_queue mq LEFT JOIN borrowers b ON b.borrowernumber = mq.borrowernumber WHERE status = ? + AND ( delay_until < CURRENT_TIMESTAMP OR delay_until IS NULL) }; my @query_params = ('pending'); diff --git a/C4/Reserves.pm b/C4/Reserves.pm index a42168bc72..32760b0301 100644 --- a/C4/Reserves.pm +++ b/C4/Reserves.pm @@ -1173,7 +1173,7 @@ sub ModReserveStatus { =head2 ModReserveAffect - &ModReserveAffect($itemnumber,$borrowernumber,$diffBranchSend,$reserve_id, $desk_id); + &ModReserveAffect($itemnumber,$borrowernumber,$diffBranchSend,$reserve_id, $desk_id, $delay_notice_until); This function affect an item and a status for a given reserve, either fetched directly by record_id, or by borrowernumber and itemnumber or biblionumber. If only biblionumber @@ -1189,7 +1189,8 @@ This function also removes any entry of the hold in holds queue table. =cut sub ModReserveAffect { - my ( $itemnumber, $borrowernumber, $transferToDo, $reserve_id, $desk_id ) = @_; + my ( $itemnumber, $borrowernumber, $transferToDo, $reserve_id, $desk_id, $delay_notice_until) = @_; + my $dbh = C4::Context->dbh; # we want to attach $itemnumber to $borrowernumber, find the biblionumber @@ -1223,7 +1224,7 @@ sub ModReserveAffect { $hold->set_processing(); } else { $hold->set_waiting($desk_id); - _koha_notify_reserve( $hold->reserve_id ) unless $already_on_shelf; + _koha_notify_reserve( $hold->reserve_id , $delay_notice_until ) unless $already_on_shelf; # Complete transfer if one exists my $transfer = $hold->item->get_transfer; $transfer->receive if $transfer; @@ -1818,7 +1819,7 @@ sub _Findgroupreserve { =head2 _koha_notify_reserve - _koha_notify_reserve( $hold->reserve_id ); + _koha_notify_reserve( $hold->reserve_id, $delay_until ); Sends a notification to the patron that their hold has been filled (through ModReserveAffect, _not_ ModReserveFill) @@ -1845,7 +1846,7 @@ The following tables are availalbe witin the notice: =cut sub _koha_notify_reserve { - my $reserve_id = shift; + my ($reserve_id, $delay_until )= @_; my $hold = Koha::Holds->find($reserve_id); my $borrowernumber = $hold->borrowernumber; @@ -1894,6 +1895,7 @@ sub _koha_notify_reserve { borrowernumber => $borrowernumber, from_address => $admin_email_address, message_transport_type => $mtt, + delay_until => $delay_until, } ); }; diff --git a/circ/returns.pl b/circ/returns.pl index 8ab9986d91..53f0a75c9c 100755 --- a/circ/returns.pl +++ b/circ/returns.pl @@ -86,6 +86,9 @@ my $userenv = C4::Context->userenv; my $userenv_branch = $userenv->{'branch'} // ''; my $forgivemanualholdsexpire = $query->param('forgivemanualholdsexpire'); +my $delay_notice_until = $query->param('delay_notice_until') || ''; +my $delay_notice_until_dt = eval { dt_from_string( $delay_notice_until ) } if $delay_notice_until; + my $overduecharges = (C4::Context->preference('finesMode') && C4::Context->preference('finesMode') eq 'production'); # Set up the item stack .... @@ -150,7 +153,7 @@ if ( $query->param('reserve_id') ) { my $diffBranchSend = ($userenv_branch ne $diffBranchReturned) ? $diffBranchReturned : undef; # diffBranchSend tells ModReserveAffect whether document is expected in this library or not, # i.e., whether to apply waiting status - ModReserveAffect( $itemnumber, $borrowernumber, $diffBranchSend, $reserve_id, $desk_id ); + ModReserveAffect( $itemnumber, $borrowernumber, $diffBranchSend, $reserve_id, $desk_id, $delay_notice_until_dt ); } # check if we have other reserves for this document, if we have a return send the message of transfer my ( $messages, $nextreservinfo ) = GetOtherReserves($itemnumber); @@ -434,7 +437,7 @@ if ( $messages->{'ResFound'}) { my $biblio = $item->biblio; my $diffBranchSend = !$branchCheck ? $reserve->{branchcode} : undef; - ModReserveAffect( $reserve->{itemnumber}, $reserve->{borrowernumber}, $diffBranchSend, $reserve->{reserve_id}, $desk_id ); + ModReserveAffect( $reserve->{itemnumber}, $reserve->{borrowernumber}, $diffBranchSend, $reserve->{reserve_id}, $desk_id, $delay_notice_until_dt ); my ( $messages, $nextreservinfo ) = GetOtherReserves($reserve->{itemnumber}); $template->param( @@ -641,6 +644,7 @@ $template->param( forgivemanualholdsexpire => $forgivemanualholdsexpire, overduecharges => $overduecharges, AudioAlerts => C4::Context->preference("AudioAlerts"), + delay_notice_until => $delay_notice_until, ); if ( $barcode ) { diff --git a/koha-tmpl/intranet-tmpl/prog/en/includes/calendar.inc b/koha-tmpl/intranet-tmpl/prog/en/includes/calendar.inc index 2805870d10..8e06466eed 100644 --- a/koha-tmpl/intranet-tmpl/prog/en/includes/calendar.inc +++ b/koha-tmpl/intranet-tmpl/prog/en/includes/calendar.inc @@ -155,6 +155,55 @@ options['enableTime'] = true; options['dateFormat'] = flatpickr_dateformat_string + " " + flatpickr_timeformat_string; } + if ( $(this).data('flatpickr-futuredatetime') === true ) { + let original_date = $(this).val(); + if ( original_date ) { + original_date = DateTime_from_syspref( original_date ).getTime(); + let now = new Date().getTime(); + + options['enable'] = [function(date){ + date = date.getTime(); + if ( date == original_date ) return true; + if ( date >= now) return true; + }]; + } + else { + options['minDate'] = new Date(); + options['defaultHour'] = new Date().getHours(); + options['defaultMinute'] = new Date().getMinutes(); + + } + options['plugins'] = [ ShortcutButtonsPlugin({ + button: [ + { + label: __("1h") + }, + { + label: __("2h") + }, + { + label: __("4h") + } + ], + label: __("or"), + onClick: (index, fp) => { + let date; + let hh = 23, mm = 59; + switch (index) { + case 0: + date = new Date(Date.now() + 1 * 60 * 60 * 1000); + break; + case 1: + date = new Date(Date.now() + 2 * 60 * 60 * 1000); + break; + case 2: + date = new Date(Date.now() + 4 * 60 * 60 * 1000); + break; + } + fp.setDate(date, true); + } + })]; + } let fp = $(this).flatpickr(options); if ( refresh_max_date ) { diff --git a/koha-tmpl/intranet-tmpl/prog/en/modules/circ/returns.tt b/koha-tmpl/intranet-tmpl/prog/en/modules/circ/returns.tt index c119c2708e..038f054789 100644 --- a/koha-tmpl/intranet-tmpl/prog/en/modules/circ/returns.tt +++ b/koha-tmpl/intranet-tmpl/prog/en/modules/circ/returns.tt @@ -367,6 +367,7 @@
+ [% FOREACH inputloo IN inputloop %] @@ -432,6 +433,7 @@ + [% FOREACH inputloo IN inputloop %] @@ -538,6 +540,7 @@ + [% INCLUDE all_checkin_messages %] @@ -609,6 +612,7 @@ [% END %] + @@ -708,6 +712,7 @@ + [% INCLUDE all_checkin_messages %] @@ -800,6 +805,13 @@ [% END %]

Saved check-in date: [% return_date_override | html %]

+ [% IF ( delay_notice_until ) %] +
+ [% ELSE %] +
@@ -851,7 +863,10 @@ [% END %] - +
+
Delay pickup notice until:
+ +
@@ -1038,6 +1053,7 @@ "dom": 'B<"clearfix">t', }, columns_settings); + $("#exemptcheck").change(function () { if (this.checked == true) { $("#barcode").addClass("input-warning"); @@ -1147,6 +1163,18 @@ window.open("/cgi-bin/koha/members/printslip.pl?borrowernumber=" + borrowernumber + "&print=checkinslip", "printwindow"); }); + $("input#delay_notice_until").on("change", function () { + console.log('change'); + let delay_date = $(this).val(); + $("span#saved_delay_notice").text(delay_date); + if ( delay_date == '' ){ + $("div#delay_notice").hide(); + } + else { + $("div#delay_notice").show(); + } + }); + }); [% END %] diff --git a/koha-tmpl/intranet-tmpl/prog/en/modules/members/notices.tt b/koha-tmpl/intranet-tmpl/prog/en/modules/members/notices.tt index acfa28cd72..c36c538203 100644 --- a/koha-tmpl/intranet-tmpl/prog/en/modules/members/notices.tt +++ b/koha-tmpl/intranet-tmpl/prog/en/modules/members/notices.tt @@ -72,7 +72,7 @@ [% IF ( QUEUED_MESSAGE.status == 'sent' ) %]sent - [% ELSIF ( QUEUED_MESSAGE.status == 'pending' ) %]pending + [% ELSIF ( QUEUED_MESSAGE.status == 'pending' ) %]pending [% IF QUEUED_MESSAGE.delay_until %], delayed until [% QUEUED_MESSAGE.delay_until | $KohaDates with_hours => 1 %][% END %] [% ELSIF ( QUEUED_MESSAGE.status == 'failed' ) %]failed [% ELSIF ( QUEUED_MESSAGE.status == 'deleted' ) %]deleted [% ELSE %][% QUEUED_MESSAGE.status | html %][% END %] -- 2.20.1