Bug Fix 3320 : condition on enabling field input was wrong
[koha.git] / cataloguing / addbiblio.pl
index 9f7f1f3..b49b187 100755 (executable)
@@ -32,6 +32,7 @@ use C4::Koha;    # XXX subfield_is_koha_internal_p
 use C4::Branch;    # XXX subfield_is_koha_internal_p
 use C4::ClassSource;
 use C4::ImportBatch;
+use C4::Charset;
 
 use Date::Calc qw(Today);
 use MARC::File::USMARC;
@@ -84,7 +85,7 @@ sub MARCfindbreeding {
             }
         }
                
-        if ( ref($record) eq undef ) {
+        if ( !defined(ref($record)) ) {
             return -1;
         }
         else {
@@ -92,7 +93,7 @@ sub MARCfindbreeding {
             if (    C4::Context->preference("z3950NormalizeAuthor")
                 and C4::Context->preference("z3950AuthorAuthFields") )
             {
-                my ( $tag, $subfield ) = GetMarcFromKohaField("biblio.author");
+                my ( $tag, $subfield ) = GetMarcFromKohaField("biblio.author",'');
 
  #                 my $summary = C4::Context->preference("z3950authortemplate");
                 my $auth_fields =
@@ -288,6 +289,14 @@ sub create_input {
 
     $value =~ s/"/"/g;
 
+    # determine maximum length; 9999 bytes per ISO 2709 except for leader and MARC21 008
+    my $max_length = 9999;
+    if ($tag eq '000') {
+        $max_length = 24;
+    } elsif ($tag eq '008' and C4::Context->preference('marcflavour') eq 'MARC21')  {
+        $max_length = 40;
+    }
+
     # if there is no value provided but a default value in parameters, get it
     unless ($value) {
         $value = $tagslib->{$tag}->{$subfield}->{defaultvalue};
@@ -299,11 +308,20 @@ sub create_input {
         $value =~ s/YYYY/$year/g;
         $value =~ s/MM/$month/g;
         $value =~ s/DD/$day/g;
+        my $username=(C4::Context->userenv?C4::Context->userenv->{'surname'}:"superlibrarian");    
+        $value=~s/user/$username/g;
+    
     }
     my $dbh = C4::Context->dbh;
+
+    # map '@' as "subfield" label for fixed fields
+    # to something that's allowed in a div id.
+    my $id_subfield = $subfield;
+    $id_subfield = "00" if $id_subfield eq "@";
+
     my %subfield_data = (
         tag        => $tag,
-        subfield   => $subfield,
+        subfield   => $id_subfield,
         marc_lib   => substr( $tagslib->{$tag}->{$subfield}->{lib}, 0, 22 ),
         marc_lib_plain => $tagslib->{$tag}->{$subfield}->{lib}, 
         tag_mandatory  => $tagslib->{$tag}->{mandatory},
@@ -311,16 +329,10 @@ sub create_input {
         repeatable     => $tagslib->{$tag}->{$subfield}->{repeatable},
         kohafield      => $tagslib->{$tag}->{$subfield}->{kohafield},
         index          => $index_tag,
-        id             => "tag_".$tag."_subfield_".$subfield."_".$index_tag."_".$index_subfield,
+        id             => "tag_".$tag."_subfield_".$id_subfield."_".$index_tag."_".$index_subfield,
         value          => $value,
         random         => CreateKey(),
     );
-    # deal with a <010 tag
-    if($subfield eq '@'){
-        $subfield_data{id} = "tag_".$tag."_subfield_00_".$index_tag."_".$index_subfield;
-    } else {
-         $subfield_data{id} = "tag_".$tag."_subfield_".$subfield."_".$index_tag."_".$index_subfield;
-    }
 
     if(exists $mandatory_z3950->{$tag.$subfield}){
         $subfield_data{z3950_mandatory} = $mandatory_z3950->{$tag.$subfield};
@@ -339,9 +351,29 @@ sub create_input {
           build_authorized_values_list( $tag, $subfield, $value, $dbh,
             $authorised_values_sth,$index_tag,$index_subfield );
 
+    # it's a subfield $9 linking to an authority record - see bug 2206
+    }
+    elsif ($subfield eq "9" and
+           exists($tagslib->{$tag}->{'a'}->{authtypecode}) and
+           defined($tagslib->{$tag}->{'a'}->{authtypecode}) and
+           $tagslib->{$tag}->{'a'}->{authtypecode} ne '') {
+
+        $subfield_data{marc_value} =
+            "<input type=\"text\"
+                    id=\"".$subfield_data{id}."\"
+                    name=\"".$subfield_data{id}."\"
+                    value=\"$value\"
+                    class=\"input_marceditor\"
+                    tabindex=\"1\"
+                    size=\"5\"
+                    maxlength=\"$max_length\"
+                    readonly=\"readonly\"
+                    \/>";
+
     # it's a thesaurus / authority field
     }
     elsif ( $tagslib->{$tag}->{$subfield}->{authtypecode} ) {
+               my $readonly=(C4::Context->preference("BiblioAddsAuthorities")?"":qq(readonly="readonly"));
         $subfield_data{marc_value} =
             "<input type=\"text\"
                     id=\"".$subfield_data{id}."\"
@@ -350,14 +382,13 @@ sub create_input {
                     class=\"input_marceditor\"
                     tabindex=\"1\"
                     size=\"67\"
-                    maxlength=\"255\" 
-                    \/>
-                    <a href=\"#\" class=\"buttonDot\"
-                        onclick=\"Dopop('/cgi-bin/koha/authorities/auth_finder.pl?authtypecode=".$tagslib->{$tag}->{$subfield}->{authtypecode}."&index=$subfield_data{id}','$subfield_data{id}'); return false;\" title=\"Tag Editor\">...</a>
-               ";
-    # it's a plugin field
+                    maxlength=\"$max_length\"
+                                       $readonly\/><a href=\"#\" class=\"buttonDot\"
+                        onclick=\"openAuth(this.parentNode.getElementsByTagName('input')[1].id,'".$tagslib->{$tag}->{$subfield}->{authtypecode}."'); return false;\" tabindex=\"1\" title=\"Tag Editor\">...</a>
+            ";
     }
     elsif ( $tagslib->{$tag}->{$subfield}->{'value_builder'} ) {
+    # it's a plugin field
 
         # opening plugin. Just check wether we are on a developper computer on a production one
         # (the cgidir differs)
@@ -380,9 +411,9 @@ sub create_input {
                             class=\"input_marceditor\"
                             onfocus=\"Focus$function_name($index_tag)\"
                             size=\"67\"
-                            maxlength=\"255\" 
+                            maxlength=\"$max_length\"
                             onblur=\"Blur$function_name($index_tag); \" \/>
-                            <a href=\"#\" class=\"buttonDot\" onclick=\"Clic$function_name('$subfield_data{id}'); return false;\" title=\"Tag Editor\">...</a>
+                            <a href=\"#\" class=\"buttonDot\" onclick=\"Clic$function_name('$subfield_data{id}'); return false;\" tabindex=\"1\" title=\"Tag Editor\">...</a>
                     $javascript";
         } else {
             warn "Plugin Failed: $plugin";
@@ -394,7 +425,7 @@ sub create_input {
                         value=\"$value\"
                         tabindex=\"1\"
                         size=\"67\"
-                        maxlength=\"255\" 
+                        maxlength=\"$max_length\"
                         class=\"input_marceditor\"
                 \/>
                 ";
@@ -408,7 +439,7 @@ sub create_input {
                     id=\"".$subfield_data{id}."\"
                     name=\"".$subfield_data{id}."\"
                     size=\"67\"
-                    maxlength=\"255\" 
+                    maxlength=\"$max_length\"
                     value=\"$value\" \/>
             ";
     }
@@ -420,7 +451,7 @@ sub create_input {
                     class=\"input_marceditor\"
                     tabindex=\"1\"
                     size=\"67\"
-                    maxlength=\"255\" 
+                    maxlength=\"$max_length\"
                     value=\"$value\"
             \/>";
 
@@ -444,8 +475,6 @@ sub create_input {
                            name=\"".$subfield_data{id}."\"
                            class=\"input_marceditor\"
                            tabindex=\"1\"
-                            size=\"67\"
-                            maxlength=\"255\" 
                            >$value</textarea>
                 ";
         }
@@ -457,7 +486,7 @@ sub create_input {
                         value=\"$value\"
                         tabindex=\"1\"
                         size=\"67\"
-                        maxlength=\"255\" 
+                        maxlength=\"$max_length\"
                         class=\"input_marceditor\"
                 \/>
                 ";
@@ -467,6 +496,22 @@ sub create_input {
     return \%subfield_data;
 }
 
+
+=item format_indicator
+
+Translate indicator value for output form - specifically, map
+indicator = ' ' to ''.  This is for the convenience of a cataloger
+using a mouse to select an indicator input.
+
+=cut
+
+sub format_indicator {
+    my $ind_value = shift;
+    return '' if not defined $ind_value;
+    return '' if $ind_value eq ' ';
+    return $ind_value;
+}
+
 sub build_tabs ($$$$$) {
     my ( $template, $record, $dbh, $encoding,$input ) = @_;
 
@@ -507,7 +552,7 @@ sub build_tabs ($$$$$) {
         foreach my $tag (@tab_data) {
             $i++;
             next if ! $tag;
-            my $indicator;
+            my ($indicator1, $indicator2);
             my $index_tag = CreateKey;
 
             # if MARC::Record is not empty =>use it as master loop, then add missing subfields that should be in the tab.
@@ -571,8 +616,15 @@ sub build_tabs ($$$$$) {
                         next if ( $tag < 10 );
                         next
                           if ( ( $tagslib->{$tag}->{$subfield}->{hidden} <= -4 )
-                            or ( $tagslib->{$tag}->{$subfield}->{hidden} >= 5 )
-                          );    #check for visibility flag
+                            or ( $tagslib->{$tag}->{$subfield}->{hidden} >= 5 ) )
+                            and not ( $subfield eq "9" and
+                                      exists($tagslib->{$tag}->{'a'}->{authtypecode}) and
+                                      defined($tagslib->{$tag}->{'a'}->{authtypecode}) and
+                                      $tagslib->{$tag}->{'a'}->{authtypecode} ne ""
+                                    )
+                          ;    #check for visibility flag
+                               # if subfield is $9 in a field whose $a is authority-controlled,
+                               # always include in the form regardless of the hidden setting - bug 2206
                         next if ( defined( $field->subfield($subfield) ) );
                         push(
                             @subfields_data,
@@ -592,12 +644,14 @@ sub build_tabs ($$$$$) {
                             index         => $index_tag,
                             tag_lib       => $tagslib->{$tag}->{lib},
                             repeatable       => $tagslib->{$tag}->{repeatable},
+                            mandatory       => $tagslib->{$tag}->{mandatory},
                             subfield_loop => \@subfields_data,
                             fixedfield    => $tag < 10?1:0,
                             random        => CreateKey,
                         );
                         if ($tag >= 010){ # no indicator for theses tag
-                           $tag_data{indicator} = $field->indicator(1).$field->indicator(2);
+                           $tag_data{indicator1} = format_indicator($field->indicator(1)),
+                           $tag_data{indicator2} = format_indicator($field->indicator(2)),
                         }
                         push( @loop_data, \%tag_data );
                     }
@@ -612,7 +666,14 @@ sub build_tabs ($$$$$) {
                     next
                       if ( ( $tagslib->{$tag}->{$subfield}->{hidden} <= -5 )
                         or ( $tagslib->{$tag}->{$subfield}->{hidden} >= 4 ) )
+                      and not ( $subfield eq "9" and
+                                exists($tagslib->{$tag}->{'a'}->{authtypecode}) and
+                                defined($tagslib->{$tag}->{'a'}->{authtypecode}) and
+                                $tagslib->{$tag}->{'a'}->{authtypecode} ne ""
+                              )
                       ;    #check for visibility flag
+                           # if subfield is $9 in a field whose $a is authority-controlled,
+                           # always include in the form regardless of the hidden setting - bug 2206
                     next
                       if ( $tagslib->{$tag}->{$subfield}->{tab} ne $tabloop );
                     push(
@@ -629,7 +690,9 @@ sub build_tabs ($$$$$) {
                         index            => $index_tag,
                         tag_lib          => $tagslib->{$tag}->{lib},
                         repeatable       => $tagslib->{$tag}->{repeatable},
-                        indicator        => $indicator,
+                        mandatory       => $tagslib->{$tag}->{mandatory},
+                        indicator1       => $indicator1,
+                        indicator2       => $indicator2,
                         subfield_loop    => \@subfields_data,
                         tagfirstsubfield => $subfields_data[0],
                         fixedfield       => $tag < 10?1:0,
@@ -649,6 +712,16 @@ sub build_tabs ($$$$$) {
     $template->param( BIG_LOOP => \@BIG_LOOP );
 }
 
+#
+# sub that tries to find authorities linked to the biblio
+# the sub :
+#   - search in the authority DB for the same authid (in $9 of the biblio)
+#   - search in the authority DB for the same 001 (in $3 of the biblio in UNIMARC)
+#   - search in the authority DB for the same values (exactly) (in all subfields of the biblio)
+# if the authority is found, the biblio is modified accordingly to be connected to the authority.
+# if the authority is not found, it's added, and the biblio is then modified to be connected to the authority.
+#
+
 sub BiblioAddAuthorities{
   my ( $record, $frameworkcode ) = @_;
   my $dbh=C4::Context->dbh;
@@ -669,15 +742,18 @@ AND (authtypecode IS NOT NULL AND authtypecode<>\"\")|);
       # No authorities id in the tag.
       # Search if there is any authorities to link to.
       my $query='at='.$data->{authtypecode}.' ';
-      map {$query.= " and he,ext=".$_->[1] if ($_->[0]=~/[A-z]/)}  $field->subfields();
-      warn $query;   
-      my ($error,$results)=SimpleSearch($query,"authorityserver");
+      map {$query.= ' and he,ext="'.$_->[1].'"' if ($_->[0]=~/[A-z]/)}  $field->subfields();
+      my ($error, $results, $total_hits)=SimpleSearch( $query, undef, undef, [ "authorityserver" ] );
     # there is only 1 result 
-      if (scalar(@$results)==1) {
+         if ( $error ) {
+        warn "BIBLIOADDSAUTHORITIES: $error";
+           return (0,0) ;
+         }
+      if ($results && scalar(@$results)==1) {
         my $marcrecord = MARC::File::USMARC::decode($results->[0]);
         $field->add_subfields('9'=>$marcrecord->field('001')->data);
         $countlinked++;
-      }elsif (scalar(@$results)>1) {
+      } elsif (scalar(@$results)>1) {
    #More than One result 
    #This can comes out of a lack of a subfield.
 #         my $marcrecord = MARC::File::USMARC::decode($results->[0]);
@@ -688,10 +764,36 @@ AND (authtypecode IS NOT NULL AND authtypecode<>\"\")|);
   ###NOTICE : This is only valid if a subfield is linked to one and only one authtypecode     
   ###NOTICE : This can be a problem. We should also look into other types and rejected forms.
          my $authtypedata=GetAuthType($data->{authtypecode});
+         next unless $authtypedata;
          my $marcrecordauth=MARC::Record->new();
          my $authfield=MARC::Field->new($authtypedata->{auth_tag_to_report},'','',"a"=>"".$field->subfield('a'));
          map { $authfield->add_subfields($_->[0]=>$_->[1]) if ($_->[0]=~/[A-z]/ && $_->[0] ne "a" )}  $field->subfields();
          $marcrecordauth->insert_fields_ordered($authfield);
+
+         # bug 2317: ensure new authority knows it's using UTF-8; currently
+         # only need to do this for MARC21, as MARC::Record->as_xml_record() handles
+         # automatically for UNIMARC (by not transcoding)
+         # FIXME: AddAuthority() instead should simply explicitly require that the MARC::Record
+         # use UTF-8, but as of 2008-08-05, did not want to introduce that kind
+         # of change to a core API just before the 3.0 release.
+         # 
+         # This isn't needed if we set the UTF flag in the leader below
+               #if (C4::Context->preference('marcflavour') eq 'MARC21') {
+        #    SetMarcUnicodeFlag($marcrecordauth, 'MARC21');
+        # }
+
+                               if (C4::Context->preference('marcflavour') eq 'MARC21') {
+                                       $marcrecordauth->leader('     nz  a22     o  4500');
+                                       $marcrecordauth->insert_fields_ordered(MARC::Field->new('667','','','a'=>"Machine generated authority record."));
+                                       my $cite = $record->author() . ", " .  $record->title_proper() . ", " . $record->publication_date() . " "; 
+                                       $cite =~ s/^[\s\,]*//;
+                                       $cite =~ s/[\s\,]*$//;
+                                       $cite = "Work cat.: (" . C4::Context->preference('MARCOrgCode') . ")". $record->subfield('999','c') . ": " . $cite;
+                                       $marcrecordauth->insert_fields_ordered(MARC::Field->new('670','','','a'=>$cite));
+                               }
+
+#          warn "AUTH RECORD ADDED : ".$marcrecordauth->as_formatted;
+
          my $authid=AddAuthority($marcrecordauth,'',$data->{authtypecode});
          $countcreated++;
          $field->add_subfields('9'=>$authid);
@@ -728,31 +830,22 @@ my ( $template, $loggedinuser, $cookie ) = get_template_and_user(
     }
 );
 
-#Getting the list of all frameworks
-my $queryfwk = $dbh->prepare("select frameworktext, frameworkcode from biblio_framework");
-$queryfwk->execute;
-my %select_fwk;
-my @select_fwk;
-my $curfwk;
-push @select_fwk, "Default";
-$select_fwk{"Default"} = "Default";
-
-while ( my ( $description, $fwk ) = $queryfwk->fetchrow ) {
-    push @select_fwk, $fwk;
-    $select_fwk{$fwk} = $description;
-}
-$curfwk = $frameworkcode;
-my $framework = CGI::scrolling_list(
-    -name     => 'Frameworks',
-    -id       => 'Frameworks',
-    -default  => $curfwk,
-    -onchange => 'Changefwk(this);',
-    -values   => \@select_fwk,
-    -labels   => \%select_fwk,
-    -size     => 1,
-    -multiple => 0
-);
-$template->param( framework => $framework, breedingid => $breedingid );
+# Getting the list of all frameworks
+# get framework list
+my $frameworks = getframeworks;
+my @frameworkcodeloop;
+foreach my $thisframeworkcode ( keys %$frameworks ) {
+       my %row = (
+               value         => $thisframeworkcode,
+               frameworktext => $frameworks->{$thisframeworkcode}->{'frameworktext'},
+       );
+       if ($frameworkcode eq $thisframeworkcode){
+               $row{'selected'}="selected=\"selected\"";
+               }
+       push @frameworkcodeloop, \%row;
+} 
+$template->param( frameworkcodeloop => \@frameworkcodeloop,
+       breedingid => $breedingid );
 
 # ++ Global
 $tagslib         = &GetMarcStructure( 1, $frameworkcode );
@@ -782,6 +875,7 @@ $is_a_modif = 0;
     
 if ($biblionumber) {
     $is_a_modif = 1;
+       $template->param( title => $record->title(), );
 
     # if it's a modif, retrieve bibli and biblioitem numbers for the future modification of old-DB.
     ( $biblionumbertagfield, $biblionumbertagsubfield ) =