From 3bf7430d1c41bf9acb363f4fff9476f6ee653fdd Mon Sep 17 00:00:00 2001 From: Joseph Sikowitz <joe@flo.org> Date: Fri, 17 Jul 2020 11:34:30 -0400 Subject: [PATCH] Bug 14648: Batch remove reserve items Adds "Batch remove items" button to course-reserves.tt. Creates batch_rm_items.pl and batch_rm_items.tt. Allows user to enter a list of barcode numbers so that they will be removed from all course reserves to which they are attached. A dialog box will provide a warning before the final deletion is made. This patch also now moves barcodes that are invalid or not attached to a course reserve to the invalid barcodes output. It also provides a count of the courses that the deleted items were attached to. Test Plan 1. Log in as a user with permissions to add and delete course reserves 2. Add the same items to multiple course reserves 3. Go to the main course reserves page (i.e. /cgi-bin/koha/course_reserves/course-reserves.pl) 4. Click the "- Batch remove items" button 5. Enter the barcodes that you added to multiple reserves in step 1 6. Click submit 7. Click Ok if you are ready to delete all of these items 8. Check each course reserve that you added the items to in step 1 to make sure the items you entered were deleted but nothing else 9. Repeat 2-5 10. Add an invalid barcode and a valid barcode that is not attached to a course reserve 11. Repeat 6-7 12. You should see that the items attached to course reserves were removed while the invalid and unattached barcodes were rejected 13. Log out 14. Log in as a user without permission to delete course reserves 15. Go to the main course reserves page (i.e. /cgi-bin/koha/course_reserves/course-reserves.pl) 16. You should not longer see the "- Batch remove items" button Signed-off-by: David Nind <david@davidnind.com> Signed-off-by: Katrin Fischer <katrin.fischer.83@web.de> Signed-off-by: Jonathan Druart <jonathan.druart@bugs.koha-community.org> --- course_reserves/batch_rm_items.pl | 90 +++++++++++++++++++ .../modules/course_reserves/batch_rm_items.tt | 84 +++++++++++++++++ .../course_reserves/course-reserves.tt | 5 +- 3 files changed, 178 insertions(+), 1 deletion(-) create mode 100755 course_reserves/batch_rm_items.pl create mode 100644 koha-tmpl/intranet-tmpl/prog/en/modules/course_reserves/batch_rm_items.tt diff --git a/course_reserves/batch_rm_items.pl b/course_reserves/batch_rm_items.pl new file mode 100755 index 0000000000..be8654089e --- /dev/null +++ b/course_reserves/batch_rm_items.pl @@ -0,0 +1,90 @@ +#!/usr/bin/perl + +# This file is part of Koha. +# +# Copyright (C) 2020 Fenway Library Organization +# +# 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 <http://www.gnu.org/licenses>. + +use Modern::Perl; + +use CGI qw( -utf8 ); +use List::MoreUtils qw( uniq ); + +use C4::Auth; +use C4::Output; +use C4::CourseReserves qw(GetItemCourseReservesInfo DelCourseReserve GetCourseItem); + +use Koha::Items; + +my $cgi = new CGI; + +my $action = $cgi->param('action') || q{}; +my $barcodes = $cgi->param('barcodes') || q{}; + +my ( $template, $loggedinuser, $cookie ) = get_template_and_user( + { + template_name => "course_reserves/batch_rm_items.tt", + query => $cgi, + type => "intranet", + flagsrequired => { coursereserves => 'delete_reserves' }, + } +); + +if ( !$action ) { + $template->param( action => 'display_form' ); +} + +elsif ( $action eq 'batch_rm' ) { + my @barcodes = uniq( split (/\s\n/, $barcodes ) ); + my @invalid_barcodes; + my @item_and_count; + + foreach my $bar (@barcodes) { + my $item = Koha::Items->find( { barcode => $bar } ); + if($item) { + my $courseitem = GetCourseItem(itemnumber => $item->id); + if($courseitem) { + + my $res_info = GetItemCourseReservesInfo(itemnumber => $item->id); + + my $no_of_res = @$res_info; + + my $delitemcount = {'delitem' => $item, 'delcount' => $no_of_res}; + push ( @item_and_count, $delitemcount ); + + foreach my $cr (@$res_info) { + if($cr->{cr_id}) { + DelCourseReserve('cr_id' => $cr->{cr_id}); + } + } + } + else { + push( @invalid_barcodes, $bar); + } + } + else { + push( @invalid_barcodes, $bar ); + } + + } + + $template->param( + action => 'display_results', + invalid_barcodes => \@invalid_barcodes, + item_and_count => \@item_and_count, + ); +} + +output_html_with_http_headers $cgi, $cookie, $template->output; diff --git a/koha-tmpl/intranet-tmpl/prog/en/modules/course_reserves/batch_rm_items.tt b/koha-tmpl/intranet-tmpl/prog/en/modules/course_reserves/batch_rm_items.tt new file mode 100644 index 0000000000..a1b415b1b8 --- /dev/null +++ b/koha-tmpl/intranet-tmpl/prog/en/modules/course_reserves/batch_rm_items.tt @@ -0,0 +1,84 @@ +[% SET footerjs = 1 %] + +[% INCLUDE 'doc-head-open.inc' %] +<title>Koha › Course reserves › Remove items</title> +[% INCLUDE 'doc-head-close.inc' %] +</head> +<body id="courses_rm_items" class="course"> + +[% INCLUDE 'header.inc' %] +[% INCLUDE 'cat-search.inc' %] + +<div id="breadcrumbs"><a href="/cgi-bin/koha/mainpage.pl">Home</a> › <a href="/cgi-bin/koha/course_reserves/course-reserves.pl">Course reserves</a> › Batch remove reserves</div> + +<div class="main container-fluid"> + <div class="row"> + <div class="col-md-8 col-md-offset-2"> + [% IF action == 'display_form' %] + <form method="post" action="/cgi-bin/koha/course_reserves/batch_rm_items.pl"> + <input type="hidden" name="action" value="batch_rm" /> + <fieldset class="rows"> + <legend>Remove items: scan barcodes</legend> + <ol> + <li> + <label class="required" for="barcodes">Item barcodes:</label> + <textarea rows="20" cols="50" id="barcodes" name="barcodes" class="focus"></textarea> + </li> + </ol> + </fieldset> + <fieldset class="action"> + <p>All course reserve items will be deleted from all courses to which they are attached.</p> + <input type="submit" value="Submit" class="submit" id="batch_rm_btn" /> + <a href="/cgi-bin/koha/course_reserves/course-reserves.pl" class="cancel">Cancel</a> + </fieldset> + </form> + [% END %] + + [% IF action == 'display_results' %] + <h1>Results</h1> + + <h3>Items deleted</h3> + [% IF item_and_count > 0 %] + <p>The following items were removed from all courses:</p> + <ul> + [% FOREACH i IN item_and_count %] + [% IF i.delcount == 1 %] + <li>[% i.delitem.biblio.title | html %] ([% i.delitem.barcode | html %]) was removed from [% i.delcount %] course.</li> + [% ELSIF i.delcount > 1 %] + <li>[% i.delitem.biblio.title | html %] ([% i.delitem.barcode | html %]) was removed from [% i.delcount %] courses.</li> + [% END %] + [% END %] + </ul> + [% ELSE %] + No valid item barcodes found. + [% END %] + + + [% IF invalid_barcodes.size > 0 %] + <h3>Invalid barcodes</h3> + <p>The following invalid barcodes were skipped:</p> + <ul> + [% FOREACH b IN invalid_barcodes %] + <li>[% b | html %]</li> + [% END %] + </ul> + [% END %] + + <p> + <a class='btn btn-default' href="/cgi-bin/koha/course_reserves/course-reserves.pl">Return</a> + </p> + [% END %] + </div> +</div> + +[% MACRO jsinclude BLOCK %] + <script> + $(document).ready(function() { + $("#batch_rm_btn").click(function(){ + return confirmDelete(_("Are you sure you want to remove these items from all courses?")); + }); + }); + </script> +[% END %] + +[% INCLUDE 'intranet-bottom.inc' %] diff --git a/koha-tmpl/intranet-tmpl/prog/en/modules/course_reserves/course-reserves.tt b/koha-tmpl/intranet-tmpl/prog/en/modules/course_reserves/course-reserves.tt index 27f73048fc..c8fa816eef 100644 --- a/koha-tmpl/intranet-tmpl/prog/en/modules/course_reserves/course-reserves.tt +++ b/koha-tmpl/intranet-tmpl/prog/en/modules/course_reserves/course-reserves.tt @@ -20,11 +20,14 @@ <div class="row"> <div class="col-md-10 col-md-offset-1"> - [% IF CAN_user_coursereserves_add_reserves OR CAN_user_coursereserves_manage_courses OR CAN_user_coursereserves_manage_courses %] + [% IF CAN_user_coursereserves_add_reserves OR CAN_user_coursereserves_manage_courses OR CAN_user_coursereserves_manage_courses OR CAN_user_coursereserves_delete_reserves %] <div id="toolbar"> [% IF ( CAN_user_coursereserves_manage_courses ) %] <a class="btn btn-default" id="new_course" href="/cgi-bin/koha/course_reserves/course.pl"><i class="fa fa-plus"></i> New course</a> [% END %] + [% IF ( CAN_user_coursereserves_delete_reserves ) %] + <a class="btn btn-default" id="batch_rm" href="/cgi-bin/koha/course_reserves/batch_rm_items.pl"><i class="fa fa-minus"></i> Batch remove items</a> + [% END %] </div><!-- /toolbar --> [% END %]