View | Details | Raw Unified | Return to bug 40529
Collapse All | Expand All

(-)a/C4/HoldsQueue.pm (+5 lines)
Lines 26-31 use C4::Context; Link Here
26
use C4::Circulation qw( GetBranchItemRule );
26
use C4::Circulation qw( GetBranchItemRule );
27
use Koha::DateUtils qw( dt_from_string );
27
use Koha::DateUtils qw( dt_from_string );
28
use Koha::Hold::HoldsQueueItems;
28
use Koha::Hold::HoldsQueueItems;
29
use Koha::HoldGroup;
29
use Koha::Items;
30
use Koha::Items;
30
use Koha::Libraries;
31
use Koha::Libraries;
31
use Koha::Logger;
32
use Koha::Logger;
Lines 250-255 that have one or more unfilled hold requests. Link Here
250
sub GetBibsWithPendingHoldRequests {
251
sub GetBibsWithPendingHoldRequests {
251
    my $dbh = C4::Context->dbh;
252
    my $dbh = C4::Context->dbh;
252
253
254
    my $skip_non_target_holds_query     = Koha::HoldGroup::skip_non_target_holds_query('sql');
255
    my $skip_non_target_holds_query_sql = $skip_non_target_holds_query ? " $skip_non_target_holds_query" : '';
256
253
    my $bib_query = "SELECT DISTINCT biblionumber
257
    my $bib_query = "SELECT DISTINCT biblionumber
254
                     FROM reserves
258
                     FROM reserves
255
                     WHERE found IS NULL
259
                     WHERE found IS NULL
Lines 257-262 sub GetBibsWithPendingHoldRequests { Link Here
257
                     AND reservedate <= CURRENT_DATE()
261
                     AND reservedate <= CURRENT_DATE()
258
                     AND suspend = 0
262
                     AND suspend = 0
259
                     AND reserve_id NOT IN (SELECT reserve_id FROM hold_fill_targets)
263
                     AND reserve_id NOT IN (SELECT reserve_id FROM hold_fill_targets)
264
                     $skip_non_target_holds_query_sql
260
                     ";
265
                     ";
261
    my $sth = $dbh->prepare($bib_query);
266
    my $sth = $dbh->prepare($bib_query);
262
267
(-)a/C4/Reserves.pm (-10 / +12 lines)
Lines 40-45 use Koha::CirculationRules; Link Here
40
use Koha::Database;
40
use Koha::Database;
41
use Koha::DateUtils qw( dt_from_string output_pref );
41
use Koha::DateUtils qw( dt_from_string output_pref );
42
use Koha::Holds;
42
use Koha::Holds;
43
use Koha::HoldGroup;
43
use Koha::ItemTypes;
44
use Koha::ItemTypes;
44
use Koha::Items;
45
use Koha::Items;
45
use Koha::Libraries;
46
use Koha::Libraries;
Lines 1353-1358 sub ModReserveAffect { Link Here
1353
1354
1354
    if ($transferToDo) {
1355
    if ($transferToDo) {
1355
        $hold->set_transfer();
1356
        $hold->set_transfer();
1357
        $hold->set_as_hold_group_target();
1356
    } elsif ( C4::Context->preference('HoldsNeedProcessingSIP')
1358
    } elsif ( C4::Context->preference('HoldsNeedProcessingSIP')
1357
        && C4::Context->interface eq 'sip'
1359
        && C4::Context->interface eq 'sip'
1358
        && !$already_on_shelf )
1360
        && !$already_on_shelf )
Lines 1366-1379 sub ModReserveAffect { Link Here
1366
        my $transfer = $hold->item->get_transfer;
1368
        my $transfer = $hold->item->get_transfer;
1367
        $transfer->receive if $transfer;
1369
        $transfer->receive if $transfer;
1368
1370
1369
        # if this hold was part of a group, cancel other holds in the group
1371
        $hold->set_as_hold_group_target();
1370
        if ( $hold->hold_group_id ) {
1371
            my @holds = $hold->hold_group->holds->as_list;
1372
            foreach my $h (@holds) {
1373
                push @reserve_ids, $h->reserve_id;
1374
                $h->cancel unless $h->reserve_id == $hold->reserve_id;
1375
            }
1376
        }
1377
    }
1372
    }
1378
1373
1379
    _koha_notify_hold_changed($hold) if $notify_library;
1374
    _koha_notify_hold_changed($hold) if $notify_library;
Lines 1862-1867 sub _Findgroupreserve { Link Here
1862
    my ( $biblionumber, $itemnumber, $lookahead, $ignore_borrowers ) = @_;
1857
    my ( $biblionumber, $itemnumber, $lookahead, $ignore_borrowers ) = @_;
1863
    my $dbh = C4::Context->dbh;
1858
    my $dbh = C4::Context->dbh;
1864
1859
1860
    my $skip_non_target_holds_query     = Koha::HoldGroup::skip_non_target_holds_query('sql');
1861
    my $skip_non_target_holds_query_sql = $skip_non_target_holds_query ? " $skip_non_target_holds_query" : '';
1862
1865
    # check for targeted match form the holds queue
1863
    # check for targeted match form the holds queue
1866
    my $hold_target_query = qq{
1864
    my $hold_target_query = qq{
1867
        SELECT reserves.biblionumber        AS biblionumber,
1865
        SELECT reserves.biblionumber        AS biblionumber,
Lines 1878-1884 sub _Findgroupreserve { Link Here
1878
               reserves.reserve_id          AS reserve_id,
1876
               reserves.reserve_id          AS reserve_id,
1879
               reserves.itemtype            AS itemtype,
1877
               reserves.itemtype            AS itemtype,
1880
               reserves.non_priority        AS non_priority,
1878
               reserves.non_priority        AS non_priority,
1881
               reserves.item_group_id           AS item_group_id
1879
               reserves.item_group_id       AS item_group_id,
1880
               reserves.hold_group_id       AS hold_group_id
1882
        FROM reserves
1881
        FROM reserves
1883
        JOIN biblioitems USING (biblionumber)
1882
        JOIN biblioitems USING (biblionumber)
1884
        JOIN hold_fill_targets USING (reserve_id)
1883
        JOIN hold_fill_targets USING (reserve_id)
Lines 1887-1892 sub _Findgroupreserve { Link Here
1887
        AND hold_fill_targets.itemnumber = ?
1886
        AND hold_fill_targets.itemnumber = ?
1888
        AND reservedate <= DATE_ADD(NOW(),INTERVAL ? DAY)
1887
        AND reservedate <= DATE_ADD(NOW(),INTERVAL ? DAY)
1889
        AND suspend = 0
1888
        AND suspend = 0
1889
        $skip_non_target_holds_query_sql
1890
        ORDER BY priority
1890
        ORDER BY priority
1891
    };
1891
    };
1892
    my $sth = $dbh->prepare($hold_target_query);
1892
    my $sth = $dbh->prepare($hold_target_query);
Lines 1913-1924 sub _Findgroupreserve { Link Here
1913
               reserves.reserve_id                 AS reserve_id,
1913
               reserves.reserve_id                 AS reserve_id,
1914
               reserves.itemtype                   AS itemtype,
1914
               reserves.itemtype                   AS itemtype,
1915
               reserves.non_priority               AS non_priority,
1915
               reserves.non_priority               AS non_priority,
1916
               reserves.item_group_id              AS item_group_id
1916
               reserves.item_group_id              AS item_group_id,
1917
               reserves.hold_group_id              AS hold_group_id
1917
        FROM reserves
1918
        FROM reserves
1918
        WHERE reserves.biblionumber = ?
1919
        WHERE reserves.biblionumber = ?
1919
          AND (reserves.itemnumber IS NULL OR reserves.itemnumber = ?)
1920
          AND (reserves.itemnumber IS NULL OR reserves.itemnumber = ?)
1920
          AND reserves.reservedate <= DATE_ADD(NOW(),INTERVAL ? DAY)
1921
          AND reserves.reservedate <= DATE_ADD(NOW(),INTERVAL ? DAY)
1921
          AND suspend = 0
1922
          AND suspend = 0
1923
          $skip_non_target_holds_query_sql
1922
          ORDER BY priority
1924
          ORDER BY priority
1923
    };
1925
    };
1924
    $sth = $dbh->prepare($query);
1926
    $sth = $dbh->prepare($query);
(-)a/Koha/Hold.pm (+19 lines)
Lines 271-276 sub cleanup_hold_group { Link Here
271
    }
271
    }
272
}
272
}
273
273
274
=head3 set_as_hold_group_target
275
276
$self->set_as_hold_group_target;
277
278
Sets this hold and its' hold group's target
279
280
=cut
281
282
sub set_as_hold_group_target {
283
    my ($self) = @_;
284
285
    if ( $self->hold_group && !$self->hold_group->target_hold_id && C4::Context->preference("DisplayAddHoldGroups") ) {
286
        $self->_result->create_related(
287
            'hold_group_target_hold',
288
            { hold_group_id => $self->hold_group->hold_group_id }
289
        );
290
    }
291
}
292
274
=head3 is_hold_group_target
293
=head3 is_hold_group_target
275
294
276
$self->is_hold_group_target;
295
$self->is_hold_group_target;
(-)a/Koha/HoldGroup.pm (+35 lines)
Lines 94-99 sub target_hold_id { Link Here
94
    return $self->_result->hold_group_target_hold->reserve_id;
94
    return $self->_result->hold_group_target_hold->reserve_id;
95
}
95
}
96
96
97
=head3 skip_non_target_holds_query
98
99
    $where{'me.hold_group_id'} = Koha::HoldGroup::skip_non_target_holds_query('dbix')
100
101
Static method, returns the query part be added if DisplayAddHoldGroups
102
Accepts a $query_type of 'dbix' or 'sql' and returns the respective query
103
The query is designed to skip non target holds that are part of a hold group which already has a hold target
104
105
=cut
106
107
sub skip_non_target_holds_query {
108
    my ($query_type) = @_;
109
110
    return unless C4::Context->preference('DisplayAddHoldGroups');
111
112
    my $query_types = {
113
        'dbix' => [
114
            -or => { '=' => undef },
115
            [
116
                -and => { '!=' => undef },
117
                {
118
                    -not_in => \
119
                        'SELECT hold_group_id FROM hold_group_target_holds WHERE reserve_id IS NOT NULL AND hold_group_id IS NOT NULL'
120
                }
121
            ]
122
        ],
123
        'sql' =>
124
            'AND (hold_group_id IS NULL OR hold_group_id IS NOT NULL AND reserves.hold_group_id NOT IN (SELECT hold_group_id FROM hold_group_target_holds WHERE reserve_id IS NOT NULL AND hold_group_id IS NOT NULL))'
125
    };
126
127
    return unless $query_type && exists $query_types->{$query_type};
128
129
    return $query_types->{$query_type};
130
}
131
97
=head3 _type
132
=head3 _type
98
133
99
=cut
134
=cut
(-)a/circ/pendingreserves.pl (-2 / +9 lines)
Lines 31-36 use C4::Items; Link Here
31
use Koha::Biblios;
31
use Koha::Biblios;
32
use Koha::DateUtils qw( dt_from_string );
32
use Koha::DateUtils qw( dt_from_string );
33
use Koha::Holds;
33
use Koha::Holds;
34
use Koha::HoldGroup;
34
use DateTime::Duration;
35
use DateTime::Duration;
35
36
36
my $input          = CGI->new;
37
my $input          = CGI->new;
Lines 182-187 if ( C4::Context->only_my_library() ) { Link Here
182
    $where{'me.branchcode'} = C4::Context->userenv->{'branch'};
183
    $where{'me.branchcode'} = C4::Context->userenv->{'branch'};
183
}
184
}
184
185
186
my $skip_non_target_holds_query = Koha::HoldGroup::skip_non_target_holds_query('dbix');
187
$where{'me.hold_group_id'} = $skip_non_target_holds_query if $skip_non_target_holds_query;
188
185
# get all distinct unfulfilled reserves
189
# get all distinct unfulfilled reserves
186
my $holds = Koha::Holds->search(
190
my $holds = Koha::Holds->search(
187
    {%where},
191
    {%where},
Lines 200-206 if ( $holds->count ) { Link Here
200
# patrons count per biblio
204
# patrons count per biblio
201
my $patrons_count = {
205
my $patrons_count = {
202
    map { $_->{biblionumber} => $_->{patrons_count} } @{ Koha::Holds->search(
206
    map { $_->{biblionumber} => $_->{patrons_count} } @{ Koha::Holds->search(
203
            { 'suspend' => 0, 'found' => undef },
207
            {
208
                'suspend' => 0,
209
                'found'   => undef,
210
                $skip_non_target_holds_query ? ( 'hold_group_id' => $skip_non_target_holds_query ) : ()
211
            },
204
            {
212
            {
205
                select   => [ 'biblionumber', { count => { distinct => 'borrowernumber' } } ],
213
                select   => [ 'biblionumber', { count => { distinct => 'borrowernumber' } } ],
206
                as       => [qw( biblionumber patrons_count )],
214
                as       => [qw( biblionumber patrons_count )],
207
- 

Return to bug 40529