File Coverage

File:C4/ItemCirculationAlertPreference.pm
Coverage:20.2%

linestmtbrancondsubtimecode
1package C4::ItemCirculationAlertPreference;
2
3# This file is part of Koha.
4#
5# Koha is free software; you can redistribute it and/or modify it under the
6# terms of the GNU General Public License as published by the Free Software
7# Foundation; either version 2 of the License, or (at your option) any later
8# version.
9#
10# Koha is distributed in the hope that it will be useful, but WITHOUT ANY
11# WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
12# A PARTICULAR PURPOSE. See the GNU General Public License for more details.
13#
14# You should have received a copy of the GNU General Public License along with
15# Koha; if not, write to the Free Software Foundation, Inc., 59 Temple Place,
16# Suite 330, Boston, MA 02111-1307 USA
17
18
15
15
15
458
43
689
use strict;
19
15
15
15
107
43
754
use warnings;
20
15
15
15
293
42
220
use C4::Context;
21
15
15
15
2952
97
512
use C4::Category;
22
15
15
15
2234
56
590
use C4::ItemType;
23
15
15
15
182
70
23009
use Carp qw(carp croak);
24
25our $AUTOLOAD;
26
27# helper function for validating \%opts
28our $valid = sub {
29    my $opts = shift;
30    for (qw(branchcode categorycode item_type notification)) {
31        exists($opts->{$_}) || croak("'$_' is a required parameter.");
32    }
33};
34
35
36
37
38 - 83
=head1 NAME

C4::ItemCirculationAlertPreference - manage preferences for sending alerts

=head1 SYNOPSIS

Basics:

    use C4::ItemCirculationAlertPreference;

    # a short-cut to reduce typing the long package name over and over again
    my $preferences = 'C4::ItemCirculationAlertPreference';

Creating a restriction on sending messages:

    my $pref = $preferences->create({
        branchcode   => 'CPL',
        categorycode => 'YA',
        item_type    => 'BK',
        notification => 'CHECKOUT',
    });

Removing a restriction on sending messages:

    $preferences->delete({
        branchcode   => 'CPL',
        categorycode => 'YA',
        item_type    => 'BK',
        notification => 'CHECKOUT',
    });

=head1 DESCRIPTION

This class is used to manage the preferences for when an alert may be sent.  By
default, item circulation alerts are enabled for every B<branch>, B<patron
category> and B<item type>.

However, if you would like to prevent item circulation alerts from being sent
for any combination of these 3 variables, a preference can be inserted into the
C<item_circulation_alert_preferences> table to make that a policy.

=head1 API

=head2 Class Methods

=cut
84
85 - 90
=head3 C4::ItemCirculationAlertPreference->new(\%opts)

This is a constructor for an in-memory C4::ItemCirculationAlertPreference
object.  The database is not affected by this method.

=cut
91
92sub new {
93
0
    my ($class, $opts) = @_;
94
0
    bless $opts => $class;
95}
96
97
98
99
100 - 126
=head3 C4::ItemCirculationAlertPreference->create(\%opts)

This will find or create an item circulation alert preference.  You must pass
it a B<branchcode>, B<categorycode>, B<item_type>, and B<notification>.  Valid
values for these attributes are as follows:

=over 4

=item branchcode

branches.branchcode

=item categorycode

category.categorycode

=item item_type

itemtypes.itemtype

=item notification

This can be "CHECKIN" or "CHECKOUT"

=back

