Bug 31371: Value builder for field 283
[srvgit] / cataloguing / addbiblio.pl
index e5c33dc..5896de1 100755 (executable)
 
 use Modern::Perl;
 
-use CGI q(-utf8);
-use C4::Output;
-use C4::Auth;
-use C4::Biblio;
-use C4::Search;
-use C4::AuthoritiesMarc;
+use CGI;
+use C4::Output qw( output_html_with_http_headers );
+use C4::Auth qw( get_template_and_user haspermission );
+use C4::Biblio qw(
+    AddBiblio
+    DelBiblio
+    GetFrameworkCode
+    GetMarcFromKohaField
+    GetMarcStructure
+    GetUsedMarcStructure
+    ModBiblio
+    prepare_host_field
+    PrepHostMarcField
+    TransformHtmlToMarc
+);
+use C4::Search qw( FindDuplicate enabled_staff_search_views );
+use C4::Auth qw( get_template_and_user haspermission );
 use C4::Context;
 use MARC::Record;
-use C4::Log;
-use C4::Koha;
-use C4::ClassSource;
-use C4::ImportBatch;
-use C4::Charset;
+use C4::ClassSource qw( GetClassSources );
+use C4::ImportBatch qw( GetImportRecordMarc );
+use C4::Charset qw( SetMarcUnicodeFlag );
 use Koha::BiblioFrameworks;
-use Koha::DateUtils;
+use Koha::DateUtils qw( dt_from_string );
 
+use Koha::Biblios;
 use Koha::ItemTypes;
 use Koha::Libraries;
 
 use Koha::BiblioFrameworks;
+use Koha::Patrons;
 
-use Date::Calc qw(Today);
 use MARC::File::USMARC;
 use MARC::File::XML;
