@@ -14,6 +14,27 @@ import (
14
14
"github.com/rs/rest-layer/schema/query"
15
15
)
16
16
17
+ func checkPayload (name string , id interface {}, payload map [string ]interface {}) requestCheckerFunc {
18
+ return func (t * testing.T , vars * requestTestVars ) {
19
+ var item * resource.Item
20
+
21
+ s := vars .Storers [name ]
22
+ q := query.Query {Predicate : query.Predicate {& query.Equal {Field : "id" , Value : id }}, Window : & query.Window {Limit : 1 }}
23
+ if items , err := s .Find (context .Background (), & q ); err != nil {
24
+ t .Errorf ("s.Find failed: %s" , err )
25
+ return
26
+ } else if len (items .Items ) != 1 {
27
+ t .Errorf ("item with ID %v not found" , id )
28
+ return
29
+ } else {
30
+ item = items .Items [0 ]
31
+ }
32
+ if ! reflect .DeepEqual (payload , item .Payload ) {
33
+ t .Errorf ("Unexpected stored payload for item %v:\n expect: %#v\n got: %#v" , id , payload , item .Payload )
34
+ }
35
+ }
36
+ }
37
+
17
38
func TestPutItem (t * testing.T ) {
18
39
now := time .Now ()
19
40
yesterday := now .Add (- 24 * time .Hour )
@@ -50,26 +71,6 @@ func TestPutItem(t *testing.T) {
50
71
Storers : map [string ]resource.Storer {"foo" : s1 , "foo.sub" : s2 },
51
72
}
52
73
}
53
- checkPayload := func (name string , id interface {}, payload map [string ]interface {}) requestCheckerFunc {
54
- return func (t * testing.T , vars * requestTestVars ) {
55
- var item * resource.Item
56
-
57
- s := vars .Storers [name ]
58
- q := query.Query {Predicate : query.Predicate {& query.Equal {Field : "id" , Value : id }}, Window : & query.Window {Limit : 1 }}
59
- if items , err := s .Find (context .Background (), & q ); err != nil {
60
- t .Errorf ("s.Find failed: %s" , err )
61
- return
62
- } else if len (items .Items ) != 1 {
63
- t .Errorf ("item with ID %v not found" , id )
64
- return
65
- } else {
66
- item = items .Items [0 ]
67
- }
68
- if ! reflect .DeepEqual (payload , item .Payload ) {
69
- t .Errorf ("Unexpected stored payload for item %v:\n expect: %#v\n got: %#v" , id , payload , item .Payload )
70
- }
71
- }
72
- }
73
74
74
75
tests := map [string ]requestTest {
75
76
`NoStorage` : {
@@ -315,3 +316,269 @@ func TestPutItem(t *testing.T) {
315
316
t .Run (n , tc .Test )
316
317
}
317
318
}
319
+
320
+ func TestPutItemDefault (t * testing.T ) {
321
+ now := time .Now ()
322
+
323
+ sharedInit := func () * requestTestVars {
324
+ s1 := mem .NewHandler ()
325
+ s1 .Insert (context .Background (), []* resource.Item {
326
+ {ID : "1" , ETag : "a" , Updated : now , Payload : map [string ]interface {}{"id" : "1" , "foo" : "odd" }},
327
+ {ID : "2" , ETag : "b" , Updated : now , Payload : map [string ]interface {}{"id" : "2" , "foo" : "odd" , "bar" : "value" }},
328
+ })
329
+ idx := resource .NewIndex ()
330
+ idx .Bind ("foo" , schema.Schema {
331
+ Fields : schema.Fields {
332
+ "id" : {Sortable : true , Filterable : true },
333
+ "foo" : {Filterable : true },
334
+ "bar" : {Filterable : true , Default : "default" },
335
+ },
336
+ }, s1 , resource .DefaultConf )
337
+ return & requestTestVars {
338
+ Index : idx ,
339
+ Storers : map [string ]resource.Storer {"foo" : s1 },
340
+ }
341
+ }
342
+
343
+ tests := map [string ]requestTest {
344
+ `pathID:not-found,body:valid,default:missing` : {
345
+ Init : sharedInit ,
346
+ NewRequest : func () (* http.Request , error ) {
347
+ body := bytes .NewReader ([]byte (`{"foo": "baz"}` ))
348
+ return http .NewRequest ("PUT" , "/foo/66" , body )
349
+ },
350
+ ResponseCode : http .StatusCreated ,
351
+ ResponseBody : `{"id": "66", "foo": "baz", "bar": "default"}` ,
352
+ ExtraTest : checkPayload ("foo" , "66" , map [string ]interface {}{"id" : "66" , "foo" : "baz" , "bar" : "default" }),
353
+ },
354
+ `pathID:not-found,body:valid,default:set` : {
355
+ Init : sharedInit ,
356
+ NewRequest : func () (* http.Request , error ) {
357
+ body := bytes .NewReader ([]byte (`{"foo": "baz", "bar": "value"}` ))
358
+ return http .NewRequest ("PUT" , "/foo/66" , body )
359
+ },
360
+ ResponseCode : http .StatusCreated ,
361
+ ResponseBody : `{"id": "66", "foo": "baz", "bar": "value"}` ,
362
+ ExtraTest : checkPayload ("foo" , "66" , map [string ]interface {}{"id" : "66" , "foo" : "baz" , "bar" : "value" }),
363
+ },
364
+ `pathID:found,body:valid,default:missing` : {
365
+ Init : sharedInit ,
366
+ NewRequest : func () (* http.Request , error ) {
367
+ body := bytes .NewReader ([]byte (`{"foo": "baz"}` ))
368
+ return http .NewRequest ("PUT" , "/foo/1" , body )
369
+ },
370
+ ResponseCode : http .StatusOK ,
371
+ ResponseBody : `{"id": "1", "foo": "baz"}` ,
372
+ ExtraTest : checkPayload ("foo" , "1" , map [string ]interface {}{"id" : "1" , "foo" : "baz" }),
373
+ },
374
+ `pathID:found,body:valid,default:set` : {
375
+ Init : sharedInit ,
376
+ NewRequest : func () (* http.Request , error ) {
377
+ body := bytes .NewReader ([]byte (`{"foo": "baz", "bar": "value"}` ))
378
+ return http .NewRequest ("PUT" , "/foo/1" , body )
379
+ },
380
+ ResponseCode : http .StatusOK ,
381
+ ResponseBody : `{"id": "1", "foo": "baz", "bar": "value"}` ,
382
+ ExtraTest : checkPayload ("foo" , "1" , map [string ]interface {}{"id" : "1" , "foo" : "baz" , "bar" : "value" }),
383
+ },
384
+ `pathID:found,body:valid,default:delete` : {
385
+ Init : sharedInit ,
386
+ NewRequest : func () (* http.Request , error ) {
387
+ body := bytes .NewReader ([]byte (`{"foo": "baz"}` ))
388
+ return http .NewRequest ("PUT" , "/foo/2" , body )
389
+ },
390
+ ResponseCode : http .StatusOK ,
391
+ ResponseBody : `{"id": "2", "foo": "baz"}` ,
392
+ ExtraTest : checkPayload ("foo" , "2" , map [string ]interface {}{"id" : "2" , "foo" : "baz" }),
393
+ },
394
+ }
395
+
396
+ for n , tc := range tests {
397
+ tc := tc // capture range variable
398
+ t .Run (n , tc .Test )
399
+ }
400
+ }
401
+
402
+ func TestPutItemRequired (t * testing.T ) {
403
+ now := time .Now ()
404
+
405
+ sharedInit := func () * requestTestVars {
406
+ s1 := mem .NewHandler ()
407
+ s1 .Insert (context .Background (), []* resource.Item {
408
+ {ID : "1" , ETag : "a" , Updated : now , Payload : map [string ]interface {}{"id" : "1" , "foo" : "odd" }},
409
+ {ID : "2" , ETag : "b" , Updated : now , Payload : map [string ]interface {}{"id" : "2" , "foo" : "odd" , "bar" : "original" }},
410
+ })
411
+ idx := resource .NewIndex ()
412
+ idx .Bind ("foo" , schema.Schema {
413
+ Fields : schema.Fields {
414
+ "id" : {Sortable : true , Filterable : true },
415
+ "foo" : {Filterable : true },
416
+ "bar" : {Filterable : true , Required : true },
417
+ },
418
+ }, s1 , resource .DefaultConf )
419
+ return & requestTestVars {
420
+ Index : idx ,
421
+ Storers : map [string ]resource.Storer {"foo" : s1 },
422
+ }
423
+ }
424
+
425
+ tests := map [string ]requestTest {
426
+ `pathID:not-found,body:valid,required:missing` : {
427
+ Init : sharedInit ,
428
+ NewRequest : func () (* http.Request , error ) {
429
+ body := bytes .NewReader ([]byte (`{"foo": "baz"}` ))
430
+ return http .NewRequest ("PUT" , "/foo/66" , body )
431
+ },
432
+ ResponseCode : http .StatusUnprocessableEntity ,
433
+ ResponseBody : `{
434
+ "code": 422,
435
+ "message": "Document contains error(s)",
436
+ "issues": {
437
+ "bar": ["required"]
438
+ }
439
+ }` ,
440
+ },
441
+ `pathID:not-found,body:valid,required:set` : {
442
+ Init : sharedInit ,
443
+ NewRequest : func () (* http.Request , error ) {
444
+ body := bytes .NewReader ([]byte (`{"foo": "baz", "bar": "value"}` ))
445
+ return http .NewRequest ("PUT" , "/foo/1" , body )
446
+ },
447
+ ResponseCode : http .StatusOK ,
448
+ ResponseBody : `{"id": "1", "foo": "baz", "bar": "value"}` ,
449
+ ExtraTest : checkPayload ("foo" , "1" , map [string ]interface {}{"id" : "1" , "foo" : "baz" , "bar" : "value" }),
450
+ },
451
+ `pathID:found,body:valid,required:missing` : {
452
+ Init : sharedInit ,
453
+ NewRequest : func () (* http.Request , error ) {
454
+ body := bytes .NewReader ([]byte (`{"foo": "baz"}` ))
455
+ return http .NewRequest ("PUT" , "/foo/1" , body )
456
+ },
457
+ ResponseCode : http .StatusUnprocessableEntity ,
458
+ ResponseBody : `{
459
+ "code": 422,
460
+ "message": "Document contains error(s)",
461
+ "issues": {
462
+ "bar": ["required"]
463
+ }
464
+ }` ,
465
+ },
466
+ `pathID:found,body:valid,required:change` : {
467
+ Init : sharedInit ,
468
+ NewRequest : func () (* http.Request , error ) {
469
+ body := bytes .NewReader ([]byte (`{"foo": "baz", "bar": "value1"}` ))
470
+ return http .NewRequest ("PUT" , "/foo/2" , body )
471
+ },
472
+ ResponseCode : http .StatusOK ,
473
+ ResponseBody : `{"id": "2", "foo": "baz", "bar": "value1"}` ,
474
+ ExtraTest : checkPayload ("foo" , "2" , map [string ]interface {}{"id" : "2" , "foo" : "baz" , "bar" : "value1" }),
475
+ },
476
+ `pathID:found,body:valid,required:delete` : {
477
+ Init : sharedInit ,
478
+ NewRequest : func () (* http.Request , error ) {
479
+ body := bytes .NewReader ([]byte (`{"foo": "baz"}` ))
480
+ return http .NewRequest ("PUT" , "/foo/2" , body )
481
+ },
482
+ ResponseCode : http .StatusUnprocessableEntity ,
483
+ ResponseBody : `{
484
+ "code": 422,
485
+ "message": "Document contains error(s)",
486
+ "issues": {
487
+ "bar": ["required"]
488
+ }
489
+ }` ,
490
+ },
491
+ }
492
+
493
+ for n , tc := range tests {
494
+ tc := tc // capture range variable
495
+ t .Run (n , tc .Test )
496
+ }
497
+ }
498
+
499
+ func TestPutItemRequiredDefault (t * testing.T ) {
500
+ now := time .Now ()
501
+
502
+ sharedInit := func () * requestTestVars {
503
+ s1 := mem .NewHandler ()
504
+ s1 .Insert (context .Background (), []* resource.Item {
505
+ {ID : "1" , ETag : "a" , Updated : now , Payload : map [string ]interface {}{"id" : "1" , "foo" : "odd" }},
506
+ {ID : "2" , ETag : "b" , Updated : now , Payload : map [string ]interface {}{"id" : "2" , "foo" : "odd" , "bar" : "original" }},
507
+ })
508
+ idx := resource .NewIndex ()
509
+ idx .Bind ("foo" , schema.Schema {
510
+ Fields : schema.Fields {
511
+ "id" : {Sortable : true , Filterable : true },
512
+ "foo" : {Filterable : true },
513
+ "bar" : {Filterable : true , Required : true , Default : "default" },
514
+ },
515
+ }, s1 , resource .DefaultConf )
516
+ return & requestTestVars {
517
+ Index : idx ,
518
+ Storers : map [string ]resource.Storer {"foo" : s1 },
519
+ }
520
+ }
521
+
522
+ tests := map [string ]requestTest {
523
+ `pathID:not-found,body:valid,required-default:missing` : {
524
+ Init : sharedInit ,
525
+ NewRequest : func () (* http.Request , error ) {
526
+ body := bytes .NewReader ([]byte (`{"foo": "baz"}` ))
527
+ return http .NewRequest ("PUT" , "/foo/66" , body )
528
+ },
529
+ ResponseCode : http .StatusCreated ,
530
+ ResponseBody : `{"id": "66", "foo": "baz", "bar": "default"}` ,
531
+ ExtraTest : checkPayload ("foo" , "66" , map [string ]interface {}{"id" : "66" , "foo" : "baz" , "bar" : "default" }),
532
+ },
533
+ `pathID:not-found,body:valid,required-default:set` : {
534
+ Init : sharedInit ,
535
+ NewRequest : func () (* http.Request , error ) {
536
+ body := bytes .NewReader ([]byte (`{"foo": "baz", "bar": "value"}` ))
537
+ return http .NewRequest ("PUT" , "/foo/1" , body )
538
+ },
539
+ ResponseCode : http .StatusOK ,
540
+ ResponseBody : `{"id": "1", "foo": "baz", "bar": "value"}` ,
541
+ ExtraTest : checkPayload ("foo" , "1" , map [string ]interface {}{"id" : "1" , "foo" : "baz" , "bar" : "value" }),
542
+ },
543
+ `pathID:found,body:valid,required-default:missing` : {
544
+ Init : sharedInit ,
545
+ NewRequest : func () (* http.Request , error ) {
546
+ body := bytes .NewReader ([]byte (`{"foo": "baz"}` ))
547
+ return http .NewRequest ("PUT" , "/foo/1" , body )
548
+ },
549
+ ResponseCode : http .StatusUnprocessableEntity ,
550
+ ResponseBody : `{
551
+ "code": 422,
552
+ "message": "Document contains error(s)",
553
+ "issues": {
554
+ "bar": ["required"]
555
+ }
556
+ }` ,
557
+ },
558
+ `pathID:found,body:valid,required-default:change` : {
559
+ Init : sharedInit ,
560
+ NewRequest : func () (* http.Request , error ) {
561
+ body := bytes .NewReader ([]byte (`{"foo": "baz", "bar": "value"}` ))
562
+ return http .NewRequest ("PUT" , "/foo/2" , body )
563
+ },
564
+ ResponseCode : http .StatusOK ,
565
+ ResponseBody : `{"id": "2", "foo": "baz", "bar": "value"}` ,
566
+ ExtraTest : checkPayload ("foo" , "2" , map [string ]interface {}{"id" : "2" , "foo" : "baz" , "bar" : "value" }),
567
+ },
568
+ `pathID:found,body:valid,required-default:delete` : {
569
+ Init : sharedInit ,
570
+ NewRequest : func () (* http.Request , error ) {
571
+ body := bytes .NewReader ([]byte (`{"foo": "baz"}` ))
572
+ return http .NewRequest ("PUT" , "/foo/2" , body )
573
+ },
574
+ ResponseCode : http .StatusOK ,
575
+ ResponseBody : `{"id": "2", "foo": "baz", "bar": "default"}` ,
576
+ ExtraTest : checkPayload ("foo" , "2" , map [string ]interface {}{"id" : "2" , "foo" : "baz" , "bar" : "default" }),
577
+ },
578
+ }
579
+
580
+ for n , tc := range tests {
581
+ tc := tc // capture range variable
582
+ t .Run (n , tc .Test )
583
+ }
584
+ }
0 commit comments