Merge remote-tracking branch 'kc/new/bug_5995' into kcmaster
[koha.git] / C4 / Search.pm
index 81f66f4..98db887 100644 (file)
@@ -30,6 +30,8 @@ use C4::XSLT;
 use C4::Branch;
 use C4::Reserves;    # CheckReserves
 use C4::Debug;
+use C4::Items;
+use YAML;
 use URI::Escape;
 
 use vars qw($VERSION @ISA @EXPORT @EXPORT_OK %EXPORT_TAGS $DEBUG);
@@ -357,10 +359,10 @@ sub getRecords {
         # Note: sort will override rank
         my $sort_by;
         foreach my $sort (@sort_by) {
-            if ( $sort eq "author_az" ) {
+            if ( $sort eq "author_az" || $sort eq "author_asc" ) {
                 $sort_by .= "1=1003 <i ";
             }
-            elsif ( $sort eq "author_za" ) {
+            elsif ( $sort eq "author_za" || $sort eq "author_dsc" ) {
                 $sort_by .= "1=1003 >i ";
             }
             elsif ( $sort eq "popularity_asc" ) {
@@ -387,10 +389,10 @@ sub getRecords {
             elsif ( $sort eq "acqdate_dsc" ) {
                 $sort_by .= "1=32 >i ";
             }
-            elsif ( $sort eq "title_az" ) {
+            elsif ( $sort eq "title_az" || $sort eq "title_asc" ) {
                 $sort_by .= "1=4 <i ";
             }
-            elsif ( $sort eq "title_za" ) {
+            elsif ( $sort eq "title_za" || $sort eq "title_dsc" ) {
                 $sort_by .= "1=4 >i ";
             }
             else {
@@ -840,6 +842,7 @@ sub getIndexes{
                     'Authority-Number',
                     'authtype',
                     'bc',
+                   'Bib-level',
                     'biblionumber',
                     'bio',
                     'biography',
@@ -870,6 +873,7 @@ sub getIndexes{
                     'Date-of-acquisition',
                     'Date-of-publication',
                     'Dewey-classification',
+                    'EAN',
                     'extent',
                     'fic',
                     'fiction',
@@ -907,6 +911,7 @@ sub getIndexes{
                     'mc-rtype',
                     'mus',
                     'name',
+                    'Music-number',
                     'Name-geographic',
                     'Name-geographic-heading',
                     'Name-geographic-see',
@@ -948,6 +953,7 @@ sub getIndexes{
                     'su-to',
                     'su-ut',
                     'ut',
+                    'UPC',
                     'Term-genre-form',
                     'Term-genre-form-heading',
                     'Term-genre-form-see',
@@ -1066,15 +1072,14 @@ sub buildQuery {
 
     my $stopwords_removed;    # flag to determine if stopwords have been removed
 
-    my $cclq;
+    my $cclq       = 0;
     my $cclindexes = getIndexes();
-    if( $query !~ /\s*ccl=/ ){
-        for my $index (@$cclindexes){
-            if($query =~ /($index)(,?\w)*[:=]/){
-                $cclq = 1;
-            }
+    if ( $query !~ /\s*ccl=/ ) {
+        while ( !$cclq && $query =~ /(?:^|\W)(\w+)(,\w+)*[:=]/g ) {
+            my $dx = lc($1);
+            $cclq = grep { lc($_) eq $dx } @$cclindexes;
         }
-        $query = "ccl=$query" if($cclq);
+        $query = "ccl=$query" if $cclq;
     }
 
 # for handling ccl, cql, pqf queries in diagnostic mode, skip the rest of the steps
@@ -1554,6 +1559,33 @@ sub searchResults {
 
         # Pull out the items fields
         my @fields = $marcrecord->field($itemtag);
+        my $marcflavor = C4::Context->preference("marcflavour");
+        # adding linked items that belong to host records
+        my $analyticsfield = '773';
+        if ($marcflavor eq 'MARC21' || $marcflavor eq 'NORMARC') {
+            $analyticsfield = '773';
+        } elsif ($marcflavor eq 'UNIMARC') {
+            $analyticsfield = '461';
+        }
+        foreach my $hostfield ( $marcrecord->field($analyticsfield)) {
+            my $hostbiblionumber = $hostfield->subfield("0");
+            my $linkeditemnumber = $hostfield->subfield("9");
+            if(!$hostbiblionumber eq undef){
+                my $hostbiblio = GetMarcBiblio($hostbiblionumber, 1);
+                my ($itemfield, undef) = GetMarcFromKohaField( 'items.itemnumber', GetFrameworkCode($hostbiblionumber) );
+                if(!$hostbiblio eq undef){
+                    my @hostitems = $hostbiblio->field($itemfield);
+                    foreach my $hostitem (@hostitems){
+                        if ($hostitem->subfield("9") eq $linkeditemnumber){
+                            my $linkeditem =$hostitem;
+                            # append linked items if they exist
+                            if (!$linkeditem eq undef){
+                                push (@fields, $linkeditem);}
+                        }
+                    }
+                }
+            }
+        }
 
         # Setting item statuses for display
         my @available_items_loop;
@@ -1591,8 +1623,14 @@ sub searchResults {
                 $item->{$code} = $field->subfield( $subfieldstosearch{$code} );
             }
 
-                       my $hbranch     = C4::Context->preference('HomeOrHoldingBranch') eq 'homebranch' ? 'homebranch'    : 'holdingbranch';
-                       my $otherbranch = C4::Context->preference('HomeOrHoldingBranch') eq 'homebranch' ? 'holdingbranch' : 'homebranch';
+               # Hidden items
+               my @items = ($item);
+               my (@hiddenitems) = GetHiddenItemnumbers(@items);
+           $item->{'hideatopac'} = 1 if (@hiddenitems); 
+
+            my $hbranch     = C4::Context->preference('HomeOrHoldingBranch') eq 'homebranch' ? 'homebranch'    : 'holdingbranch';
+            my $otherbranch = C4::Context->preference('HomeOrHoldingBranch') eq 'homebranch' ? 'holdingbranch' : 'homebranch';
+
             # set item's branch name, use HomeOrHoldingBranch syspref first, fall back to the other one
             if ($item->{$hbranch}) {
                 $item->{'branchname'} = $branches{$item->{$hbranch}};
@@ -1660,11 +1698,12 @@ sub searchResults {
                    ($reservestatus, $reserveitem) = C4::Reserves::CheckReserves($item->{itemnumber});
                 }
 
-                # item is withdrawn, lost or damaged
+                # item is withdrawn, lost, damaged, not for loan, reserved or in transit
                 if (   $item->{wthdrawn}
                     || $item->{itemlost}
                     || $item->{damaged}
                     || $item->{notforloan} > 0
+                    || $item->{hideatopac}
                    || $reservestatus eq 'Waiting'
                     || ($transfertwhen ne ''))
                 {
@@ -1674,13 +1713,22 @@ sub searchResults {
                     $item_in_transit_count++ if $transfertwhen ne '';
                    $item_onhold_count++     if $reservestatus eq 'Waiting';
                     $item->{status} = $item->{wthdrawn} . "-" . $item->{itemlost} . "-" . $item->{damaged} . "-" . $item->{notforloan};
+                    
+                    # can place hold on item ?
+                    if ((!$item->{damaged} || C4::Context->preference('AllowHoldsOnDamagedItems'))
+                      && !$item->{itemlost}
+                      && !$item->{withdrawn}
+                    ) {
+                        $can_place_holds = 1;
+                    }
+                    
                     $other_count++;
 
-                                       my $key = $prefix . $item->{status};
-                                       foreach (qw(wthdrawn itemlost damaged branchname itemcallnumber)) {
-                       $other_items->{$key}->{$_} = $item->{$_};
-                                       }
-                    $other_items->{$key}->{intransit} = ($transfertwhen ne '') ? 1 : 0;
+                    my $key = $prefix . $item->{status};
+                    foreach (qw(wthdrawn itemlost damaged branchname itemcallnumber hideatopac)) {
+                        $other_items->{$key}->{$_} = $item->{$_};
+                    }
+                    $other_items->{$key}->{intransit} = ( $transfertwhen ne '' ) ? 1 : 0;
                     $other_items->{$key}->{onhold} = ($reservestatus) ? 1 : 0;
                                        $other_items->{$key}->{notforloan} = GetAuthorisedValueDesc('','',$item->{notforloan},'','',$notforloan_authorised_value) if $notforloan_authorised_value;
                                        $other_items->{$key}->{count}++ if $item->{$hbranch};
@@ -1692,7 +1740,7 @@ sub searchResults {
                     $can_place_holds = 1;
                     $available_count++;
                                        $available_items->{$prefix}->{count}++ if $item->{$hbranch};
-                                       foreach (qw(branchname itemcallnumber)) {
+                                       foreach (qw(branchname itemcallnumber hideatopac)) {
                        $available_items->{$prefix}->{$_} = $item->{$_};
                                        }
                                        $available_items->{$prefix}->{location} = $shelflocations->{ $item->{location} };
@@ -2274,7 +2322,7 @@ sub NZorder {
     # sort the hash and return the same structure as GetRecords (Zebra querying)
         my $result_hash;
         my $numbers = 0;
-        if ( $ordering eq 'author_za' ) {    # sort by author desc
+        if ( $ordering eq 'author_za' || $ordering eq 'author_dsc' ) {    # sort by author desc
             foreach my $key ( sort { $b cmp $a } ( keys %result ) ) {
                 $result_hash->{'RECORDS'}[ $numbers++ ] =
                   $result{$key}->as_usmarc();