Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
20 changes: 17 additions & 3 deletions lib/jsonapi/request_parser.rb
Original file line number Diff line number Diff line change
Expand Up @@ -217,8 +217,14 @@ def parse_include_directives(raw_include)
fail JSONAPI::Exceptions::ParametersNotAllowed.new([:include])
end

included_resources = CSV.parse_line(raw_include)
return if included_resources.nil?
included_resources = []
begin
included_resources += CSV.parse_line(raw_include)
rescue CSV::MalformedCSVError
fail JSONAPI::Exceptions::InvalidInclude.new(format_key(@resource_klass._type), raw_include)
end

return if included_resources.empty?

result = included_resources.map do |included_resource|
check_include(@resource_klass, included_resource.partition('.'))
Expand Down Expand Up @@ -264,7 +270,15 @@ def parse_sort_criteria(sort_criteria)
fail JSONAPI::Exceptions::ParametersNotAllowed.new([:sort])
end

@sort_criteria = CSV.parse_line(URI.unescape(sort_criteria)).collect do |sort|
sorts = []
begin
raw = URI.unescape(sort_criteria)
sorts += CSV.parse_line(raw)
rescue CSV::MalformedCSVError
fail JSONAPI::Exceptions::InvalidSortCriteria.new(format_key(@resource_klass._type), raw)
end

@sort_criteria = sorts.collect do |sort|
if sort.start_with?('-')
sort_criteria = { field: unformat_key(sort[1..-1]).to_s }
sort_criteria[:direction] = :desc
Expand Down
6 changes: 5 additions & 1 deletion lib/jsonapi/resource.rb
Original file line number Diff line number Diff line change
Expand Up @@ -807,7 +807,11 @@ def is_filter_relationship?(filter)
def verify_filter(filter, raw, context = nil)
filter_values = []
if raw.present?
filter_values += raw.is_a?(String) ? CSV.parse_line(raw) : [raw]
begin
filter_values += raw.is_a?(String) ? CSV.parse_line(raw) : [raw]
rescue CSV::MalformedCSVError
filter_values << raw
end
end

strategy = _allowed_filters.fetch(filter, Hash.new)[:verify]
Expand Down
29 changes: 29 additions & 0 deletions test/integration/requests/request_test.rb
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,15 @@ def test_get_underscored_key
JSONAPI.configuration = original_config
end

def test_filter_with_value_containing_double_quote
original_config = JSONAPI.configuration.dup
JSONAPI.configuration.json_key_format = :underscored_key
get '/iso_currencies?filter[country_name]=%22'
assert_jsonapi_response 200
ensure
JSONAPI.configuration = original_config
end

def test_get_underscored_key_filtered
original_config = JSONAPI.configuration.dup
JSONAPI.configuration.json_key_format = :underscored_key
Expand Down Expand Up @@ -1063,6 +1072,26 @@ def test_sort_parameter_not_allowed
JSONAPI.configuration.allow_sort = true
end

def test_sort_parameter_quoted
get '/api/v2/books?sort=%22title%22', headers: { 'Accept' => JSONAPI::MEDIA_TYPE }
assert_jsonapi_response 200
end

def test_sort_parameter_openquoted
get '/api/v2/books?sort=%22title', headers: { 'Accept' => JSONAPI::MEDIA_TYPE }
assert_jsonapi_response 400
end

def test_include_parameter_quoted
get '/api/v2/posts?include=%22author%22', headers: { 'Accept' => JSONAPI::MEDIA_TYPE }
assert_jsonapi_response 200
end

def test_include_parameter_openquoted
get '/api/v2/posts?include=%22author', headers: { 'Accept' => JSONAPI::MEDIA_TYPE }
assert_jsonapi_response 400
end

def test_getting_different_resources_when_sti
assert_cacheable_jsonapi_get '/vehicles'
types = json_response['data'].map{|r| r['type']}.sort
Expand Down