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

(-)a/Koha/Object.pm (-8 / +14 lines)
Lines 553-561 sub to_api { Link Here
553
    my ( $self, $params ) = @_;
553
    my ( $self, $params ) = @_;
554
    my $json_object = $self->TO_JSON;
554
    my $json_object = $self->TO_JSON;
555
555
556
    # Make sure we duplicate the $params variable to avoid
557
    # breaking calls in a loop (Koha::Objects->to_api)
558
    $params = defined $params ? {%$params} : {};
559
560
    # children should be able to handle without
561
    my $embeds    = delete $params->{embed};
562
    my $av_expand = delete $params->{av_expand};
563
556
    # coded values handling
564
    # coded values handling
557
    my $avs = {};
565
    my $avs = {};
558
    if ( $params->{av_expand} and $self->can('api_av_mapping') ) {
566
    if ( $av_expand and $self->can('api_av_mapping') ) {
559
        $avs = $self->api_av_mapping($params);
567
        $avs = $self->api_av_mapping($params);
560
    }
568
    }
561
569
Lines 565-571 sub to_api { Link Here
565
            delete $json_object->{$field} unless any { $_ eq $field } @{ $self->public_read_list };
573
            delete $json_object->{$field} unless any { $_ eq $field } @{ $self->public_read_list };
566
        }
574
        }
