View | Details | Raw Unified | Return to bug 24807
Collapse All | Expand All

(-)a/Koha/SearchEngine/Elasticsearch.pm (-25 / +48 lines)
Lines 472-508 sub _process_mappings { Link Here
472
        # Copy (scalar) data since can have multiple targets
472
        # Copy (scalar) data since can have multiple targets
473
        # with differing options for (possibly) mutating data
473
        # with differing options for (possibly) mutating data
474
        # so need a different copy for each
474
        # so need a different copy for each
475
        my $_data = $data;
475
        my $data_copy = $data;
476
        if (defined $options->{substr}) {
476
        if (defined $options->{substr}) {
477
            my ($start, $length) = @{$options->{substr}};
477
            my ($start, $length) = @{$options->{substr}};
478
            $_data = length($data) > $start ? substr $data, $start, $length : '';
478
            $data_copy = length($data) > $start ? substr $data_copy, $start, $length : '';
479
        }
480
481
        # Add data to tokens array for callbacks processing
482
        my $tokens = [$data_copy];
483
484
        # Tokenize callbacks takes as token (possibly tokenized subfield data)
485
        # as argument, and returns a possibly different list of tokens.
486
        # Note that this list also might be empty.
487
        if (defined $options->{tokenize_callbacks}) {
488
            foreach my $callback (@{$options->{tokenize_callbacks}}) {
489
                # Pass each token to current callback which returns a list
490
                # (scalar is fine too) resulting either in a list or
491
                # a list of lists that will be flattened by perl.
492
                # The next callback will recieve the possibly expanded list of tokens.
493
                $tokens = [ map { $callback->($_) } @{$tokens} ];
494
            }
479
        }
495
        }
480
        if (defined $options->{value_callbacks}) {
496
        if (defined $options->{value_callbacks}) {
481
            $_data = reduce { $b->($a) } ($_data, @{$options->{value_callbacks}});
497
            $tokens = [ map { reduce { $b->($a) } ($_, @{$options->{value_callbacks}}) } @{$tokens} ];
482
        }
498
        }
483
        if (defined $options->{filter_callbacks}) {
499
        if (defined $options->{filter_callbacks}) {
484
            # Skip mapping unless all filter callbacks return true
500
            my @tokens_filtered;
485
            next unless all { $_data = $_->($_data) } @{$options->{filter_callbacks}};
501
            foreach my $_data (@{$tokens}) {
502
                if ( all { $_->($_data) } @{$options->{filter_callbacks}} ) {
503
                    push @tokens_filtered, $_data;
504
                }
505
            }
506
            # Overwrite $tokens with filtered values
507
            $tokens = \@tokens_filtered;
486
        }
508
        }
509
        # Skip mapping if all values has been removed
510
        next unless @{$tokens};
511
487
        if (defined $options->{property}) {
512
        if (defined $options->{property}) {
488
            $_data = {
513
            $tokens = [ map { { $options->{property} => $_ } } @{$tokens} ];
489
                $options->{property} => $_data
490
            }
491
        }
514
        }
492
        if (defined $options->{nonfiling_characters_indicator}) {
515
        if (defined $options->{nonfiling_characters_indicator}) {
493
            my $nonfiling_chars = $meta->{field}->indicator($options->{nonfiling_characters_indicator});
516
            my $nonfiling_chars = $meta->{field}->indicator($options->{nonfiling_characters_indicator});
494
            $nonfiling_chars = looks_like_number($nonfiling_chars) ? int($nonfiling_chars) : 0;
517
            $nonfiling_chars = looks_like_number($nonfiling_chars) ? int($nonfiling_chars) : 0;
495
            if ($nonfiling_chars) {
518
            # Nonfiling chars does not make sense for multiple tokens
496
                $_data = substr $_data, $nonfiling_chars;
519
            # Only apply on first element
497
            }
520
            $tokens->[0] = substr $tokens->[0], $nonfiling_chars;
498
        }
521
        }
499
522
500
        $record_document->{$target} //= [];
523
        $record_document->{$target} //= [];
501
        if( ref $_data eq 'ARRAY' ){
524
        push @{$record_document->{$target}}, @{$tokens};
502
            push @{$record_document->{$target}}, @{$_data};
503
        } else {
504
            push @{$record_document->{$target}}, $_data;
505
        }
506
    }
