Browse Source

Bug 8976: Add the ability to sort subfields for the MARC frameworks

This new enhancement adds the ability to change the default order the subfields.

Both bibliographic and authority MARC subfield structure are taken into
account. And so the item edition as well (in the different screens when
item can be added/edited).

This will answer the following needs that have been listed in the
comments of the bug report:
- $i in 7xx fields should be the first subfield in the sequence
- 300 fields are sorted number first when cataloguers enter the letter fields first
- 100 field, it's commonly $a, $q, $d.

Test plan:
1. Edit a MARC frameworks, field 300
2. Resort the subfield (drag and drop the tab of the subfield) as you
like
3. Save
=> Notice that the list of fields are displayed following the order you
chose
4. Edit it again
=> The order is correctly kept!
5. Create a new bibliographic record
6. Notice that the subfields are order in the same sequence
7. Fill different subfields, not all
8. Save, edit again
9. Note that the subfields that have been filled are listed first, then
the empty ones. But the sequence defined at the framework level is kept.
10. Do the same for an authority framework and create/edit an authority
record
11. Modify item (952) subfields order
12. Create an item and confirm that the order is correct
13. Modify the ACQ framework, 952, modify the order of the subfield
14. Create a new order and confirm that the item form has the subfield
ordered following the sequence defined at the framework level

QA: Note that this patch is about bibliographic records only, next
patches deal with authotiries and items.

Sponsored-by: Orex Digital

Signed-off-by: Michal Denar <black23@gmail.com>
Signed-off-by: Tomas Cohen Arazi <tomascohen@theke.io>

Signed-off-by: Jonathan Druart <jonathan.druart@bugs.koha-community.org>
21.05.x
Jonathan Druart 3 years ago
parent
commit
b387502eaf
  1. 13
      C4/Biblio.pm
  2. 12
      admin/marc_subfields_structure.pl
  3. 19
      cataloguing/addbiblio.pl
  4. 16
      koha-tmpl/intranet-tmpl/prog/en/modules/admin/marc_subfields_structure.tt
  5. 23
      koha-tmpl/intranet-tmpl/prog/js/marc_subfields_structure.js

13
C4/Biblio.pm