567
575
568
        if ( $params->{av_expand} ) {
576
        if ( $av_expand ) {
569
            foreach my $field (keys %{$avs}) {
577
            foreach my $field (keys %{$avs}) {
570
                delete $avs->{$field}
578
                delete $avs->{$field}
571
                    unless any { $_ eq $field } @{ $self->public_read_list };
579
                    unless any { $_ eq $field } @{ $self->public_read_list };
Lines 598-609 sub to_api { Link Here
598
    }
606
    }
599
607
600
    $json_object->{_str} = $avs
608
    $json_object->{_str} = $avs
601
      if $params->{av_expand};
609
      if $av_expand;
602
603
    # Make sure we duplicate the $params variable to avoid
604
    # breaking calls in a loop (Koha::Objects->to_api)
605
    $params    = {%$params};
606
    my $embeds = delete $params->{embed};
607
610
608
    if ($embeds) {
611
    if ($embeds) {
609
        foreach my $embed ( keys %{$embeds} ) {
612
        foreach my $embed ( keys %{$embeds} ) {
Lines 617-622 sub to_api { Link Here
617
                my $curr = $embed;
620
                my $curr = $embed;
618
                my $next = $embeds->{$curr}->{children};
621
                my $next = $embeds->{$curr}->{children};
619
622
623
                $params->{av_expand} = 1
624
                  if $embeds->{$embed}->{av_expand};
625
620
                my $children = $self->$curr;
626
                my $children = $self->$curr;
621
627
622
                if ( defined $children and ref($children) eq 'ARRAY' ) {
628
                if ( defined $children and ref($children) eq 'ARRAY' ) {
(-)a/Koha/REST/Plugin/Objects.pm (-2 / +2 lines)
Lines 54-60 the requested object. It passes through any embeds if specified. Link Here
54
54
55
            # Look for embeds
55
            # Look for embeds
56
            my $embed     = $c->stash('koha.embed');
56
            my $embed     = $c->stash('koha.embed');
57
            my $av_expand = $c->req->headers->header('x-koha-av-expand');
57
            my $av_expand = $c->stash('koha.av_expand');
58
58
59
            # Generate prefetches for embedded stuff
59
            # Generate prefetches for embedded stuff
60
            $c->dbic_merge_prefetch(
60
            $c->dbic_merge_prefetch(
Lines 100-106 shouldn't be called twice in it. Link Here
100
            my $is_public = $c->stash('is_public');
100
            my $is_public = $c->stash('is_public');
101
            # Look for embeds
101
            # Look for embeds
102
            my $embed     = $c->stash('koha.embed');
102
            my $embed     = $c->stash('koha.embed');
103
            my $av_expand = $c->req->headers->header('x-koha-av-expand');
103
            my $av_expand = $c->stash('koha.av_expand');
104
104
105
            # Merge sorting into query attributes
105
            # Merge sorting into query attributes
106
            $c->dbic_merge_sorting(
106
            $c->dbic_merge_sorting(
(-)a/Koha/REST/Plugin/Query.pm (-1 / +9 lines)
Lines 242-248 Unwraps and stashes the x-koha-embed headers for use later query construction Link Here
242
            if ($embed_header) {
242
            if ($embed_header) {
243
                my $THE_embed = {};
243
                my $THE_embed = {};
244
                foreach my $embed_req ( split /\s*,\s*/, $embed_header ) {
244
                foreach my $embed_req ( split /\s*,\s*/, $embed_header ) {
245
                    _merge_embed( _parse_embed($embed_req), $THE_embed );
245
                    if ( $embed_req eq '+av_expand' ) {    # special case
246
                        $c->stash( 'koha.av_expand' => 1 );
247
                    } else {
248
                        _merge_embed( _parse_embed($embed_req), $THE_embed );
249
                    }
246
                }
250
                }
247
251
248
                $c->stash( 'koha.embed' => $THE_embed )
252
                $c->stash( 'koha.embed' => $THE_embed )
Lines 364-369 sub _parse_embed { Link Here
364
            my $key = $+{relation} . "_count";
368
            my $key = $+{relation} . "_count";
365
            $result->{$key} = { is_count => 1 };
369
            $result->{$key} = { is_count => 1 };
366
        }
370
        }
371
        elsif ( $curr =~ m/^(?<relation>.*)\+av_expand/ ) {
372
            my $key = $+{relation};
373
            $result->{$key} = { av_expand => 1 };
374
        }
367
        else {
375
        else {
368
            $result->{$curr} = {};
376
            $result->{$curr} = {};
369
        }
377
        }
(-)a/t/Koha/REST/Plugin/Query.t (-7 / +25 lines)
Lines 210-220 get '/stash_embed' => sub { Link Here
210
    my $c = shift;
210
    my $c = shift;
211
211
212
    $c->stash_embed();
212
    $c->stash_embed();
213
    my $embed = $c->stash('koha.embed');
213
    my $embed     = $c->stash('koha.embed');
214
    my $av_expand = $c->stash('koha.av_expand');
214
215
215
    $c->render(
216
    $c->render(
216
        status => 200,
217
        status => 200,
217
        json   => $embed
218
        json   => {
219
            av_expand => $av_expand,
220
            embed     => $embed,
221
        }
218
    );
222
    );
219
};
223
};
220
224
Lines 429-452 subtest '_build_query_params_from_api' => sub { Link Here
429
433
430
subtest 'stash_embed() tests' => sub {
434
subtest 'stash_embed() tests' => sub {
431
435
432
    plan tests => 8;
436
    plan tests => 14;
433
437
434
    my $t = Test::Mojo->new;
438
    my $t = Test::Mojo->new;
435
439
436
    $t->get_ok( '/stash_embed' => { 'x-koha-embed' => 'checkouts,checkouts.item' } )
440
    $t->get_ok( '/stash_embed' => { 'x-koha-embed' => 'checkouts,checkouts.item' } )
437
      ->json_is( { checkouts => { children => { item => { } } } } );
441
      ->json_is( '/embed' => { checkouts => { children => { item => { } } } } );
438
442
439
    $t->get_ok( '/stash_embed' => { 'x-koha-embed' => 'checkouts,checkouts.item,library' } )
443
    $t->get_ok( '/stash_embed' => { 'x-koha-embed' => 'checkouts,checkouts.item,library' } )
440
      ->json_is( { checkouts => { children => { item => {} } }, library => {} } );
444
      ->json_is( '/embed' => { checkouts => { children => { item => {} } }, library => {} } );
441
445
442
    $t->get_ok( '/stash_embed' => { 'x-koha-embed' => 'holds+count' } )
446
    $t->get_ok( '/stash_embed' => { 'x-koha-embed' => 'holds+count' } )
443
      ->json_is( { holds_count => { is_count => 1 } } );
447
      ->json_is( '/embed' => { holds_count => { is_count => 1 } } );
444
448
445
    $t->get_ok( '/stash_embed' => { 'x-koha-embed' => 'checkouts,checkouts.item,patron' } )
449
    $t->get_ok( '/stash_embed' => { 'x-koha-embed' => 'checkouts,checkouts.item,patron' } )
446
      ->json_is({
450
      ->json_is( '/embed' => {
447
            checkouts => { children => { item => {} } },
451
            checkouts => { children => { item => {} } },
448
            patron    => {}
452
            patron    => {}
449
        });
453
        });
454
455
    $t->get_ok( '/stash_embed' => { 'x-koha-embed' => 'checkouts,checkouts.item+av_expand,patron+av_expand' } )
456
      ->json_is( '/embed' => {
457
            checkouts => { children => { item => { av_expand => 1 } } },
458
            patron    => { av_expand => 1 }
459
        })
460
      ->json_is( '/av_expand' => undef );
461
462
    $t->get_ok( '/stash_embed' => { 'x-koha-embed' => 'checkouts+av_expand,checkouts.item,patron,+av_expand' } )
463
      ->json_is( '/embed' => {
464
            checkouts => { children => { item => { } }, av_expand => 1 },
465
            patron    => { }
466
        })
467
      ->json_is( '/av_expand' => 1 );
450
};
468
};
451
469
452
subtest 'stash_overrides() tests' => sub {
470
subtest 'stash_overrides() tests' => sub {
(-)a/t/db_dependent/Koha/Object.t (-2 / +24 lines)
Lines 226-232 subtest 'TO_JSON tests' => sub { Link Here
226
226
227
subtest "to_api() tests" => sub {
227
subtest "to_api() tests" => sub {
228
228
229
    plan tests => 30;
229
    plan tests => 31;
230
230
231
    $schema->storage->txn_begin;
231
    $schema->storage->txn_begin;
232
232
Lines 303-316 subtest "to_api() tests" => sub { Link Here
303
    is($biblio_api->{items}->[0]->{holds}->[0]->{hold_id}, $hold->reserve_id, 'Hold matches');
303
    is($biblio_api->{items}->[0]->{holds}->[0]->{hold_id}, $hold->reserve_id, 'Hold matches');
304
    is_deeply($biblio_api->{biblioitem}, $biblio->biblioitem->to_api, 'More than one root');
304
    is_deeply($biblio_api->{biblioitem}, $biblio->biblioitem->to_api, 'More than one root');
305
305
306
    my $_str = {
307
        location => {
308
            category => 'ASD',
309
            str      => 'Estante alto',
310
            type     => 'av'
311
        }
312
    };
313
314
    # mock Koha::Item so it implements 'api_av_mapping'
315
    my $item_mock = Test::MockModule->new('Koha::Item');
316
    $item_mock->mock(
317
        'api_av_mapping',
318
        sub {
319
            return $_str;
320
        }
321
    );
322
306
    my $hold_api = $hold->to_api(
323
    my $hold_api = $hold->to_api(
307
        {
324
        {
308
            embed => { 'item' => {} }
325
            embed => { 'item' => { av_expand => 1 } }
309
        }
326
        }
310
    );
327
    );
311
328
312
    is( ref($hold_api->{item}), 'HASH', 'Single nested object works correctly' );
329
    is( ref($hold_api->{item}), 'HASH', 'Single nested object works correctly' );
313
    is( $hold_api->{item}->{item_id}, $item->itemnumber, 'Object embedded correctly' );
330
    is( $hold_api->{item}->{item_id}, $item->itemnumber, 'Object embedded correctly' );
331
    is_deeply(
332
        $hold_api->{item}->{_str},
333
        $_str,
334
        '_str correctly added to nested embed'
335
    );
314
336
315
    # biblio with no items
337
    # biblio with no items
316
    my $new_biblio = $builder->build_sample_biblio;
338
    my $new_biblio = $builder->build_sample_biblio;
(-)a/t/db_dependent/Koha/REST/Plugin/Objects.t (-6 / +6 lines)
Lines 38-43 plugin 'Koha::REST::Plugin::Pagination'; Link Here
38
get '/cities' => sub {
38
get '/cities' => sub {
39
    my $c = shift;
39
    my $c = shift;
40
    $c->validation->output($c->req->params->to_hash);
40
    $c->validation->output($c->req->params->to_hash);
41
    $c->stash_embed;
41
    my $cities = $c->objects->search(Koha::Cities->new);
42
    my $cities = $c->objects->search(Koha::Cities->new);
42
    $c->render( status => 200, json => $cities );
43
    $c->render( status => 200, json => $cities );
43
};
44
};
Lines 45-50 get '/cities' => sub { Link Here
45
get '/cities/:city_id' => sub {
46
get '/cities/:city_id' => sub {
46
    my $c = shift;
47
    my $c = shift;
47
    my $id = $c->stash("city_id");
48
    my $id = $c->stash("city_id");
49
    $c->stash_embed;
48
    my $city = $c->objects->find(Koha::Cities->new, $id);
50
    my $city = $c->objects->find(Koha::Cities->new, $id);
49
    $c->render( status => 200, json => $city );
51
    $c->render( status => 200, json => $city );
50
};
52
};
Lines 712-718 subtest 'objects.find helper with expanded authorised values' => sub { Link Here
712
        }
714
        }
713
    );
715
    );
714
716
715
    $t->get_ok( '/cities/' . $manuel->id => { 'x-koha-av-expand' => 1 } )
717
    $t->get_ok( '/cities/' . $manuel->id => { 'x-koha-embed' => '+av_expand' } )
716
      ->status_is(200)->json_is( '/name' => 'Manuel' )
718
      ->status_is(200)->json_is( '/name' => 'Manuel' )
717
      ->json_has('/_str')
719
      ->json_has('/_str')
718
      ->json_is( '/_str/country/type'     => 'av' )
720
      ->json_is( '/_str/country/type'     => 'av' )
Lines 723-729 subtest 'objects.find helper with expanded authorised values' => sub { Link Here
723
      ->status_is(200)->json_is( '/name' => 'Manuel' )
725
      ->status_is(200)->json_is( '/name' => 'Manuel' )
724
      ->json_hasnt('/_str');
726
      ->json_hasnt('/_str');
725
727
726
    $t->get_ok( '/cities/' . $manuela->id => { 'x-koha-av-expand' => 1 } )
728
    $t->get_ok( '/cities/' . $manuela->id => { 'x-koha-embed' => '+av_expand' } )
727
      ->status_is(200)->json_is( '/name' => 'Manuela' )
729
      ->status_is(200)->json_is( '/name' => 'Manuela' )
728
      ->json_has('/_str')
730
      ->json_has('/_str')
729
      ->json_is( '/_str/country/type'     => 'av' )
731
      ->json_is( '/_str/country/type'     => 'av' )
Lines 827-833 subtest 'objects.search helper with expanded authorised values' => sub { Link Here
827
    );
829
    );
828
830
829
    $t->get_ok( '/cities?name=manuel&_per_page=4&_page=1&_match=starts_with' =>
831
    $t->get_ok( '/cities?name=manuel&_per_page=4&_page=1&_match=starts_with' =>
830
          { 'x-koha-av-expand' => 1 } )->status_is(200)
832
          { 'x-koha-embed' => '+av_expand' } )->status_is(200)
831
      ->json_has('/0')->json_has('/1')->json_hasnt('/2')
833
      ->json_has('/0')->json_has('/1')->json_hasnt('/2')
832
      ->json_is( '/0/name' => 'Manuel' )
834
      ->json_is( '/0/name' => 'Manuel' )
833
      ->json_has('/0/_str')
835
      ->json_has('/0/_str')
Lines 840-847 subtest 'objects.search helper with expanded authorised values' => sub { Link Here
840
      ->json_is( '/1/_str/country/type'     => 'av' )
842
      ->json_is( '/1/_str/country/type'     => 'av' )
841
      ->json_is( '/1/_str/country/category' => $cat->category_name );
843
      ->json_is( '/1/_str/country/category' => $cat->category_name );
842
844
843
    $t->get_ok( '/cities?name=manuel&_per_page=4&_page=1&_match=starts_with' =>
845
    $t->get_ok( '/cities?name=manuel&_per_page=4&_page=1&_match=starts_with' )->status_is(200)
844
          { 'x-koha-av-expand' => 0 } )->status_is(200)
845
      ->json_has('/0')->json_has('/1')->json_hasnt('/2')
846
      ->json_has('/0')->json_has('/1')->json_hasnt('/2')
846
      ->json_is( '/0/name' => 'Manuel' )->json_hasnt('/0/_str')
847
      ->json_is( '/0/name' => 'Manuel' )->json_hasnt('/0/_str')
847
      ->json_is( '/1/name' => 'Manuela' )->json_hasnt('/1/_str');
848
      ->json_is( '/1/name' => 'Manuela' )->json_hasnt('/1/_str');
848
- 

Return to bug 26635