class JSONAPI::Parser::Document
Constants
- JSONAPI_OBJECT_KEYS
- RELATIONSHIP_KEYS
- RELATIONSHIP_LINK_KEYS
- RESOURCE_IDENTIFIER_KEYS
- TOP_LEVEL_KEYS
Public Class Methods
ensure!(condition, message)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 183 def self.ensure!(condition, message) raise InvalidDocument, message unless condition end
parse!(document)
click to toggle source
Validate the structure of a JSONAPI
response document.
@param [Hash] document The input JSONAPI
document. @raise [JSONAPI::Parser::InvalidDocument] if document is invalid.
# File lib/jsonapi/parser/document.rb, line 16 def self.parse!(document) ensure!(document.is_a?(Hash), 'A JSON object MUST be at the root of every JSON API request ' \ 'and response containing data.') ensure!(!(document.keys & TOP_LEVEL_KEYS).empty?, "A document MUST contain at least one of #{TOP_LEVEL_KEYS}.") ensure!(!(document.key?('data') && document.key?('errors')), 'The members data and errors MUST NOT coexist in the same ' \ 'document.') ensure!(document.key?('data') || !document.key?('included'), 'If a document does not contain a top-level data key, the ' \ 'included member MUST NOT be present either.') parse_data!(document['data']) if document.key?('data') parse_errors!(document['errors']) if document.key?('errors') parse_meta!(document['meta']) if document.key?('meta') parse_jsonapi!(document['jsonapi']) if document.key?('jsonapi') parse_included!(document['included']) if document.key?('included') parse_links!(document['links']) if document.key?('links') end
parse_attributes!(attrs)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 67 def self.parse_attributes!(attrs) ensure!(attrs.is_a?(Hash), 'The value of the attributes key MUST be an object.') end
parse_data!(data)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 37 def self.parse_data!(data) if data.is_a?(Hash) parse_resource!(data) elsif data.is_a?(Array) data.each { |res| parse_resource!(res) } elsif data.nil? # Do nothing else ensure!(false, 'Primary data must be either nil, an object or an array.') end end
parse_error!(_error)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 177 def self.parse_error!(_error) # NOTE(beauby): Do nothing for now, as errors are under-specified as of # JSONAPI 1.0 end
parse_errors!(errors)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 170 def self.parse_errors!(errors) ensure!(errors.is_a?(Array), 'Top level errors member must be an array.') errors.each { |error| parse_error!(error) } end
parse_included!(included)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 163 def self.parse_included!(included) ensure!(included.is_a?(Array), 'Top level included member must be an array.') included.each { |res| parse_resource!(res) } end
parse_jsonapi!(jsonapi)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 149 def self.parse_jsonapi!(jsonapi) ensure!(jsonapi.is_a?(Hash), 'A JSONAPI object must be an object.') unexpected_keys = jsonapi.keys - JSONAPI_OBJECT_KEYS ensure!(unexpected_keys.empty?, 'Unexpected members for JSONAPI object: ' \ "#{JSONAPI_OBJECT_KEYS}.") if jsonapi.key?('version') ensure!(jsonapi['version'].is_a?(String), "Value of JSONAPI's version member must be a string.") end parse_meta!(jsonapi['meta']) if jsonapi.key?('meta') end
parse_link!(link)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 131 def self.parse_link!(link) if link.is_a?(String) # Do nothing elsif link.is_a?(Hash) # TODO(beauby): Pending clarification request # https://github.com/json-api/json-api/issues/1103 else ensure!(false, 'The value of a link must be either a string or an object.') end end
parse_links!(links)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 125 def self.parse_links!(links) ensure!(links.is_a?(Hash), 'A links object must be an object.') links.values.each { |link| parse_link!(link) } end
parse_meta!(meta)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 144 def self.parse_meta!(meta) ensure!(meta.is_a?(Hash), 'A meta object must be an object.') end
parse_primary_resource!(res)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 51 def self.parse_primary_resource!(res) ensure!(res.is_a?(Hash), 'A resource object must be an object.') ensure!(res.key?('type'), 'A resource object must have a type.') parse_attributes!(res['attributes']) if res.key?('attributes') parse_relationships!(res['relationships']) if res.key?('relationships') parse_links!(res['links']) if res.key?('links') parse_meta!(res['meta']) if res.key?('meta') end
parse_relationship!(rel)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 80 def self.parse_relationship!(rel) ensure!(rel.is_a?(Hash), 'A relationship object must be an object.') ensure!(!rel.keys.empty?, 'A relationship object MUST contain at least one of ' \ "#{RELATIONSHIP_KEYS}") parse_relationship_data!(rel['data']) if rel.key?('data') parse_relationship_links!(rel['links']) if rel.key?('links') parse_meta!(rel['meta']) if rel.key?('meta') end
parse_relationship_data!(data)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 91 def self.parse_relationship_data!(data) if data.is_a?(Hash) parse_resource_identifier!(data) elsif data.is_a?(Array) data.each { |ri| parse_resource_identifier!(ri) } elsif data.nil? # Do nothing else ensure!(false, 'Relationship data must be either nil, an object or ' \ 'an array.') end end
parse_relationship_links!(links)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 117 def self.parse_relationship_links!(links) parse_links!(links) ensure!(!(links.keys & RELATIONSHIP_LINK_KEYS).empty?, 'A relationship link must contain at least one of '\ "#{RELATIONSHIP_LINK_KEYS}.") end
parse_relationships!(rels)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 73 def self.parse_relationships!(rels) ensure!(rels.is_a?(Hash), 'The value of the relationships key MUST be an object') rels.values.each { |rel| parse_relationship!(rel) } end
parse_resource!(res)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 61 def self.parse_resource!(res) parse_primary_resource!(res) ensure!(res.key?('id'), 'A resource object must have an id.') end
parse_resource_identifier!(ri)
click to toggle source
@api private
# File lib/jsonapi/parser/document.rb, line 105 def self.parse_resource_identifier!(ri) ensure!(ri.is_a?(Hash), 'A resource identifier object must be an object') ensure!(RESOURCE_IDENTIFIER_KEYS & ri.keys == RESOURCE_IDENTIFIER_KEYS, 'A resource identifier object MUST contain ' \ "#{RESOURCE_IDENTIFIER_KEYS} members.") ensure!(ri['id'].is_a?(String), 'Member id must be a string.') ensure!(ri['type'].is_a?(String), 'Member type must be a string.') parse_meta!(ri['meta']) if ri.key?('meta') end