LP1913807 Staff catalog shows preferred lib holdings counts
[evergreen-equinox.git] / Open-ILS / src / perlmods / lib / OpenILS / Application / Search / Biblio.pm
index 03ae377..9fe2500 100644 (file)
@@ -2887,8 +2887,9 @@ sub mk_copy_query {
     my $copy_offset = shift;
     my $pref_ou = shift;
     my $is_staff = shift;
+    my $base_query = shift;
 
-    my $query = $U->basic_opac_copy_query(
+    my $query = $base_query || $U->basic_opac_copy_query(
         $rec_id, undef, undef, $copy_limit, $copy_offset, $is_staff
     );
 
@@ -2912,6 +2913,16 @@ sub mk_copy_query {
                 }
             }
         }};
+
+        if ($pref_ou) {
+            # Make sure the pref OU is included in the results
+            my $in = $query->{from}->{acp}->[1]->{aou}->{filter}->{id}->{in};
+            delete $query->{from}->{acp}->[1]->{aou}->{filter}->{id};
+            $query->{from}->{acp}->[1]->{aou}->{filter}->{'-or'} = [
+                {id => {in => $in}},
+                {id => $pref_ou}
+            ];
+        }
     };
 
     # Unsure if we want these in the shared function, leaving here for now
@@ -2976,8 +2987,7 @@ sub record_urls {
 
         my $marc_doc = $U->marc_xml_to_doc($bib->marc);
 
-        for my $node ($marc_doc->findnodes(
-            '//*[@tag="856" and @ind1="4" and (@ind2="0" or @ind2="1")]')) {
+        for my $node ($marc_doc->findnodes('//*[@tag="856" and @ind1="4"]')) {
 
             # asset.uri's
             next if $node->findnodes('./*[@code="9" or @code="w" or @code="n"]');
@@ -2999,7 +3009,8 @@ sub record_urls {
                 push(@urls, {
                     href => $href,
                     label => ($first && $label) ?  $label->textContent : $href,
-                    note => ($first && $notes) ? $notes->textContent : ''
+                    note => ($first && $notes) ? $notes->textContent : '',
+                    ind2 => $node->getAttribute('ind2')
                 });
                 $first = 0;
             }
@@ -3057,8 +3068,10 @@ __PACKAGE__->register_method(
 
 
 sub catalog_record_summary {
-    my ($self, $client, $org_id, $record_ids) = @_;
+    my ($self, $client, $org_id, $record_ids, $options) = @_;
     my $e = new_editor();
+    $options ||= {};
+    my $pref_ou = $options->{pref_ou};
 
     my $is_meta = ($self->api_name =~ /metabib/);
     my $is_staff = ($self->api_name =~ /staff/);
@@ -3083,15 +3096,117 @@ sub catalog_record_summary {
 
         ($response->{copy_counts}) = $copy_method->run($org_id, $rec_id);
 
+        $response->{first_call_number} = get_first_call_number(
+            $e, $rec_id, $org_id, $is_staff, $is_meta, $options);
+
+        if ($pref_ou) {
+
+            # If we already have the pref ou copy counts, avoid the extra fetch.
+            my ($match) = 
+                grep {$_->{org_unit} eq $pref_ou} @{$response->{copy_counts}};
+
+            if (!$match) {
+                my ($counts) = $copy_method->run($pref_ou, $rec_id);
+                ($match) = grep {$_->{org_unit} eq $pref_ou} @$counts;
+            }
+
+            $response->{pref_ou_copy_counts} = $match;
+        }
+
         $response->{hold_count} = 
             $U->simplereq('open-ils.circ', $holds_method, $rec_id);
 
+        if ($options->{flesh_copies}) {
+            $response->{copies} = get_representative_copies(
+                $e, $rec_id, $org_id, $is_staff, $is_meta, $options);
+        }
+
         $client->respond($response);
     }
 
     return undef;
 }
 
+# Returns a snapshot of copy information for a given record or metarecord,
+# sorted by pref org and search org.
+sub get_representative_copies {
+    my ($e, $rec_id, $org_id, $is_staff, $is_meta, $options) = @_;
+
+    my @rec_ids;
+    my $limit = $options->{copy_limit};
+    my $copy_depth = $options->{copy_depth};
+    my $copy_offset = $options->{copy_offset};
+    my $pref_ou = $options->{pref_ou};
+
+    my $org_tree = $U->get_org_tree;
+    if (!$org_id) { $org_id = $org_tree->id; }
+    my $org = $U->find_org($org_tree, $org_id);
+
+    return [] unless $org;
+
+    my $func = 'unapi.biblio_record_entry_feed';
+    my $includes = '{holdings_xml,acp,acnp,acns}';
+    my $limits = "acn=>$limit,acp=>$limit";
+
+    if ($is_meta) {
+        $func = 'unapi.metabib_virtual_record_feed';
+        $includes = '{holdings_xml,acp,acnp,acns,mmr.unapi}';
+        $limits .= ",bre=>$limit";
+    }
+
+    my $xml_query = $e->json_query({from => [
+        $func, '{'.$rec_id.'}', 'marcxml', 
+        $includes, $org->shortname, $copy_depth, $limits,
+        undef, undef,undef, undef, undef, 
+        undef, undef, undef, $pref_ou
+    ]})->[0];
+
+    my $xml = $xml_query->{$func};
+
+    my $doc = XML::LibXML->new->parse_string($xml);
+
+    my $copies = [];
+    for my $volume ($doc->documentElement->findnodes('//*[local-name()="volume"]')) {
+        my $label = $volume->getAttribute('label');
+        my $prefix = $volume->getElementsByTagName('call_number_prefix')->[0]->getAttribute('label');
+        my $suffix = $volume->getElementsByTagName('call_number_suffix')->[0]->getAttribute('label');
+
+        my $copies_node = $volume->findnodes('./*[local-name()="copies"]')->[0];
+
+        for my $copy ($copies_node->findnodes('./*[local-name()="copy"]')) {
+
+            my $status = $copy->getElementsByTagName('status')->[0]->textContent;
+            my $location = $copy->getElementsByTagName('location')->[0]->textContent;
+            my $circ_lib_sn = $copy->getElementsByTagName('circ_lib')->[0]->getAttribute('shortname');
+
+            push(@$copies, {
+                call_number_label => $label,
+                call_number_prefix_label => $prefix,
+                call_number_suffix_label => $suffix,
+                circ_lib_sn => $circ_lib_sn,
+                copy_status => $status,
+                copy_location => $location
+            });
+        }
+    }
+
+    return $copies;
+}
+
+sub get_first_call_number {
+    my ($e, $rec_id, $org_id, $is_staff, $is_meta, $options) = @_;
+
+    my $limit = $options->{copy_limit};
+    $options->{copy_limit} = 1;
+
+    my $copies = get_representative_copies(
+        $e, $rec_id, $org_id, $is_staff, $is_meta, $options);
+
+    $options->{copy_limit} = $limit;
+
+    return $copies->[0];
+}
+
 sub get_one_rec_urls {
     my ($self, $e, $org_id, $bib_id) = @_;
 
@@ -3112,7 +3227,7 @@ sub get_one_metarecord_summary {
 
     my $bre_id = $meta->master_record; 
 
-    my $response = get_one_record_summary($e, $org_id, $bre_id);
+    my $response = get_one_record_summary($self, $e, $org_id, $bre_id);
     $response->{urls} = get_one_rec_urls($self, $e, $org_id, $bre_id);
 
     $response->{metabib_id} = $rec_id;