Bug 8836 - Resurrect Rotating Collections
[koha.git] / C4 / RotatingCollections.pm
1 package C4::RotatingCollections;
2
3 # $Id: RotatingCollections.pm,v 0.1 2007/04/20 kylemhall
4
5 # This package is inteded to keep track of what library
6 # Items of a certain collection should be at.
7
8 # Copyright 2007 Kyle Hall
9 #
10 # This file is part of Koha.
11 #
12 # Koha is free software; you can redistribute it and/or modify it under the
13 # terms of the GNU General Public License as published by the Free Software
14 # Foundation; either version 2 of the License, or (at your option) any later
15 # version.
16 #
17 # Koha is distributed in the hope that it will be useful, but WITHOUT ANY
18 # WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR
19 # A PARTICULAR PURPOSE.  See the GNU General Public License for more details.
20 #
21 # You should have received a copy of the GNU General Public License along
22 # with Koha; if not, write to the Free Software Foundation, Inc.,
23 # 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
24
25 use Modern::Perl;
26
27 use C4::Context;
28 use C4::Circulation;
29 use C4::Reserves qw(GetReserveStatus);
30
31 use DBI;
32
33 use Data::Dumper;
34
35 use vars qw($VERSION @ISA @EXPORT);
36
37 # set the version for version checking
38 $VERSION = 3.07.00.049;
39
40 =head1 NAME
41
42 C4::RotatingCollections - Functions for managing rotating collections
43
44 =head1 FUNCTIONS
45
46 =cut
47
48 BEGIN {
49     require Exporter;
50     @ISA    = qw( Exporter );
51     @EXPORT = qw(
52       CreateCollection
53       UpdateCollection
54       DeleteCollection
55
56       GetItemsInCollection
57
58       GetCollection
59       GetCollections
60
61       AddItemToCollection
62       RemoveItemFromCollection
63       TransferCollection
64
65       GetCollectionItemBranches
66     );
67 }
68
69 =head2  CreateCollection
70  ( $success, $errorcode, $errormessage ) = CreateCollection( $title, $description );
71  Creates a new collection
72
73  Input:
74    $title: short description of the club or service
75    $description: long description of the club or service
76
77  Output:
78    $success: 1 if all database operations were successful, 0 otherwise
79    $errorCode: Code for reason of failure, good for translating errors in templates
80    $errorMessage: English description of error
81
82 =cut
83
84 sub CreateCollection {
85     my ( $title, $description ) = @_;
86
87     ## Check for all neccessary parameters
88     if ( !$title ) {
89         return ( 0, 1, "No Title Given" );
90     }
91     if ( !$description ) {
92         return ( 0, 2, "No Description Given" );
93     }
94
95     my $success = 1;
96
97     my $dbh = C4::Context->dbh;
98
99     my $sth;
100     $sth = $dbh->prepare(
101         "INSERT INTO collections ( colId, colTitle, colDesc )
102                         VALUES ( NULL, ?, ? )"
103     );
104     $sth->execute( $title, $description ) or return ( 0, 3, $sth->errstr() );
105
106     return 1;
107
108 }
109
110 =head2 UpdateCollection
111
112  ( $success, $errorcode, $errormessage ) = UpdateCollection( $colId, $title, $description );
113
114 Updates a collection
115
116  Input:
117    $colId: id of the collection to be updated
118    $title: short description of the club or service
119    $description: long description of the club or service
120
121  Output:
122    $success: 1 if all database operations were successful, 0 otherwise
123    $errorCode: Code for reason of failure, good for translating errors in templates
124    $errorMessage: English description of error
125
126 =cut
127
128 sub UpdateCollection {
129     my ( $colId, $title, $description ) = @_;
130
131     ## Check for all neccessary parameters
132     if ( !$colId ) {
133         return ( 0, 1, "No Id Given" );
134     }
135     if ( !$title ) {
136         return ( 0, 2, "No Title Given" );
137     }
138     if ( !$description ) {
139         return ( 0, 3, "No Description Given" );
140     }
141
142     my $dbh = C4::Context->dbh;
143
144     my $sth;
145     $sth = $dbh->prepare(
146         "UPDATE collections
147                         SET 
148                         colTitle = ?, colDesc = ? 
149                         WHERE colId = ?"
150     );
151     $sth->execute( $title, $description, $colId )
152       or return ( 0, 4, $sth->errstr() );
153
154     return 1;
155
156 }
157
158 =head2 DeleteCollection
159
160  ( $success, $errorcode, $errormessage ) = DeleteCollection( $colId );
161  Deletes a collection of the given id
162
163  Input:
164    $colId : id of the Archtype to be deleted
165
166  Output:
167    $success: 1 if all database operations were successful, 0 otherwise
168    $errorCode: Code for reason of failure, good for translating errors in templates
169    $errorMessage: English description of error
170
171 =cut
172
173 sub DeleteCollection {
174     my ($colId) = @_;
175
176     ## Paramter check
177     if ( !$colId ) {
178         return ( 0, 1, "No Collection Id Given" );
179     }
180
181     my $dbh = C4::Context->dbh;
182
183     my $sth;
184
185     $sth = $dbh->prepare("DELETE FROM collections WHERE colId = ?");
186     $sth->execute($colId) or return ( 0, 4, $sth->errstr() );
187
188     return 1;
189 }
190
191 =head2 GetCollections
192
193  $collections = GetCollections();
194  Returns data about all collections
195
196  Output:
197   On Success:
198    $results: Reference to an array of associated arrays
199   On Failure:
200    $errorCode: Code for reason of failure, good for translating errors in templates
201    $errorMessage: English description of error
202
203 =cut
204
205 sub GetCollections {
206
207     my $dbh = C4::Context->dbh;
208
209     my $sth = $dbh->prepare("SELECT * FROM collections");
210     $sth->execute() or return ( 1, $sth->errstr() );
211
212     my @results;
213     while ( my $row = $sth->fetchrow_hashref ) {
214         push( @results, $row );
215     }
216
217     return \@results;
218 }
219
220 =head2 GetItemsInCollection
221
222  ( $results, $success, $errorcode, $errormessage ) = GetItemsInCollection( $colId );
223
224  Returns information about the items in the given collection
225  
226  Input:
227    $colId: The id of the collection
228
229  Output:
230    $results: Reference to an array of associated arrays
231    $success: 1 if all database operations were successful, 0 otherwise
232    $errorCode: Code for reason of failure, good for translating errors in templates
233    $errorMessage: English description of error
234
235 =cut
236
237 sub GetItemsInCollection {
238     my ($colId) = @_;
239
240     ## Paramter check
241     if ( !$colId ) {
242         return ( 0, 0, 1, "No Collection Id Given" );
243     }
244
245     my $dbh = C4::Context->dbh;
246
247     my $sth = $dbh->prepare(
248         "SELECT
249                              biblio.title,
250                              items.itemcallnumber,
251                              items.barcode
252                            FROM collections, collections_tracking, items, biblio
253                            WHERE collections.colId = collections_tracking.colId
254                            AND collections_tracking.itemnumber = items.itemnumber
255                            AND items.biblionumber = biblio.biblionumber
256                            AND collections.colId = ? ORDER BY biblio.title"
257     );
258     $sth->execute($colId) or return ( 0, 0, 2, $sth->errstr() );
259
260     my @results;
261     while ( my $row = $sth->fetchrow_hashref ) {
262         push( @results, $row );
263     }
264
265     return \@results;
266 }
267
268 =head2 GetCollection
269
270  ( $colId, $colTitle, $colDesc, $colBranchcode ) = GetCollection( $colId );
271
272 Returns information about a collection
273
274  Input:
275    $colId: Id of the collection
276  Output:
277    $colId, $colTitle, $colDesc, $colBranchcode
278
279 =cut
280
281 sub GetCollection {
282     my ($colId) = @_;
283
284     my $dbh = C4::Context->dbh;
285
286     my ( $sth, @results );
287     $sth = $dbh->prepare("SELECT * FROM collections WHERE colId = ?");
288     $sth->execute($colId) or return 0;
289
290     my $row = $sth->fetchrow_hashref;
291
292     return (
293         $$row{'colId'},   $$row{'colTitle'},
294         $$row{'colDesc'}, $$row{'colBranchcode'}
295     );
296
297 }
298
299 =head2 AddItemToCollection
300
301  ( $success, $errorcode, $errormessage ) = AddItemToCollection( $colId, $itemnumber );
302
303 Adds an item to a rotating collection.
304
305  Input:
306    $colId: Collection to add the item to.
307    $itemnumber: Item to be added to the collection
308  Output:
309    $success: 1 if all database operations were successful, 0 otherwise
310    $errorCode: Code for reason of failure, good for translating errors in templates
311    $errorMessage: English description of error
312
313 =cut
314
315 sub AddItemToCollection {
316     my ( $colId, $itemnumber ) = @_;
317
318     ## Check for all neccessary parameters
319     if ( !$colId ) {
320         return ( 0, 1, "No Collection Given" );
321     }
322     if ( !$itemnumber ) {
323         return ( 0, 2, "No Itemnumber Given" );
324     }
325
326     if ( isItemInThisCollection( $itemnumber, $colId ) ) {
327         return ( 0, 2, "Item is already in the collection!" );
328     }
329     elsif ( isItemInAnyCollection($itemnumber) ) {
330         return ( 0, 3, "Item is already in a different collection!" );
331     }
332
333     my $dbh = C4::Context->dbh;
334
335     my $sth;
336     $sth = $dbh->prepare("
337         INSERT INTO collections_tracking (
338             colId,
339             itemnumber
340         ) VALUES ( ?, ? )
341     ");
342     $sth->execute( $colId, $itemnumber ) or return ( 0, 3, $sth->errstr() );
343
344     return 1;
345
346 }
347
348 =head2  RemoveItemFromCollection
349
350  ( $success, $errorcode, $errormessage ) = RemoveItemFromCollection( $colId, $itemnumber );
351
352 Removes an item to a collection
353
354  Input:
355    $colId: Collection to add the item to.
356    $itemnumber: Item to be removed from collection
357
358  Output:
359    $success: 1 if all database operations were successful, 0 otherwise
360    $errorCode: Code for reason of failure, good for translating errors in templates
361    $errorMessage: English description of error
362
363 =cut
364
365 sub RemoveItemFromCollection {
366     my ( $colId, $itemnumber ) = @_;
367
368     ## Check for all neccessary parameters
369     if ( !$itemnumber ) {
370         return ( 0, 2, "No Itemnumber Given" );
371     }
372
373     if ( !isItemInThisCollection( $itemnumber, $colId ) ) {
374         return ( 0, 2, "Item is not in the collection!" );
375     }
376
377     my $dbh = C4::Context->dbh;
378
379     my $sth;
380     $sth = $dbh->prepare(
381         "DELETE FROM collections_tracking
382                         WHERE itemnumber = ?"
383     );
384     $sth->execute($itemnumber) or return ( 0, 3, $sth->errstr() );
385
386     return 1;
387 }
388
389 =head2 TransferCollection
390
391  ( $success, $errorcode, $errormessage ) = TransferCollection( $colId, $colBranchcode );
392
393 Transfers a collection to another branch
394
395  Input:
396    $colId: id of the collection to be updated
397    $colBranchcode: branch where collection is moving to
398
399  Output:
400    $success: 1 if all database operations were successful, 0 otherwise
401    $errorCode: Code for reason of failure, good for translating errors in templates
402    $errorMessage: English description of error
403
404 =cut
405
406 sub TransferCollection {
407     my ( $colId, $colBranchcode ) = @_;
408
409     ## Check for all neccessary parameters
410     if ( !$colId ) {
411         return ( 0, 1, "No Id Given" );
412     }
413     if ( !$colBranchcode ) {
414         return ( 0, 2, "No Branchcode Given" );
415     }
416
417     my $dbh = C4::Context->dbh;
418
419     my $sth;
420     $sth = $dbh->prepare(
421         "UPDATE collections
422                         SET 
423                         colBranchcode = ? 
424                         WHERE colId = ?"
425     );
426     $sth->execute( $colBranchcode, $colId ) or return ( 0, 4, $sth->errstr() );
427
428     $sth = $dbh->prepare(q{
429         SELECT items.itemnumber, items.barcode FROM collections_tracking
430         LEFT JOIN items ON collections_tracking.itemnumber = items.itemnumber
431         LEFT JOIN issues ON items.itemnumber = issues.itemnumber
432         WHERE issues.borrowernumber IS NULL
433           AND collections_tracking.colId = ?
434     });
435     $sth->execute($colId) or return ( 0, 4, $sth->errstr );
436     my @results;
437     while ( my $item = $sth->fetchrow_hashref ) {
438         transferbook( $colBranchcode, $item->{barcode},
439             my $ignore_reserves = 1 )
440           unless ( GetReserveStatus( $item->{itemnumber} ) eq "Waiting" );
441     }
442
443     return 1;
444
445 }
446
447 =head2 GetCollectionItemBranches
448
449   my ( $holdingBranch, $collectionBranch ) = GetCollectionItemBranches( $itemnumber );
450
451 =cut
452
453 sub GetCollectionItemBranches {
454     my ($itemnumber) = @_;
455
456     if ( !$itemnumber ) {
457         return;
458     }
459
460     my $dbh = C4::Context->dbh;
461
462     my ( $sth, @results );
463     $sth = $dbh->prepare(
464 "SELECT holdingbranch, colBranchcode FROM items, collections, collections_tracking
465                         WHERE items.itemnumber = collections_tracking.itemnumber
466                         AND collections.colId = collections_tracking.colId
467                         AND items.itemnumber = ?"
468     );
469     $sth->execute($itemnumber);
470
471     my $row = $sth->fetchrow_hashref;
472
473     return ( $$row{'holdingbranch'}, $$row{'colBranchcode'}, );
474 }
475
476 =head2 isItemInThisCollection
477
478   $inCollection = isItemInThisCollection( $itemnumber, $colId );
479
480 =cut
481
482 sub isItemInThisCollection {
483     my ( $itemnumber, $colId ) = @_;
484
485     my $dbh = C4::Context->dbh;
486
487     my $sth = $dbh->prepare(
488 "SELECT COUNT(*) as inCollection FROM collections_tracking WHERE itemnumber = ? AND colId = ?"
489     );
490     $sth->execute( $itemnumber, $colId ) or return (0);
491
492     my $row = $sth->fetchrow_hashref;
493
494     return $$row{'inCollection'};
495 }
496
497 =head2 isItemInAnyCollection
498
499 $inCollection = isItemInAnyCollection( $itemnumber );
500
501 =cut
502
503 sub isItemInAnyCollection {
504     my ($itemnumber) = @_;
505
506     my $dbh = C4::Context->dbh;
507
508     my $sth = $dbh->prepare(
509         "SELECT itemnumber FROM collections_tracking WHERE itemnumber = ?");
510     $sth->execute($itemnumber) or return (0);
511
512     my $row = $sth->fetchrow_hashref;
513
514     $itemnumber = $row->{itemnumber};
515     if ($itemnumber) {
516         return 1;
517     }
518     else {
519         return 0;
520     }
521 }
522
523 1;
524
525 __END__
526
527 =head1 AUTHOR
528
529 Kyle Hall <kylemhall@gmail.com>
530
531 =cut