adding holdings data to marcxml/htmlcard output
authormiker <miker@dcc99617-32d9-48b4-a31d-7c20da2025e4>
Tue, 6 Jun 2006 02:54:08 +0000 (02:54 +0000)
committermiker <miker@dcc99617-32d9-48b4-a31d-7c20da2025e4>
Tue, 6 Jun 2006 02:54:08 +0000 (02:54 +0000)
git-svn-id: svn://svn.open-ils.org/ILS/trunk@4513 dcc99617-32d9-48b4-a31d-7c20da2025e4

Open-ILS/src/perlmods/OpenILS/Application/SuperCat.pm
Open-ILS/src/perlmods/OpenILS/WWW/SuperCat.pm
Open-ILS/src/perlmods/OpenILS/WWW/SuperCat/Feed.pm
Open-ILS/xsl/MARC21slim2HTMLCard.xsl

index becceb3..b85aaa0 100644 (file)
@@ -168,6 +168,107 @@ sub entityize {
        return $stuff;
 }
 
+sub new_record_holdings {
+       my $self = shift;
+       my $client = shift;
+       my $bib = shift;
+       my $ou = shift;
+
+       my $_storage = OpenSRF::AppSession->create( 'open-ils.storage' );
+       my $_cstore = OpenSRF::AppSession->create( 'open-ils.cstore' );
+
+       my $tree = $_cstore->request(
+               "open-ils.cstore.direct.biblio.record_entry.retrieve",
+               $bib,
+               {flesh => 3, flesh_fields => [qw/call_numbers copies location status owning_lib circ_lib/] }
+       )->gather(1);
+
+       my ($year,$month,$day) = reverse( (localtime)[3,4,5] );
+       $year += 1900;
+       $month += 1;
+
+       my $xml = "<hold:volumes xmlns:hold='http://open-ils.org/spec/holdings/v1'>";
+
+       for my $cn (@{$tree->call_numbers}) {
+
+               if ($ou ne '-') {
+                       next unless grep {$_->circ_lib->shortname =~ /^$ou/} @{$cn->copies};
+               }
+
+               (my $cn_class = $cn->class_name) =~ s/::/-/gso;
+               $cn_class =~ s/Fieldmapper-//gso;
+               my $cn_tag = sprintf("tag:open-ils.org,$year-\%0.2d-\%0.2d:$cn_class/".$cn->id, $month, $day);
+
+               my $cn_lib = $cn->owning_lib->shortname;
+
+               my $cn_label = $cn->label;
+
+               $xml .= "<hold:volume id='$cn_tag' lib='$cn_lib' label='$cn_label'><hold:copies>";
+               
+               for my $cp (@{$cn->copies}) {
+
+                       if ($ou ne '-') {
+                               next unless $cp->circ_lib->shortname =~ /^$ou/;
+                       }
+
+                       (my $cp_class = $cp->class_name) =~ s/::/-/gso;
+                       $cp_class =~ s/Fieldmapper-//gso;
+                       my $cp_tag = sprintf("tag:open-ils.org,$year-\%0.2d-\%0.2d:$cp_class/".$cp->id, $month, $day);
+
+                       my $cp_stat = $cp->status->name;
+
+                       my $cp_loc = $cp->location->name;
+
+                       my $cp_lib = $cp->circ_lib->shortname;
+
+                       my $cp_bc = $cp->barcode;
+
+                       $xml .= "<hold:copy id='$cp_tag' barcode='$cp_bc'><hold:status>$cp_stat</hold:status><hold:location>$cp_loc</hold:location><hold:circlib>$cp_lib</hold:circlib><hold:notes>";
+
+                       #for my $note ( @{$_storage->request( "open-ils.storage.direct.asset.copy_note.search.atomic" => {id => $cp->id, pub => "t" })->gather(1)} ) {
+                       #       $xml .= sprintf('<hold:note date="%s" title="%s">%s</hold:note>',$note->create_date, escape($note->title), escape($note->value));
+                       #}
+
+                       $xml .= "</hold:notes><hold:statcats>";
+
+                       #for my $sce ( @{$_storage->request( "open-ils.storage.direct.asset.stat_cat_entry_copy_map.search.atomic" => { owning_copy => $cp->id })->gather(1)} ) {
+                       #       my $sc = $holdings_data_cache{statcat}{$sce->stat_cat_entry};
+                       #       $xml .= sprintf('<hold:statcat>%s</hold:statcat>',escape($sc->value));
+                       #}
+
+                       $xml .= "</hold:statcats></hold:copy>";
+               }
+               
+               $xml .= "</hold:copies></hold:volume>";
+       }
+
+       $xml .= "</hold:volumes>";
+
+       return $xml;
+}
+__PACKAGE__->register_method(
+       method    => 'new_record_holdings',
+       api_name  => 'open-ils.supercat.record.holdings_xml.retrieve',
+       api_level => 1,
+       argc      => 1,
+       signature =>
+               { desc     => <<"                 DESC",
+Returns the XML representation of the requested bibliographic record's holdings
+                 DESC
+                 params   =>
+                       [
+                               { name => 'bibId',
+                                 desc => 'An OpenILS biblio::record_entry id',
+                                 type => 'number' },
+                       ],
+                 'return' =>
+                       { desc => 'The bib record holdings hierarchy in XML',
+                         type => 'string' }
+               }
+);
+
+
+
 sub record_holdings {
        my $self = shift;
        my $client = shift;
@@ -246,27 +347,6 @@ sub record_holdings {
 
        return $xml;
 }
-__PACKAGE__->register_method(
-       method    => 'record_holdings',
-       api_name  => 'open-ils.supercat.record.holdings_xml.retrieve',
-       api_level => 1,
-       argc      => 1,
-       signature =>
-               { desc     => <<"                 DESC",
-Returns the XML representation of the requested bibliographic record's holdings
-                 DESC
-                 params   =>
-                       [
-                               { name => 'bibId',
-                                 desc => 'An OpenILS biblio::record_entry id',
-                                 type => 'number' },
-                       ],
-                 'return' =>
-                       { desc => 'The bib record holdings hierarchy in XML',
-                         type => 'string' }
-               }
-);
-
 
 sub escape {
        my $text = shift;
index b1fbdff..82840ea 100644 (file)
@@ -93,13 +93,14 @@ sub unapi {
        my $host = $cgi->virtual_host || $cgi->server_name;
 
        my $format = $cgi->param('format');
-       my ($id,$type,$command) = ('','','');
+       my ($id,$type,$command,$lib) = ('','','');
 
        if (!$format) {
                print "Content-type: application/xml; charset=utf-8\n";
        
                if ($uri =~ m{^tag:[^:]+:([^\/]+)/(\d+)}o) {
                        $id = $2;
+                       $lib = $3;
                        $type = 'record';
                        $type = 'metarecord' if ($1 =~ /^m/o);
 
@@ -163,8 +164,9 @@ sub unapi {
        }
 
                
-       if ($uri =~ m{^tag:[^:]+:([^\/]+)/(\d+)}o) {
+       if ($uri =~ m{^tag:[^:]+:([^\/]+)/(\d+)(?:/(.+))?}o) {
                $id = $2;
+               $lib = $3;
                $type = 'record';
                $type = 'metarecord' if ($1 =~ /^m/o);
                $command = 'retrieve';
@@ -176,10 +178,12 @@ sub unapi {
                print "Location: $root/../../en-US/skin/default/xml/rdetail.xml?r=$id\n\n"
                        if ($type eq 'record');
                return 302;
-       } elsif ($format =~ /^html/o) {
+       } else {
+       #} elsif ($format =~ /^html/o) {
                my $feed = create_record_feed(
                        $format => [ $id ],
                        $base,
+                       $lib,
                );
 
                $feed->root($root);
@@ -663,6 +667,7 @@ sub opensearch_feed {
                $type,
                [ map { $_->[0] } @{$recs->{ids}}[$offset .. $offset + $limit - 1] ],
                $unapi,
+               $org
        );
        $feed->root($root);
        $feed->lib($org);
@@ -743,6 +748,8 @@ sub create_record_feed {
        my $records = shift;
        my $unapi = shift;
 
+       my $lib = shift || '';
+
        my $cgi = new CGI;
        my $base = $cgi->url;
        my $host = $cgi->virtual_host || $cgi->server_name;
@@ -759,7 +766,7 @@ sub create_record_feed {
        for my $rec (@$records) {
                next unless($rec);
 
-               my $item_tag = "tag:$host,$year:biblio-record_entry/" . $rec;
+               my $item_tag = "tag:$host,$year:biblio-record_entry/$rec/$lib";
 
 
                my $xml = $supercat->request(
@@ -769,8 +776,13 @@ sub create_record_feed {
 
                my $node = $feed->add_item($xml);
 
+               if ($lib && $type eq 'marcxml') {
+                       $xml = $supercat->request( "open-ils.supercat.record.holdings_xml.retrieve", $rec, $lib )->gather(1);
+                       $node->add_holdings($xml);
+               }
+
                $node->id($item_tag);
-               $node->link(alternate => $feed->unapi . "?id=$item_tag&format=opac" => 'text/html');
+               $node->link(alternate => $feed->unapi . "?id=$item_tag&format=htmlcard" => 'text/html');
                $node->link(opac => $feed->unapi . "?id=$item_tag&format=opac");
                $node->link(unapi => $feed->unapi . "?id=$item_tag");
                $node->link('unapi-id' => $item_tag);
index 80a3aba..ffd86db 100644 (file)
@@ -136,6 +136,20 @@ sub add_item {
        return $entry;
 }
 
+sub add_holdings {
+       my $self = shift;
+       my $holdings_xml = shift;
+
+       $parser = new XML::LibXML if (!$parser);
+       my $new_doc = $parser->parse_string($holdings_xml);
+
+       for my $root ( $self->{doc}->findnodes($self->{holdings_xpath}) ) {
+               $root->appendChild($new_doc->documentElement);
+               last;
+       }
+       return $self;
+}
+
 sub composeDoc {
        my $self = shift;
        for my $root ( $self->{doc}->findnodes($self->{item_xpath}) ) {
@@ -228,6 +242,7 @@ sub new {
        my $self = $class->SUPER::build($xml);
        $self->{doc}->documentElement->setNamespace('http://www.w3.org/2005/Atom', 'atom');
        $self->{item_xpath} = '/atom:entry';
+       $self->{holdings_xpath} = '/atom:entry';
        $self->{type} = 'application/xml';
        return $self;
 }
@@ -292,6 +307,7 @@ sub new {
        my $self = $class->SUPER::build($xml);
        $self->{type} = 'application/xml';
        $self->{item_xpath} = '/item';
+       $self->{holdings_xpath} = '/item';
        return $self;
 }
 
@@ -318,6 +334,7 @@ sub new {
        my $self = $class->SUPER::build($xml);
        $self->{doc}->documentElement->setNamespace('http://www.loc.gov/mods/', 'mods');
        $self->{type} = 'application/xml';
+       $self->{holdings_xpath} = '/mods:mods';
        return $self;
 }
 
@@ -369,6 +386,7 @@ sub new {
        my $self = $class->SUPER::build($xml);
        $self->{doc}->documentElement->setNamespace('http://www.loc.gov/mods/v3', 'mods');
        $self->{type} = 'application/xml';
+       $self->{holdings_xpath} = '/mods:mods';
        return $self;
 }
 
@@ -395,6 +413,7 @@ sub new {
        my $self = $class->SUPER::build($xml);
        $self->{doc}->documentElement->setNamespace('http://www.loc.gov/MARC21/slim', 'marc');
        $self->{type} = 'application/xml';
+       $self->{holdings_xpath} = '/marc:record';
        return $self;
 }
 
index 4bcb087..5ac8c4c 100755 (executable)
@@ -3,7 +3,8 @@
 <xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
   xmlns="http://www.w3.org/1999/xhtml"
   xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
-  xmlns:marc="http://www.loc.gov/MARC21/slim" 
+  xmlns:marc="http://www.loc.gov/MARC21/slim"
+  xmlns:hold="http://open-ils.org/spec/holdings/v1"
   version="1.0">
   <xsl:output method="html" doctype-public="-//W3C/DTD HTML 4.01 Transitional//EN" doctype-system="http://www.w3.org/TR/html4/strict.dtd" />    
   <xsl:template match="/">
      </span>
     </div>
     <br/>
+    <u>Holdings</u>
+    <xsl:apply-templates select="hold:volumes"/>
+    <br/>
   </xsl:template>
-      
+
+  <xsl:template match="hold:volumes">
+    <ul>
+    <xsl:apply-templates select="hold:volume">
+      <xsl:sort select="@lib"/>
+    </xsl:apply-templates>
+    </ul>
+  </xsl:template>
+
+  <xsl:template match="hold:volume">
+      <li> <b><xsl:value-of select="./@label"/></b>
+        <xsl:apply-templates select="hold:copies"/>
+      </li>
+  </xsl:template>
+
+  <xsl:template match="hold:copies">
+    <ul>
+    <xsl:apply-templates select="hold:copy">
+      <xsl:sort select="hold:location"/>
+    </xsl:apply-templates>
+    </ul>
+  </xsl:template>
+
+  <xsl:template match="hold:copy">
+      <li> <xsl:value-of select="./@barcode"/>
+        <ul>
+         <li>Circulating from <b><xsl:value-of select="hold:circlib"/></b></li>
+         <li>Located at <b><xsl:value-of select="hold:location"/></b></li>
+         <li>Status is <b><xsl:value-of select="hold:status"/></b></li>
+       </ul>
+      </li>
+  </xsl:template>
+
   <xsl:template match="marc:controlfield">
       <span class="oclc">#<xsl:value-of select="substring(.,4)"/></span>
   </xsl:template>