525
    }
507
}
526
}
508
527
Lines 894-909 sub _field_mappings { Link Here
894
        };
913
        };
895
    }
914
    }
896
    elsif ($target_type eq 'year') {
915
    elsif ($target_type eq 'year') {
897
        $default_options->{filter_callbacks} //= [];
916
        $default_options->{tokenize_callbacks} //= [];
898
        push @{$default_options->{filter_callbacks}}, sub {
917
        # Only accept years containing digits and "u"
918
        push @{$default_options->{tokenize_callbacks}}, sub {
899
            my ($value) = @_;
919
            my ($value) = @_;
900
            my @years = ();
920
            my @years = ( $value =~ /[0-9u]{4}/g );
901
            my @field_years = ( $value =~ /[0-9u]{4}/g );
921
            return @years;
902
            foreach my $year (@field_years){
922
        };
903
                $year =~ s/[u]/0/g;
923
904
                push @years, $year;
924
        $default_options->{value_callbacks} //= [];
905
            }
925
        # Replace "u" with "0" for sorting
906
            return \@years;
926
        push @{$default_options->{value_callbacks}}, sub {
927
            my ($value) = @_;
928
            $value =~ s/[u]/0/g;
929
            return $value;
907
        };
930
        };
908
    }
931
    }
909
932
(-)a/t/Koha/SearchEngine/Elasticsearch.t (-3 / +2 lines)
Lines 357-362 subtest 'Koha::SearchEngine::Elasticsearch::marc_records_to_documents () tests' Link Here
357
        MARC::Field->new('100', '', '', a => 'Author 2'),
357
        MARC::Field->new('100', '', '', a => 'Author 2'),
358
        # MARC::Field->new('210', '', '', a => 'Title 2'),
358
        # MARC::Field->new('210', '', '', a => 'Title 2'),
359
        # MARC::Field->new('245', '', '', a => 'Title: second record'),
359
        # MARC::Field->new('245', '', '', a => 'Title: second record'),
360
        MARC::Field->new('260', '', '', a => 'New York :', b => 'Ace ,', c => '1963-2003'),
360
        MARC::Field->new('999', '', '', c => '1234568'),
361
        MARC::Field->new('999', '', '', c => '1234568'),
361
        MARC::Field->new('952', '', '', 0 => 1, g => 'string where should be numeric', o => $long_callno),
362
        MARC::Field->new('952', '', '', 0 => 1, g => 'string where should be numeric', o => $long_callno),
362
    );
363
    );
Lines 517-523 subtest 'Koha::SearchEngine::Elasticsearch::marc_records_to_documents () tests' Link Here
517
    # Tests for 'year' type
518
    # Tests for 'year' type
518
    is_deeply(
519
    is_deeply(
519
      $docs->[1]->{'copydate'},
520
      $docs->[1]->{'copydate'},
520
      ['1963','2003'],
521
      ['1963', '2003'],
521
      'Second document copydate field should be set correctly'
522
      'Second document copydate field should be set correctly'
522
    );
523
    );
523
    is_deeply(
524
    is_deeply(
Lines 659-665 subtest 'Koha::SearchEngine::Elasticsearch::marc_records_to_documents_array () t Link Here
659
        MARC::Field->new('100', '', '', a => 'Author 2'),
660
        MARC::Field->new('100', '', '', a => 'Author 2'),
660
        # MARC::Field->new('210', '', '', a => 'Title 2'),
661
        # MARC::Field->new('210', '', '', a => 'Title 2'),
661
        # MARC::Field->new('245', '', '', a => 'Title: second record'),
662
        # MARC::Field->new('245', '', '', a => 'Title: second record'),
662
        MARC::Field->new('260', '', '', a => 'New York :', b => 'Ace ,', c => '1963-2003'),
663
        MARC::Field->new('999', '', '', c => '1234568'),
663
        MARC::Field->new('999', '', '', c => '1234568'),
664
        MARC::Field->new('952', '', '', 0 => 1, g => 'string where should be numeric'),
664
        MARC::Field->new('952', '', '', 0 => 1, g => 'string where should be numeric'),
665
    );
665
    );
666
- 

Return to bug 24807