From 4f86a43513d498e230d8eedf3f36d3c0f9fa7b6e Mon Sep 17 00:00:00 2001 From: Adam Worrall Date: Wed, 8 Apr 2015 00:39:18 -0400 Subject: [PATCH 1/5] refactor #parse_add_operation --- lib/jsonapi/request.rb | 13 +++---------- 1 file changed, 3 insertions(+), 10 deletions(-) diff --git a/lib/jsonapi/request.rb b/lib/jsonapi/request.rb index a09f35275..9e465703b 100644 --- a/lib/jsonapi/request.rb +++ b/lib/jsonapi/request.rb @@ -198,16 +198,9 @@ def check_sort_criteria(resource_klass, sort_criteria) end def parse_add_operation(data) - if data.is_a?(Array) - data.each do |p| - @operations.push JSONAPI::CreateResourceOperation.new(@resource_klass, - parse_params(verify_and_remove_type(p), - @resource_klass.createable_fields(@context))) - end - else - @operations.push JSONAPI::CreateResourceOperation.new(@resource_klass, - parse_params(verify_and_remove_type(data), - @resource_klass.createable_fields(@context))) + Array.wrap(data).each do |p| + values = parse_params(verify_and_remove_type(p), @resource_klass.createable_fields(@context)) + @operations.push JSONAPI::CreateResourceOperation.new(@resource_klass, values) end rescue JSONAPI::Exceptions::Error => e @errors.concat(e.errors) From 4aca6d7828c7d360438874ad9f5e8e44cbb30b69 Mon Sep 17 00:00:00 2001 From: Adam Worrall Date: Wed, 8 Apr 2015 07:25:33 -0400 Subject: [PATCH 2/5] add failing test for minimal POST POST with only 'type' key is not triggering a save on the activerecord model, but no errors are reported. This leads to an incorrect 201 status. --- test/integration/requests/request_test.rb | 13 ++++++++++++- 1 file changed, 12 insertions(+), 1 deletion(-) diff --git a/test/integration/requests/request_test.rb b/test/integration/requests/request_test.rb index 4050a7724..f4a8ef759 100644 --- a/test/integration/requests/request_test.rb +++ b/test/integration/requests/request_test.rb @@ -156,6 +156,17 @@ def test_post_single assert_equal 201, status end + def test_post_single_minimal_invalid + post '/posts', + { + 'data' => { + 'type' => 'posts' + } + }.to_json, "CONTENT_TYPE" => JSONAPI::MEDIA_TYPE + + assert_equal 422, status + end + def test_update_association_without_content_type ruby = Section.find_by(name: 'ruby') patch '/posts/3/links/section', { 'data' => {type: 'sections', id: ruby.id.to_s }}.to_json @@ -189,7 +200,7 @@ def test_patch_update_association_has_many_acts_as_set def test_post_update_association_has_many rogue = Comment.find_by(body: 'Rogue Comment Here') post '/posts/5/links/comments', { 'data' => [{type: 'comments', id: rogue.id.to_s }]}.to_json, "CONTENT_TYPE" => JSONAPI::MEDIA_TYPE - + assert_equal 204, status end From 01fb2de6485a40e4e52e24dd56df426c02020f87 Mon Sep 17 00:00:00 2001 From: Adam Worrall Date: Wed, 8 Apr 2015 07:35:12 -0400 Subject: [PATCH 3/5] add is_new check to #change. Resource#create_model instantiates an activerecord model, but doesn't trigger a save. The save comes in _replace_fields, but if field_data[:attributes] is empty it never sets @save_needed. I'm sure this isn't the best way to solve this issue, but it works for now. --- lib/jsonapi/resource.rb | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/lib/jsonapi/resource.rb b/lib/jsonapi/resource.rb index eca620854..e1cb7212b 100644 --- a/lib/jsonapi/resource.rb +++ b/lib/jsonapi/resource.rb @@ -46,7 +46,7 @@ def change(callback) @changing = true run_callbacks callback do yield - save if @save_needed + save if @save_needed || is_new? end end end From d17ed92e4e944bcce9133cfb74e9e4b70eb9638b Mon Sep 17 00:00:00 2001 From: Adam Worrall Date: Wed, 8 Apr 2015 08:28:04 -0400 Subject: [PATCH 4/5] correct indentation --- lib/jsonapi/request.rb | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/lib/jsonapi/request.rb b/lib/jsonapi/request.rb index 9e465703b..8fda570fa 100644 --- a/lib/jsonapi/request.rb +++ b/lib/jsonapi/request.rb @@ -199,8 +199,8 @@ def check_sort_criteria(resource_klass, sort_criteria) def parse_add_operation(data) Array.wrap(data).each do |p| - values = parse_params(verify_and_remove_type(p), @resource_klass.createable_fields(@context)) - @operations.push JSONAPI::CreateResourceOperation.new(@resource_klass, values) + values = parse_params(verify_and_remove_type(p), @resource_klass.createable_fields(@context)) + @operations.push JSONAPI::CreateResourceOperation.new(@resource_klass, values) end rescue JSONAPI::Exceptions::Error => e @errors.concat(e.errors) From 72b4495c3213da7970fabc5d51e4c38cde133491 Mon Sep 17 00:00:00 2001 From: Larry Gebhardt Date: Wed, 8 Apr 2015 10:23:23 -0400 Subject: [PATCH 5/5] Adds tests posting empty data and posting data with only required type --- test/integration/requests/request_test.rb | 24 +++++++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/test/integration/requests/request_test.rb b/test/integration/requests/request_test.rb index f4a8ef759..14a17ba92 100644 --- a/test/integration/requests/request_test.rb +++ b/test/integration/requests/request_test.rb @@ -156,6 +156,30 @@ def test_post_single assert_equal 201, status end + def test_post_single_missing_data_contents + post '/posts', + { + 'data' => { + } + }.to_json, "CONTENT_TYPE" => JSONAPI::MEDIA_TYPE + + assert_equal 400, status + end + + def test_post_single_minimal_valid + post '/comments', + { + 'data' => { + 'type' => 'comments' + } + }.to_json, "CONTENT_TYPE" => JSONAPI::MEDIA_TYPE + + assert_equal 201, status + assert_nil json_response['data']['body'] + assert_nil json_response['data']['links']['post']['linkage'] + assert_nil json_response['data']['links']['author']['linkage'] + end + def test_post_single_minimal_invalid post '/posts', {