=cut
127
128sub create {
129
0
    my ($class, $opts) = @_;
130
0
    $valid->($opts);
131
0
    my $dbh = C4::Context->dbh;
132
0
    my $prefs = $dbh->selectall_arrayref(
133        "SELECT id, branchcode, categorycode, item_type
134        FROM item_circulation_alert_preferences
135        WHERE branchcode = ?
136        AND categorycode = ?
137        AND item_type = ?
138        AND notification = ?",
139        { Slice => {} },
140        $opts->{branchcode},
141        $opts->{categorycode},
142        $opts->{item_type},
143        $opts->{notification},
144    );
145
0
    if (@$prefs) {
146
0
        return $class->new($prefs->[0]);
147    } else {
148
0
        my $success = $dbh->do(
149            "INSERT INTO item_circulation_alert_preferences
150            (branchcode, categorycode, item_type, notification) VALUES (?, ?, ?, ?)",
151            {},
152            $opts->{branchcode},
153            $opts->{categorycode},
154            $opts->{item_type},
155            $opts->{notification},
156        );
157
0
        if ($success) {
158
0
            my $self = {
159                id => $dbh->last_insert_id(undef, undef, undef, undef),
160                branchcode => $opts->{branchcode},
161                categorycode => $opts->{categorycode},
162                item_type => $opts->{item_type},
163                notification => $opts->{notification},
164            };
165
0
            return $class->new($self);
166        } else {
167
0
            carp $dbh->errstr;
168
0
            return undef;
169        }
170    }
171}
172
173
174
175
176 - 182
=head3 C4::ItemCirculationAlertPreference->delete(\%opts)

Delete an item circulation alert preference.  You can delete by either passing
in an B<id> or passing in a B<branchcode>, B<categorycode>, B<item_type>
triplet.

=cut
183
184sub delete {
185
0
    my ($class, $opts) = @_;
186
0
    my $dbh = C4::Context->dbh;
187
0
    if ($opts->{id}) {
188
0
        $dbh->do(
189            "DELETE FROM item_circulation_alert_preferences WHERE id = ?",
190            {},
191            $opts->{id}
192        );
193    } else {
194
0
        $valid->($opts);
195
0
        my $sql =
196            "DELETE FROM item_circulation_alert_preferences
197            WHERE branchcode = ?
198            AND categorycode = ?
199            AND item_type = ?
200            AND notification = ?";
201
0
        $dbh->do(
202            $sql,
203            {},
204            $opts->{branchcode},
205            $opts->{categorycode},
206            $opts->{item_type},
207            $opts->{notification},
208        );
209    }
210}
211
212
213
214
215 - 234
=head3 C4::ItemCirculationAlertPreference->is_enabled_for(\%opts)

Based on the existing preferences in the C<item_circulation_alert_preferences>
table, can an alert be sent for the given B<branchcode>, B<categorycode>, and
B<itemtype>?

B<Example>:

    my $alert = 'C4::ItemCirculationAlertPreference';
    my $conditions = {
        branchcode   => 'CPL',
        categorycode => 'IL',
        item_type    => 'MU',
    };

    if ($alert->is_enabled_for($conditions)) {
        # ...
    }

=cut
235
236sub is_disabled_for {
237
0
    my ($class, $opts) = @_;
238
0
    $valid->($opts);
239
0
    my $dbh = C4::Context->dbh;
240
241    # Does a preference exist to block this alert?
242
0
    my $query = qq{
243        SELECT id, branchcode, categorycode, item_type, notification
244          FROM item_circulation_alert_preferences
245         WHERE (branchcode = ? OR branchcode = '*')
246           AND (categorycode = ? OR categorycode = '*')
247           AND (item_type = ? OR item_type = '*')
248           AND (notification = ? OR notification = '*')
249    };
250
251
0
    my $preferences = $dbh->selectall_arrayref(
252        $query,
253        { Slice => {} },
254        $opts->{branchcode},
255        $opts->{categorycode},
256        $opts->{item_type},
257        $opts->{notification},
258    );
259
260    # If any preferences showed up, we are NOT enabled.
261
0
    return @$preferences;
262}
263
264sub is_enabled_for {
265
0
    my ($class, $opts) = @_;
266
0
    return not $class->is_disabled_for($opts);
267}
268
269
270
271
272 - 284
=head3 C4::ItemCirculationAlertPreference->find({ branchcode => $bc, notification => $type })

This method returns all the item circulation alert preferences for a given
branch and notification.

B<Example>:

    my @branch_prefs = C4::ItemCirculationAlertPreference->find({
        branchcode   => 'CPL',
        notification => 'CHECKIN',
    });