-use URI::Escape;
+use URI::Escape qw( uri_escape_utf8 );
 
 if ( C4::Context->preference('marcflavour') eq 'UNIMARC' ) {
     MARC::File::XML->default_record_format('UNIMARC');
@@ -72,6 +82,10 @@ sub MARCfindbreeding {
     # remove the - in isbn, koha store isbn without any -
     if ($marc) {
         my $record = MARC::Record->new_from_usmarc($marc);
+        if(C4::Context->preference('autoControlNumber') eq 'biblionumber'){
+            my @control_num = $record->field('001');
+            $record->delete_fields(@control_num);
+        }
         my ($isbnfield,$isbnsubfield) = GetMarcFromKohaField( 'biblioitems.isbn' );
         if ( $record->field($isbnfield) ) {
             foreach my $field ( $record->field($isbnfield) ) {
@@ -274,12 +288,13 @@ sub GetMandatoryFieldZ3950 {
 =cut
 
 sub create_input {
-    my ( $tag, $subfield, $value, $index_tag, $tabloop, $rec, $authorised_values_sth,$cgi ) = @_;
+    my ( $tag, $subfield, $value, $index_tag, $rec, $authorised_values_sth,$cgi ) = @_;
     
     my $index_subfield = CreateKey(); # create a specifique key for each subfield
 
-    # if there is no value provided but a default value in parameters, get it
-    if ( $value eq '' ) {
+    # Apply optional framework default value when it is a new record
+    # Substitute date parts, user name
+    if ( $value eq '' && !$cgi->param('biblionumber') ) {
         $value = $tagslib->{$tag}->{$subfield}->{defaultvalue} // q{};
 
         # get today date & replace <<YYYY>>, <<YY>>, <<MM>>, <<DD>> if provided in the default value
@@ -295,8 +310,8 @@ sub create_input {
         # And <<USER>> with surname (?)
         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
@@ -343,13 +358,14 @@ 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
+    # it's a subfield $9 linking to an authority record - see bug 2206 and 28022
     }
     elsif ($subfield eq "9" and
            exists($tagslib->{$tag}->{'a'}->{authtypecode}) and
            defined($tagslib->{$tag}->{'a'}->{authtypecode}) and
-           $tagslib->{$tag}->{'a'}->{authtypecode} ne '') {
-
+           $tagslib->{$tag}->{'a'}->{authtypecode} ne '' and
+           $tagslib->{$tag}->{'a'}->{hidden} > -4 and
+           $tagslib->{$tag}->{'a'}->{hidden} < 5) {
         $subfield_data{marc_value} = {
             type      => 'text',
             id        => $subfield_data{id},
@@ -364,7 +380,7 @@ sub create_input {
     }
     elsif ( $tagslib->{$tag}->{$subfield}->{authtypecode} ) {
         # when authorities auto-creation is allowed, do not set readonly
-        my $is_readonly = !C4::Context->preference("BiblioAddsAuthorities");
+        my $is_readonly = C4::Context->preference("RequireChoosingExistingAuthority");
 
         $subfield_data{marc_value} = {
             type      => 'text',
@@ -384,7 +400,7 @@ sub create_input {
             name => $tagslib->{$tag}->{$subfield}->{'value_builder'},
         });
         my $pars= { dbh => $dbh, record => $rec, tagslib => $tagslib,
-            id => $subfield_data{id}, tabloop => $tabloop };
+            id => $subfield_data{id} };
         $plugin->build( $pars );
         if( !$plugin->errstr ) {
             $subfield_data{marc_value} = {
@@ -395,6 +411,7 @@ sub create_input {
                 size           => 67,
                 maxlength      => $subfield_data{maxlength},
                 javascript     => $plugin->javascript,
+                plugin         => $plugin->name,
                 noclick        => $plugin->noclick,
             };
         } else {
@@ -556,7 +573,7 @@ sub build_tabs {
                         push(
                             @subfields_data,
                             &create_input(
-                                $tag, $subfield, $value, $index_tag, $tabloop, $record,
+                                $tag, $subfield, $value, $index_tag, $record,
                                 $authorised_values_sth,$input
                             )
                         );
@@ -571,7 +588,7 @@ sub build_tabs {
                             push(
                                 @subfields_data,
                                 &create_input(
-                                    $tag, $subfield, $value, $index_tag, $tabloop,
+                                    $tag, $subfield, $value, $index_tag,
                                     $record, $authorised_values_sth,$input
                                 )
                             );
@@ -590,16 +607,18 @@ sub build_tabs {
                             and not ( $subfield eq "9" and
                                       exists($tagslib->{$tag}->{'a'}->{authtypecode}) and
                                       defined($tagslib->{$tag}->{'a'}->{authtypecode}) and
-                                      $tagslib->{$tag}->{'a'}->{authtypecode} ne ""
+                                      $tagslib->{$tag}->{'a'}->{authtypecode} ne "" and
+                                      $tagslib->{$tag}->{'a'}->{hidden} > -4 and
+                                      $tagslib->{$tag}->{'a'}->{hidden} < 5
                                     )
                           ;    #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
+                               # always include in the form regardless of the hidden setting - bug 2206 and 28022
                         next if ( defined( $field->subfield($subfield) ) );
                         push(
                             @subfields_data,
                             &create_input(
-                                $tag, $subfield, '', $index_tag, $tabloop, $record,
+                                $tag, $subfield, '', $index_tag, $record,
                                 $authorised_values_sth,$input
                             )
                         );
@@ -632,25 +651,30 @@ sub build_tabs {
             }
             else {
                 my @subfields_data;
-                foreach my $subfield ( sort( keys %{ $tagslib->{$tag} } ) ) {
-                    next if ( length $subfield != 1 );
+                foreach my $subfield (
+                    sort { $a->{display_order} <=> $b->{display_order} || $a->{subfield} cmp $b->{subfield} }
+                    grep { ref($_) && %$_ } # Not a subfield (values for "important", "lib", "mandatory", etc.) or empty
+                    values %{ $tagslib->{$tag} } )
+                {
                     next
-                      if ( ( $tagslib->{$tag}->{$subfield}->{hidden} <= -4 )
-                        or ( $tagslib->{$tag}->{$subfield}->{hidden} >= 5 ) )
-                      and not ( $subfield eq "9" and
+                      if ( ( $subfield->{hidden} <= -4 )
+                        or ( $subfield->{hidden} >= 5 ) )
+                      and not ( $subfield->{subfield} eq "9" and
                                 exists($tagslib->{$tag}->{'a'}->{authtypecode}) and
                                 defined($tagslib->{$tag}->{'a'}->{authtypecode}) and
-                                $tagslib->{$tag}->{'a'}->{authtypecode} ne ""
+                                $tagslib->{$tag}->{'a'}->{authtypecode} ne "" and
+                                $tagslib->{$tag}->{'a'}->{hidden} > -4 and
+                                $tagslib->{$tag}->{'a'}->{hidden} < 5
                               )
                       ;    #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
+                           # always include in the form regardless of the hidden setting - bug 2206 and 28022
                     next
-                      if ( $tagslib->{$tag}->{$subfield}->{tab} ne $tabloop );
+                      if ( $subfield->{tab} ne $tabloop );
                        push(
                         @subfields_data,
                         &create_input(
-                            $tag, $subfield, '', $index_tag, $tabloop, $record,
+                            $tag, $subfield->{subfield}, '', $index_tag, $record,
                             $authorised_values_sth,$input
                         )
                     );
@@ -688,17 +712,17 @@ sub build_tabs {
 # ========================
 #          MAIN
 #=========================
-my $input = new CGI;
+my $input = CGI->new;
 my $error = $input->param('error');
 my $biblionumber  = $input->param('biblionumber'); # if biblionumber exists, it's a modif, not a new biblio.
 my $parentbiblio  = $input->param('parentbiblionumber');
 my $breedingid    = $input->param('breedingid');
 my $z3950         = $input->param('z3950');
 my $op            = $input->param('op') // q{};
-my $mode          = $input->param('mode');
+my $mode          = $input->param('mode') // q{};
 my $frameworkcode = $input->param('frameworkcode');
 my $redirect      = $input->param('redirect');
-my $searchid      = $input->param('searchid');
+my $searchid      = $input->param('searchid') // "";
 my $dbh           = C4::Context->dbh;
 my $hostbiblionumber = $input->param('hostbiblionumber');
 my $hostitemnumber = $input->param('hostitemnumber');
@@ -729,9 +753,10 @@ my ( $template, $loggedinuser, $cookie ) = get_template_and_user(
     }
 );
 
+my $biblio;
 if ($biblionumber){
-    my $does_bib_exist = Koha::Biblios->find($biblionumber);
-    if (!defined $does_bib_exist){
+    $biblio = Koha::Biblios->find($biblionumber);
+    unless ( $biblio ) {
         $biblionumber = undef;
         $template->param( bib_doesnt_exist => 1 );
     }
@@ -780,13 +805,17 @@ my (
        $biblioitemnumber
 );
 
-if (($biblionumber) && !($breedingid)){
-    $record = GetMarcBiblio({ biblionumber => $biblionumber });
+if ( $biblio && !$breedingid ) {
+    $record = $biblio->metadata->record;
 }
 if ($breedingid) {
     ( $record, $encoding ) = MARCfindbreeding( $breedingid ) ;
 }
-
+if ( $record && $op eq 'duplicate' &&
+     C4::Context->preference('autoControlNumber') eq 'biblionumber' ){
+    my @control_num = $record->field('001');
+    $record->delete_fields(@control_num);
+}
 #populate hostfield if hostbiblionumber is available
 if ($hostbiblionumber) {
     my $marcflavour = C4::Context->preference("marcflavour");
@@ -846,7 +875,19 @@ if ( $op eq "addbiblio" ) {
     if ( !$duplicatebiblionumber or $confirm_not_duplicate ) {
         my $oldbibitemnum;
         if ( $is_a_modif ) {
-            ModBiblio( $record, $biblionumber, $frameworkcode );
+            my $member = Koha::Patrons->find($loggedinuser);
+            ModBiblio(
+                $record,
+                $biblionumber,
+                $frameworkcode,
+                {
+                    overlay_context => {
+                        source       => $z3950 ? 'z39.50' : 'intranet',
+                        categorycode => $member->categorycode,
+                        userid       => $member->userid
+                    }
+                }
+            );
         }
         else {
             ( $biblionumber, $oldbibitemnum ) = AddBiblio( $record, $frameworkcode );
@@ -939,6 +980,7 @@ elsif ( $op eq "delete" ) {
     $template->param(
         biblionumberdata => $biblionumber,
         op               => $op,
+        z3950            => $z3950
     );
     if ( $op eq "duplicate" ) {
         $biblionumber = "";