@ -961,10 +961,10 @@ sub GetMarcStructure {
}
$sth = $dbh->prepare(
"SELECT tagfield,tagsubfield,liblibrarian,libopac,tab,mandatory,repeatable,authorised_value,authtypecode,value_builder,kohafield,seealso,hidden,isurl,link,defaultvalue,maxlength,important
"SELECT tagfield,tagsubfield,liblibrarian,libopac,tab,mandatory,repeatable,authorised_value,authtypecode,value_builder,kohafield,seealso,hidden,isurl,link,defaultvalue,maxlength,important, display_order
FROM marc_subfield_structure
WHERE frameworkcode=?
ORDER BY tagfield,tagsubfield
ORDER BY tagfield, tagsubfield
"
);
@ -981,16 +981,18 @@ sub GetMarcStructure {
my $link;
my $defaultvalue;
my $maxlength;
my $display_order;
while (
( $tag, $subfield, $liblibrarian, $libopac, $tab, $mandatory, $repeatable, $authorised_value,
$authtypecode, $value_builder, $kohafield, $seealso, $hidden, $isurl, $link, $defaultvalue,
$maxlength, $important
$maxlength, $important, $display_order
)
= $sth->fetchrow
) {
$res->{$tag}->{$subfield}->{lib} = ( $forlibrarian or !$libopac ) ? $liblibrarian : $libopac;
$res->{$tag}->{$subfield}->{tab} = $tab;
$res->{$tag}->{$subfield}->{subfield} = $subfield;
$res->{$tag}->{$subfield}->{mandatory} = $mandatory;
$res->{$tag}->{$subfield}->{important} = $important;
$res->{$tag}->{$subfield}->{repeatable} = $repeatable;
@ -1004,6 +1006,7 @@ sub GetMarcStructure {
$res->{$tag}->{$subfield}->{'link'} = $link;
$res->{$tag}->{$subfield}->{defaultvalue} = $defaultvalue;
$res->{$tag}->{$subfield}->{maxlength} = $maxlength;
$res->{$tag}->{$subfield}->{display_order} = $display_order;
}
$cache->set_in_cache($cache_key, $res);
@ -1031,7 +1034,7 @@ sub GetUsedMarcStructure {
FROM marc_subfield_structure
WHERE tab > -1
AND frameworkcode = ?
ORDER BY tagfield, tagsubfield
ORDER BY tagfield, display_order, tagsubfield
};
my $sth = C4::Context->dbh->prepare($query);
$sth->execute($frameworkcode);
@ -1096,7 +1099,7 @@ sub GetMarcSubfieldStructure {
FROM marc_subfield_structure
WHERE frameworkcode = ?
AND kohafield > ''
ORDER BY frameworkcode,tagfield,tagsubfield
ORDER BY frameworkcode, tagfield, display_order, tagsubfield
|, { Slice => {} }, $frameworkcode );
# Now map the output to a hash structure
my $subfield_structure = {};

12
admin/marc_subfields_structure.pl

@ -37,7 +37,7 @@ sub string_search {
my $count = @data;
my $sth =
$dbh->prepare(
"Select * from marc_subfield_structure where (tagfield like ? and frameworkcode=?) order by tagfield"
"Select * from marc_subfield_structure where (tagfield like ? and frameworkcode=?) order by tagfield, display_order"
);
$sth->execute( "$searchstring%", $frameworkcode );
my @results;
@ -161,7 +161,7 @@ if ( $op eq 'add_form' ) {
# build values list
my $sth =
$dbh->prepare(
"select * from marc_subfield_structure where tagfield=? and frameworkcode=?"
"select * from marc_subfield_structure where tagfield=? and frameworkcode=? order by display_order"
); # and tagsubfield='$tagsubfield'");
$sth->execute( $tagfield, $frameworkcode );
my @loop_data = ();
@ -263,7 +263,7 @@ elsif ( $op eq 'add_validate' ) {
my $dbh = C4::Context->dbh;
$template->param( tagfield => "$input->param('tagfield')" );
my $sth_update = $dbh->prepare(qq{
update marc_subfield_structure set tagfield=?, tagsubfield=?, liblibrarian=?, libopac=?, repeatable=?, mandatory=?, important=?, kohafield=?, tab=?, seealso=?, authorised_value=?, authtypecode=?, value_builder=?, hidden=?, isurl=?, frameworkcode=?, link=?, defaultvalue=?, maxlength=?
update marc_subfield_structure set tagfield=?, tagsubfield=?, liblibrarian=?, libopac=?, repeatable=?, mandatory=?, important=?, kohafield=?, tab=?, seealso=?, authorised_value=?, authtypecode=?, value_builder=?, hidden=?, isurl=?, frameworkcode=?, link=?, defaultvalue=?, maxlength=?, display_order=?
where tagfield=? and tagsubfield=? and frameworkcode=?
});
my @tagsubfield = $input->multi_param('tagsubfield');
@ -279,7 +279,8 @@ elsif ( $op eq 'add_validate' ) {
my @link = $input->multi_param('link');
my @defaultvalue = $input->multi_param('defaultvalue');
my @maxlength = $input->multi_param('maxlength');
my $display_order;
for ( my $i = 0 ; $i <= $#tagsubfield ; $i++ ) {
my $tagfield = $input->param('tagfield');
my $tagsubfield = $tagsubfield[$i];
@ -323,6 +324,7 @@ elsif ( $op eq 'add_validate' ) {
$link,
$defaultvalue,
$maxlength,
$display_order->{$tagfield} || 0,
(
$tagfield,
$tagsubfield,
@ -356,9 +358,11 @@ elsif ( $op eq 'add_validate' ) {
link => $link,
defaultvalue => $defaultvalue,
maxlength => $maxlength,
display_order => $display_order->{$tagfield} || 0,
}
)->store;
}
$display_order->{$tagfield}++;
}
}
$sth_update->finish;

19
cataloguing/addbiblio.pl

@ -580,7 +580,7 @@ sub build_tabs {
}
# now, loop again to add parameter subfield that are not in the MARC::Record
foreach my $subfield ( sort( keys %{ $tagslib->{$tag} } ) )
foreach my $subfield ( keys %{ $tagslib->{$tag} } )
{
next if ( length $subfield != 1 );
next if ( $tagslib->{$tag}->{$subfield}->{tab} ne $tabloop );
@ -633,12 +633,15 @@ 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 ""
@ -647,11 +650,11 @@ sub build_tabs {
# 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 );
if ( $subfield->{tab} ne $tabloop );
push(
@subfields_data,
&create_input(
$tag, $subfield, '', $index_tag, $tabloop, $record,
$tag, $subfield->{subfield}, '', $index_tag, $tabloop, $record,
$authorised_values_sth,$input
)
);

16
koha-tmpl/intranet-tmpl/prog/en/modules/admin/marc_subfields_structure.tt

@ -80,13 +80,15 @@
<div id="subfieldtabs" class="toptabs numbered">
<ul>
[% FOREACH loo IN loop %]
[% IF ( loo.new_subfield ) %]
<li><a href="#sub[% loo.urisubfieldcode | uri %]field" title="[% loo.liblibrarian | html_entity %]">New</a></li>
[% ELSE %]
<li><a href="#sub[% loo.urisubfieldcode | uri %]field" title="[% loo.liblibrarian | html_entity %]">
[% loo.subfieldcode | html %]
</a></li>
[% END %]
<li id="tab_subfield_[% loo.urisubfieldcode | html %]">
[% IF ( loo.new_subfield ) %]
<a href="#sub[% loo.urisubfieldcode | uri %]field" title="[% loo.liblibrarian | html_entity %]">New</a>
[% ELSE %]
<a href="#sub[% loo.urisubfieldcode | uri %]field" title="[% loo.liblibrarian | html_entity %]">
[% loo.subfieldcode | html %]
</a>
[% END %]
</li>
[% END %]
</ul>

23
koha-tmpl/intranet-tmpl/prog/js/marc_subfields_structure.js

@ -1,6 +1,26 @@
/* global dataTablesDefaults */
$(document).ready(function() {
$('#subfieldtabs').tabs();
var tabs = $('#subfieldtabs').tabs();
var current_index;
tabs.find( ".ui-tabs-nav" ).sortable({
axis: "x",
start: function (e, ui) {
current_index = $(ui.item[0]).index();
},
stop: function (e, ui) {
var new_index = $(ui.item[0]).index();
if (current_index < new_index) new_index++;
var subfield_code = $(ui.item[0]).attr('id').replace( /^tab_subfield_/, '');
var content = $('#sub' + subfield_code + 'field');
var panels = $("#subfieldtabs > div");
if ( new_index < $(panels).size() ){
$(content).insertBefore($("#subfieldtabs > div")[new_index]);
} else {
$(content).insertAfter($("#subfieldtabs > div")[new_index-1]);
}
tabs.tabs("refresh");
}
});
$("input[id^='hidden_']").click(setHiddenValue);
$("input[id^='hidden-']").each(function() {
populateHiddenCheckboxes($(this).attr('id').split('-')[1]);
@ -9,6 +29,7 @@ $(document).ready(function() {
"columnDefs": [
{ 'sortable': false, 'targets': [ 'NoSort' ] }
],
aaSorting: [],
paginate: false
}));
});

Loading…
Cancel
Save