=cut
285
286sub find {
287
0
    my ($class, $where) = @_;
288
0
    my $dbh = C4::Context->dbh;
289
0
    my $query = qq{
290        SELECT id, branchcode, categorycode, item_type, notification
291          FROM item_circulation_alert_preferences
292         WHERE branchcode = ? AND notification = ?
293         ORDER BY categorycode, item_type
294    };
295
0
0
0
    return map { $class->new($_) } @{$dbh->selectall_arrayref(
296        $query,
297        { Slice => {} },
298        $where->{branchcode},
299        $where->{notification},
300    )};
301}
302
303
304
305
306 - 325
=head3 C4::ItemCirculationAlertPreference->grid({ branchcode => $c, notification => $type })

Return a 2D arrayref for the grid view in F<admin/item_circulation_alert_preferences.pl>.
Each row represents a category (like 'Patron' or 'Young Adult') and
each column represents an itemtype (like 'Book' or 'Music').

Each cell contains...

B<Example>:

    use Data::Dump 'pp';
    my $grid = C4::ItemCirculationAlertPreference->grid({
        branchcode   => 'CPL',
        notification => 'CHECKOUT',
    });
    warn pp($grid);

See F<admin/item_circulation_alerts.pl> to see how this method is used.

=cut
326
327sub grid {
328
0
    my ($class, $where) = @_;
329
0
    my @branch_prefs = $class->find($where);
330
0
    my @default_prefs = $class->find({ branchcode => '*', notification => $where->{notification} });
331
0
    my @cc = C4::Category->all;
332
0
    my @it = C4::ItemType->all;
333
0
    my $notification = $where->{notification};
334
0
    my %disabled = map {
335
0
        my $key = $_->categorycode . "-" . $_->item_type . "-" . $notification;
336
0
        $key =~ s/\*/_/g;
337
0
        ($key => 1);
338    } @branch_prefs;
339
0
    my %default = map {
340
0
        my $key = $_->categorycode . "-" . $_->item_type . "-" . $notification;
341
0
        $key =~ s/\*/_/g;
342
0
        ($key => 1);
343    } @default_prefs;
344
0
    my @grid;
345
0
    for my $c (@cc) {
346
0
        my $row = { description => $c->description, items => [] };
347
0
        push @grid, $row;
348
0
        for my $i (@it) {
349
0
            my $key = $c->categorycode . "-" . $i->itemtype . "-" . $notification;
350
0
            $key =~ s/\*/_/g;
351
0
            my @classes;
352
0
            my $text = " ";
353
0
            if ($disabled{$key}) {
354
0
                push @classes, 'disabled';
355
0
                $text = "Disabled for $where->{branchcode}";
356            }
357
0
            if ($default{$key}) {
358
0
                push @classes, 'default';
359
0
                $text = "Disabled for all";
360            }
361
0
0
            push @{$row->{items}}, {
362                class => join(' ', @classes),
363                id => $key,
364                text => $text,
365            };
366        }
367    }
368
0
    return \@grid;
369}
370
371
372
373
374 - 380
=head2 Object Methods

These are read-only accessors for the various attributes of a preference.

=head3 $pref->id

=cut
381
382 - 384
=head3 $pref->branchcode

=cut
385
386 - 388
=head3 $pref->categorycode

=cut
389
390 - 392
=head3 $pref->item_type

=cut
393
394 - 396
=head3 $pref->notification

=cut
397
398sub AUTOLOAD {
399
0
    my $self = shift;
400
0
    my $attr = $AUTOLOAD;
401
0
    $attr =~ s/.*://;
402
0
    if (exists $self->{$attr}) {
403
0
        return $self->{$attr};
404    } else {
405
0
        return undef;
406    }
407}
408
409
0
sub DESTROY { }
410
411
412
413 - 421
=head1 SEE ALSO

L<C4::Circulation>, F<admin/item_circulation_alerts.pl>

=head1 AUTHOR

John Beppu <john.beppu@liblime.com>

=cut
422
4231;