memoize GetMarcStructure
[koha.git] / C4 / Biblio.pm
index 96baaef..a24079d 100644 (file)
@@ -78,6 +78,7 @@ BEGIN {
       &GetMarcBiblio
       &GetMarcAuthors
       &GetMarcSeries
+      &GetMarcHosts
       GetMarcUrls
       &GetUsedMarcStructure
       &GetXmlBiblio
@@ -90,8 +91,12 @@ BEGIN {
       &GetMarcFromKohaField
       &GetFrameworkCode
       &TransformKohaToMarc
+      &PrepHostMarcField
 
       &CountItemsIssued
+      &CountBiblioInOrders
+      &GetSubscriptionsId
+      &GetHolds
     );
 
     # To modify something
@@ -145,6 +150,9 @@ eval {
     }
 };
 
+use Memoize;
+memoize('GetMarcStructure');
+
 =head1 NAME
 
 C4::Biblio - cataloging management functions
@@ -1070,9 +1078,9 @@ sub GetMarcBiblio {
         if ($@) { warn " problem with :$biblionumber : $@ \n$marcxml"; }
         return unless $record;
 
+        C4::Biblio::_koha_marc_update_bib_ids($record, '', $biblionumber, $biblionumber);
        C4::Biblio::EmbedItemsInMarcBiblio($record, $biblionumber) if ($embeditems);
 
-        #      $record = MARC::Record::new_from_usmarc( $marc) if $marc;
         return $record;
     } else {
         return undef;
@@ -1217,7 +1225,8 @@ sub GetCOinSBiblio {
         $subtitle = $record->subfield( '245', 'b' ) || '';
         $title .= $subtitle;
         if ($titletype eq 'a') {
-            $pubyear   = substr $record->field('008')->data(), 7, 4;
+            $pubyear   = $record->field('008') || '';
+            $pubyear   = substr($pubyear->data(), 7, 4) if $pubyear;
             $isbn      = $record->subfield( '773', 'z' ) || '';
             $issn      = $record->subfield( '773', 'x' ) || '';
             if ($mtx eq 'journal') {
@@ -1332,6 +1341,8 @@ descriptions rather than normal ones when they exist.
 
 =cut
 
+my $_auth_val;
+
 sub GetAuthorisedValueDesc {
     my ( $tag, $subfield, $value, $framework, $tagslib, $category, $opac ) = @_;
     my $dbh = C4::Context->dbh;
@@ -1355,9 +1366,16 @@ sub GetAuthorisedValueDesc {
     }
 
     if ( $category ne "" ) {
-        my $sth = $dbh->prepare( "SELECT lib, lib_opac FROM authorised_values WHERE category = ? AND authorised_value = ?" );
-        $sth->execute( $category, $value );
-        my $data = $sth->fetchrow_hashref;
+
+       my $data;
+
+       if ( $data = $_auth_val->{$category}->{$value} ) {
+warn "XXX auth_val hit: $category $value\n";
+       } else {
+               my $sth = $dbh->prepare( "SELECT lib, lib_opac FROM authorised_values WHERE category = ? AND authorised_value = ?" );
+               $sth->execute( $category, $value );
+               $_auth_val->{$category}->{$value} = $data = $sth->fetchrow_hashref;
+       }
         return ( $opac && $data->{'lib_opac'} ) ? $data->{'lib_opac'} : $data->{'lib'};
     } else {
         return $value;    # if nothing is found return the original value
@@ -1760,19 +1778,70 @@ sub GetMarcSeries {
     return $marcseriessarray;
 }    #end getMARCseriess
 
+=head2 GetMarcHosts
+
+  $marchostsarray = GetMarcHosts($record,$marcflavour);
+
+Get all host records (773s MARC21, 461 UNIMARC) from the MARC record and returns them in an array.
+
+=cut
+
+sub GetMarcHosts {
+    my ( $record, $marcflavour ) = @_;
+    my ( $tag,$title_subf,$bibnumber_subf,$itemnumber_subf);
+    $marcflavour ||="MARC21";
+    if ( $marcflavour eq "MARC21" || $marcflavour eq "NORMARC" ) {
+        $tag = "773";
+        $title_subf = "t";
+        $bibnumber_subf ="0";
+        $itemnumber_subf='9';
+    }
+    elsif ($marcflavour eq "UNIMARC") {
+        $tag = "461";
+        $title_subf = "t";
+        $bibnumber_subf ="0";
+        $itemnumber_subf='9';
+    };
+
+    my @marchosts;
+
+    foreach my $field ( $record->field($tag)) {
+
+        my @fields_loop;
+
+        my $hostbiblionumber = $field->subfield("$bibnumber_subf");
+        my $hosttitle = $field->subfield($title_subf);
+        my $hostitemnumber=$field->subfield($itemnumber_subf);
+        push @fields_loop, { hostbiblionumber => $hostbiblionumber, hosttitle => $hosttitle, hostitemnumber => $hostitemnumber};
+        push @marchosts, { MARCHOSTS_FIELDS_LOOP => \@fields_loop };
+
+        }
+    my $marchostsarray = \@marchosts;
+    return $marchostsarray;
+}
+
 =head2 GetFrameworkCode
 
   $frameworkcode = GetFrameworkCode( $biblionumber )
 
 =cut
 
+our $_frameworkcode;
+
 sub GetFrameworkCode {
     my ($biblionumber) = @_;
+
+    my $frameworkcode;
+    if ( $frameworkcode = $_frameworkcode->{$biblionumber} ) {
+warn "# _frameworkcode hit $biblionumber\n";
+       return $frameworkcode;
+    }
+
     my $dbh            = C4::Context->dbh;
     my $sth            = $dbh->prepare("SELECT frameworkcode FROM biblio WHERE biblionumber=?");
     $sth->execute($biblionumber);
     my ($frameworkcode) = $sth->fetchrow;
-    return $frameworkcode;
+    return $_frameworkcode->{$biblionumber} = $frameworkcode;
 }
 
 =head2 TransformKohaToMarc
@@ -1797,6 +1866,86 @@ sub TransformKohaToMarc {
     return $record;
 }
 
+=head2 PrepHostMarcField
+
+    $hostfield = PrepHostMarcField ( $hostbiblionumber,$hostitemnumber,$marcflavour )
+
+This function returns a host field populated with data from the host record, the field can then be added to an analytical record
+
+=cut
+
+sub PrepHostMarcField {
+    my ($hostbiblionumber,$hostitemnumber, $marcflavour) = @_;
+    $marcflavour ||="MARC21";
+    
+    my $hostrecord = GetMarcBiblio($hostbiblionumber);
+       my $item = C4::Items::GetItem($hostitemnumber);
+       
+       my $hostmarcfield;
+    if ( $marcflavour eq "MARC21" || $marcflavour eq "NORMARC" ) {
+       
+        #main entry
+        my $mainentry;
+        if ($hostrecord->subfield('100','a')){
+            $mainentry = $hostrecord->subfield('100','a');
+        } elsif ($hostrecord->subfield('110','a')){
+            $mainentry = $hostrecord->subfield('110','a');
+        } else {
+            $mainentry = $hostrecord->subfield('111','a');
+        }
+       
+        # qualification info
+        my $qualinfo;
+        if (my $field260 = $hostrecord->field('260')){
+            $qualinfo =  $field260->as_string( 'abc' );
+        }
+       
+
+       #other fields
+        my $ed = $hostrecord->subfield('250','a');
+        my $barcode = $item->{'barcode'};
+        my $title = $hostrecord->subfield('245','a');
+
+        # record control number, 001 with 003 and prefix
+        my $recctrlno;
+        if ($hostrecord->field('001')){
+            $recctrlno = $hostrecord->field('001')->data();
+            if ($hostrecord->field('003')){
+                $recctrlno = '('.$hostrecord->field('003')->data().')'.$recctrlno;
+            }
+        }
+
+        # issn/isbn
+        my $issn = $hostrecord->subfield('022','a');
+        my $isbn = $hostrecord->subfield('020','a');
+
+
+        $hostmarcfield = MARC::Field->new(
+                773, '0', '',
+                '0' => $hostbiblionumber,
+                '9' => $hostitemnumber,
+                'a' => $mainentry,
+                'b' => $ed,
+                'd' => $qualinfo,
+                'o' => $barcode,
+                't' => $title,
+                'w' => $recctrlno,
+                'x' => $issn,
+                'z' => $isbn
+                );
+    } elsif ($marcflavour eq "UNIMARC") {
+        $hostmarcfield = MARC::Field->new(
+            461, '', '',
+            '0' => $hostbiblionumber,
+            't' => $hostrecord->subfield('200','a'), 
+            '9' => $hostitemnumber
+        );     
+    };
+
+    return $hostmarcfield;
+}
+
+
 =head2 TransformKohaToMarcOneField
 
     $record = TransformKohaToMarcOneField( $sth, $record, $kohafieldname, $value, $frameworkcode );
@@ -1989,8 +2138,8 @@ sub _default_ind_to_space {
 
 =head2 TransformHtmlToMarc
 
-    L<$record> = TransformHtmlToMarc(L<$params>,L<$cgi>)
-    L<$params> is a ref to an array as below:
+    L<$record> = TransformHtmlToMarc(L<$cgi>)
+    L<$cgi> is the CGI object which containts the values for subfields
     {
         'tag_010_indicator1_531951' ,
         'tag_010_indicator2_531951' ,
@@ -2007,15 +2156,15 @@ sub _default_ind_to_space {
         'tag_200_code_f_873510_110730' ,
         'tag_200_subfield_f_873510_110730' ,
     }
-    L<$cgi> is the CGI object which containts the value.
     L<$record> is the MARC::Record object.
 
 =cut
 
 sub TransformHtmlToMarc {
-    my $params = shift;
     my $cgi    = shift;
 
+    my @params = $cgi->param();
+
     # explicitly turn on the UTF-8 flag for all
     # 'tag_' parameters to avoid incorrect character
     # conversion later on
@@ -2035,8 +2184,8 @@ sub TransformHtmlToMarc {
     my $record = MARC::Record->new();
     my $i      = 0;
     my @fields;
-    while ( $params->[$i] ) {    # browse all CGI params
-        my $param    = $params->[$i];
+    while ( $params[$i] ) {    # browse all CGI params
+        my $param    = $params[$i];
         my $newfield = 0;
 
         # if we are on biblionumber, store it in the MARC::Record (it may not be in the edited fields)
@@ -2052,7 +2201,7 @@ sub TransformHtmlToMarc {
             my $tag = $1;
 
             my $ind1 = _default_ind_to_space( substr( $cgi->param($param), 0, 1 ) );
-            my $ind2 = _default_ind_to_space( substr( $cgi->param( $params->[ $i + 1 ] ), 0, 1 ) );
+            my $ind2 = _default_ind_to_space( substr( $cgi->param( $params[ $i + 1 ] ), 0, 1 ) );
             $newfield = 0;
             my $j = $i + 2;
 
@@ -2062,27 +2211,27 @@ sub TransformHtmlToMarc {
                     # Force a fake leader even if not provided to avoid crashing
                     # during decoding MARC record containing UTF-8 characters
                     $record->leader(
-                        length( $cgi->param($params->[$j+1]) ) == 24
-                        ? $cgi->param( $params->[ $j + 1 ] )
+                        length( $cgi->param($params[$j+1]) ) == 24
+                        ? $cgi->param( $params[ $j + 1 ] )
                         : '     nam a22        4500'
                        )
                     ;
                     # between 001 and 009 (included)
-                } elsif ( $cgi->param( $params->[ $j + 1 ] ) ne '' ) {
-                    $newfield = MARC::Field->new( $tag, $cgi->param( $params->[ $j + 1 ] ), );
+                } elsif ( $cgi->param( $params[ $j + 1 ] ) ne '' ) {
+                    $newfield = MARC::Field->new( $tag, $cgi->param( $params[ $j + 1 ] ), );
                 }
 
                 # > 009, deal with subfields
             } else {
-                while ( defined $params->[$j] && $params->[$j] =~ /_code_/ ) {    # browse all it's subfield
-                    my $inner_param = $params->[$j];
+                while ( defined $params[$j] && $params[$j] =~ /_code_/ ) {    # browse all it's subfield
+                    my $inner_param = $params[$j];
                     if ($newfield) {
-                        if ( $cgi->param( $params->[ $j + 1 ] ) ne '' ) {         # only if there is a value (code => value)
-                            $newfield->add_subfields( $cgi->param($inner_param) => $cgi->param( $params->[ $j + 1 ] ) );
+                        if ( $cgi->param( $params[ $j + 1 ] ) ne '' ) {         # only if there is a value (code => value)
+                            $newfield->add_subfields( $cgi->param($inner_param) => $cgi->param( $params[ $j + 1 ] ) );
                         }
                     } else {
-                        if ( $cgi->param( $params->[ $j + 1 ] ) ne '' ) {         # creating only if there is a value (code => value)
-                            $newfield = MARC::Field->new( $tag, $ind1, $ind2, $cgi->param($inner_param) => $cgi->param( $params->[ $j + 1 ] ), );
+                        if ( $cgi->param( $params[ $j + 1 ] ) ne '' ) {         # creating only if there is a value (code => value)
+                            $newfield = MARC::Field->new( $tag, $ind1, $ind2, $cgi->param($inner_param) => $cgi->param( $params[ $j + 1 ] ), );
                         }
                     }
                     $j += 2;
@@ -2730,7 +2879,7 @@ sub EmbedItemsInMarcBiblio {
         my $item_marc = C4::Items::GetMarcItem($biblionumber, $itemnumber);
         push @item_fields, $item_marc->field($itemtag);
     }
-    $marc->insert_fields_ordered(@item_fields);
+    $marc->append_fields(@item_fields);
 }
 
 =head1 INTERNAL FUNCTIONS
@@ -3681,6 +3830,76 @@ sub get_biblio_authorised_values {
     return $authorised_values;
 }
 
+=head2 CountBiblioInOrders
+
+=over 4
+$count = &CountBiblioInOrders( $biblionumber);
+
+=back
+
+This function return count of biblios in orders with $biblionumber 
+
+=cut
+
+sub CountBiblioInOrders {
+ my ($biblionumber) = @_;
+    my $dbh            = C4::Context->dbh;
+    my $query          = "SELECT count(*)
+          FROM  aqorders 
+          WHERE biblionumber=? AND (datecancellationprinted IS NULL OR datecancellationprinted='0000-00-00')";
+    my $sth = $dbh->prepare($query);
+    $sth->execute($biblionumber);
+    my $count = $sth->fetchrow;
+    return ($count);
+}
+
+=head2 GetSubscriptionsId
+
+=over 4
+$subscriptions = &GetSubscriptionsId($biblionumber);
+
+=back
+
+This function return an array of subscriptionid with $biblionumber
+
+=cut
+
+sub GetSubscriptionsId {
+ my ($biblionumber) = @_;
+    my $dbh            = C4::Context->dbh;
+    my $query          = "SELECT subscriptionid
+          FROM  subscription
+          WHERE biblionumber=?";
+    my $sth = $dbh->prepare($query);
+    $sth->execute($biblionumber);
+    my @subscriptions = $sth->fetchrow_array;
+    return (@subscriptions);
+}
+
+=head2 GetHolds
+
+=over 4
+$holds = &GetHolds($biblionumber);
+
+=back
+
+This function return the count of holds with $biblionumber
+
+=cut
+
+sub GetHolds {
+ my ($biblionumber) = @_;
+    my $dbh            = C4::Context->dbh;
+    my $query          = "SELECT count(*)
+          FROM  reserves
+          WHERE biblionumber=?";
+    my $sth = $dbh->prepare($query);
+    $sth->execute($biblionumber);
+    my $holds = $sth->fetchrow;
+    return ($holds);
+}
+
+
 1;
 
 __END__