Skip to content

Commit

Permalink
Finish 3.2.4
Browse files Browse the repository at this point in the history
  • Loading branch information
gkellogg committed Apr 15, 2023
2 parents 37d6180 + 73ee226 commit 0786a2e
Show file tree
Hide file tree
Showing 16 changed files with 477 additions and 205 deletions.
17 changes: 5 additions & 12 deletions .github/workflows/ci.yml
Expand Up @@ -19,16 +19,10 @@ jobs:
strategy:
fail-fast: false
matrix:
ruby:
- 2.6
- 2.7
- "3.0"
- 3.1
- ruby-head
- jruby
ruby: [2.6, 2.7, '3.0', 3.1, 3.2, ruby-head, jruby]
steps:
- name: Clone repository
uses: actions/checkout@v2
uses: actions/checkout@v3
- name: Set up Ruby
uses: ruby/setup-ruby@v1
with:
Expand All @@ -48,15 +42,14 @@ jobs:
runs-on: windows-latest
env:
CI: true
ALLOW_FAILURES: ${{ endsWith(matrix.ruby, 'head') || matrix.ruby == 'jruby' }}
ALLOW_FAILURES: ${{ matrix.ruby == '3.2' || matrix.ruby == 'jruby' }}
strategy:
fail-fast: false
matrix:
ruby:
- 3.1
ruby: [3.1, 3.2]
steps:
- name: Clone repository
uses: actions/checkout@v2
uses: actions/checkout@v3
- name: Set up Ruby
uses: ruby/setup-ruby@v1
with:
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/generate-docs.yml
Expand Up @@ -10,7 +10,7 @@ jobs:
name: Update gh-pages with docs
steps:
- name: Clone repository
uses: actions/checkout@v2
uses: actions/checkout@v3
- name: Set up Ruby
uses: ruby/setup-ruby@v1
with:
Expand Down
2 changes: 1 addition & 1 deletion VERSION
@@ -1 +1 @@
3.2.3
3.2.4
14 changes: 7 additions & 7 deletions json-ld.gemspec
Expand Up @@ -32,24 +32,24 @@ Gem::Specification.new do |gem|

gem.required_ruby_version = '>= 2.6'
gem.requirements = []
gem.add_runtime_dependency 'rdf', '~> 3.2', '>= 3.2.9'
gem.add_runtime_dependency 'rdf', '~> 3.2', '>= 3.2.10'
gem.add_runtime_dependency 'multi_json', '~> 1.15'
gem.add_runtime_dependency 'link_header', '~> 0.0', '>= 0.0.8'
gem.add_runtime_dependency 'json-canonicalization', '~> 0.3'
gem.add_runtime_dependency 'htmlentities', '~> 4.3'
gem.add_runtime_dependency 'rack', '~> 2.2'
gem.add_runtime_dependency 'htmlentities', '~> 4.3'
gem.add_runtime_dependency "rack", '>= 2.2', '< 4'
gem.add_development_dependency 'sinatra-linkeddata','~> 3.2'
gem.add_development_dependency 'jsonlint', '~> 0.3' unless is_java
gem.add_development_dependency 'oj', '~> 3.13' unless is_java
gem.add_development_dependency 'jsonlint', '~> 0.4' unless is_java
gem.add_development_dependency 'oj', '~> 3.14' unless is_java
gem.add_development_dependency 'yajl-ruby', '~> 1.4' unless is_java
gem.add_development_dependency 'rack-test', '~> 1.1'
gem.add_development_dependency 'rack-test', '>= 1.1', '< 3'
gem.add_development_dependency 'rdf-isomorphic', '~> 3.2'
gem.add_development_dependency 'rdf-spec', '~> 3.2'
gem.add_development_dependency 'rdf-trig', '~> 3.2'
gem.add_development_dependency 'rdf-turtle', '~> 3.2'
gem.add_development_dependency 'rdf-vocab', '~> 3.2'
gem.add_development_dependency 'rdf-xsd', '~> 3.2'
gem.add_development_dependency 'rspec', '~> 3.11'
gem.add_development_dependency 'rspec', '~> 3.12'
gem.add_development_dependency 'rspec-its', '~> 1.3'
gem.add_development_dependency 'yard' , '~> 0.9'

Expand Down
39 changes: 23 additions & 16 deletions lib/json/ld/api.rb
Expand Up @@ -66,6 +66,7 @@ class API
# @param [String, #read, Hash, Array, JSON::LD::Context] context
# An external context to use additionally to the context embedded in input when expanding the input.
# @param [Hash{Symbol => Object}] options
# @option options [Symbol] :adapter used with MultiJson
# @option options [RDF::URI, String, #to_s] :base
# The Base IRI to use when expanding the document. This overrides the value of `input` if it is a _IRI_. If not specified and `input` is not an _IRI_, the base IRI defaults to the current document IRI if in a browser context, or the empty string if there is no document context. If not specified, and a base IRI is found from `input`, options[:base] will be modified with this value.
# @option options [Boolean] :compactArrays (true)
Expand All @@ -74,10 +75,10 @@ class API
# Creates document relative IRIs when compacting, if `true`, otherwise leaves expanded.
# @option options [Proc] :documentLoader
# The callback of the loader to be used to retrieve remote documents and contexts. If specified, it must be used to retrieve remote documents and contexts; otherwise, if not specified, the processor's built-in loader must be used. See {documentLoader} for the method signature.
# @option options [Boolean] :lowercaseLanguage
# By default, language tags are left as is. To normalize to lowercase, set this option to `true`.
# @option options [String, #read, Hash, Array, JSON::LD::Context] :expandContext
# A context that is used to initialize the active context when expanding a document.
# @option options [Boolean] :extendedRepresentation (false)
# Use the extended internal representation.
# @option options [Boolean] :extractAllScripts
# If set, when given an HTML input without a fragment identifier, extracts all `script` elements with type `application/ld+json` into an array during expansion.
# @option options [Boolean, String, RDF::URI] :flatten
Expand All @@ -86,19 +87,19 @@ class API
# When set, this has the effect of inserting a context definition with `@language` set to the associated value, creating a default language for interpreting string values.
# @option options [Symbol] :library
# One of :nokogiri or :rexml. If nil/unspecified uses :nokogiri if available, :rexml otherwise.
# @option options [Boolean] :lowercaseLanguage
# By default, language tags are left as is. To normalize to lowercase, set this option to `true`.
# @option options [Boolean] :ordered (true)
# Order traversal of dictionary members by key when performing algorithms.
# @option options [String] :processingMode
# Processing mode, json-ld-1.0 or json-ld-1.1.
# If `processingMode` is not specified, a mode of `json-ld-1.0` or `json-ld-1.1` is set, the context used for `expansion` or `compaction`.
# @option options [Boolean] rdfstar (false)
# @option options [Boolean] :rdfstar (false)
# support parsing JSON-LD-star statement resources.
# @option options [Boolean] :rename_bnodes (true)
# Rename bnodes as part of expansion, or keep them the same.
# @option options [Boolean] :unique_bnodes (false)
# Use unique bnode identifiers, defaults to using the identifier which the node was originally initialized with (if any).
# @option options [Symbol] :adapter used with MultiJson
# @option options [Boolean] :validate Validate input, if a string or readable object.
# @option options [Boolean] :ordered (true)
# Order traversal of dictionary members by key when performing algorithms.
# @yield [api]
# @yieldparam [API]
# @raise [JsonLdError]
Expand Down Expand Up @@ -235,7 +236,7 @@ def self.compact(input, context, expanded: false, serializer: nil, **options)
end

API.new(expanded_input, context, no_default_base: true, **options) do
log_debug(".compact") {"expanded input: #{expanded_input.to_json(JSON_STATE) rescue 'malformed json'}"}
# log_debug(".compact") {"expanded input: #{expanded_input.to_json(JSON_STATE) rescue 'malformed json'}"}
result = compact(value)

# xxx) Add the given context to the output
Expand Down Expand Up @@ -289,7 +290,7 @@ def self.flatten(input, context, expanded: false, serializer: nil, **options)

# Initialize input using
API.new(expanded_input, context, no_default_base: true, **options) do
log_debug(".flatten") {"expanded input: #{value.to_json(JSON_STATE) rescue 'malformed json'}"}
# log_debug(".flatten") {"expanded input: #{value.to_json(JSON_STATE) rescue 'malformed json'}"}

# Rename blank nodes recusively. Note that this does not create new blank node identifiers where none exist, which is performed in the node map generation algorithm.
@value = rename_bnodes(@value) if @options[:rename_bnodes]
Expand Down Expand Up @@ -410,8 +411,8 @@ def self.frame(input, frame, expanded: false, serializer: nil, **options)

# Initialize input using frame as context
API.new(expanded_input, frame['@context'], no_default_base: true, **options) do
log_debug(".frame") {"expanded input: #{expanded_input.to_json(JSON_STATE) rescue 'malformed json'}"}
log_debug(".frame") {"expanded frame: #{expanded_frame.to_json(JSON_STATE) rescue 'malformed json'}"}
# log_debug(".frame") {"expanded input: #{expanded_input.to_json(JSON_STATE) rescue 'malformed json'}"}
# log_debug(".frame") {"expanded frame: #{expanded_frame.to_json(JSON_STATE) rescue 'malformed json'}"}

if %w(@first @last).include?(options[:embed]) && context.processingMode('json-ld-1.1')
raise JSON::LD::JsonLdError::InvalidEmbedValue, "#{options[:embed]} is not a valid value of @embed in 1.1 mode" if @options[:validate]
Expand Down Expand Up @@ -458,7 +459,7 @@ def self.frame(input, frame, expanded: false, serializer: nil, **options)

# Replace values with `@preserve` with the content of its entry.
result = cleanup_preserve(result)
log_debug(".frame") {"expanded result: #{result.to_json(JSON_STATE) rescue 'malformed json'}"}
# log_debug(".frame") {"expanded result: #{result.to_json(JSON_STATE) rescue 'malformed json'}"}

# Compact result
compacted = compact(result)
Expand All @@ -477,7 +478,7 @@ def self.frame(input, frame, expanded: false, serializer: nil, **options)
# Only add context if one was provided
result = context.serialize(provided_context: frame).merge(result) if frame['@context']

log_debug(".frame") {"after compact: #{result.to_json(JSON_STATE) rescue 'malformed json'}"}
# log_debug(".frame") {"after compact: #{result.to_json(JSON_STATE) rescue 'malformed json'}"}
result
end

Expand Down Expand Up @@ -518,7 +519,7 @@ def self.toRdf(input, expanded: false, **options, &block)
API.new(flattened_input, nil, **options) do
# 1) Perform the Expansion Algorithm on the JSON-LD input.
# This removes any existing context to allow the given context to be cleanly applied.
log_debug(".toRdf") {"flattened input: #{flattened_input.to_json(JSON_STATE) rescue 'malformed json'}"}
# log_debug(".toRdf") {"flattened input: #{flattened_input.to_json(JSON_STATE) rescue 'malformed json'}"}

# Recurse through input
flattened_input.each do |node|
Expand All @@ -527,7 +528,7 @@ def self.toRdf(input, expanded: false, **options, &block)

# Drop invalid statements (other than IRIs)
unless statement.valid_extended?
log_debug(".toRdf") {"drop invalid statement: #{statement.to_nquads}"}
# log_debug(".toRdf") {"drop invalid statement: #{statement.to_nquads}"}
next
end

Expand Down Expand Up @@ -562,6 +563,7 @@ def self.fromRdf(input, useRdfType: false, useNativeTypes: false, serializer: ni

API.new(nil, nil, **options) do
result = from_statements(input,
extendedRepresentation: options[:extendedRepresentation],
useRdfType: useRdfType,
useNativeTypes: useNativeTypes)
end
Expand All @@ -574,6 +576,9 @@ def self.fromRdf(input, useRdfType: false, useNativeTypes: false, serializer: ni
# Uses built-in or provided documentLoader to retrieve a parsed document.
#
# @param [RDF::URI, String] url
# @param [Regexp] allowed_content_types
# A regular expression matching other content types allowed
# beyond types for JSON and HTML.
# @param [String, RDF::URI] base
# Location to use as documentUrl instead of `url`.
# @option options [Proc] :documentLoader
Expand All @@ -594,6 +599,7 @@ def self.fromRdf(input, useRdfType: false, useNativeTypes: false, serializer: ni
# If a block is given, the result of evaluating the block is returned, otherwise, the retrieved remote document and context information unless block given
# @raise [JsonLdError]
def self.loadRemoteDocument(url,
allowed_content_types: nil,
base: nil,
documentLoader: nil,
extractAllScripts: false,
Expand Down Expand Up @@ -674,7 +680,8 @@ def self.loadRemoteDocument(url,

if remote_doc.contentType && validate
raise IOError, "url: #{url}, contentType: #{remote_doc.contentType}" unless
remote_doc.contentType.match?(/application\/(.+\+)?json|text\/html|application\/xhtml\+xml/)
remote_doc.contentType.match?(/application\/(.+\+)?json|text\/html|application\/xhtml\+xml/) ||
(allowed_content_types && remote_doc.contentType.match?(allowed_content_types))
end
block_given? ? yield(remote_doc) : remote_doc
end
Expand Down
32 changes: 16 additions & 16 deletions lib/json/ld/compact.rb
Expand Up @@ -21,14 +21,14 @@ def compact(element,
base: nil,
property: nil,
log_depth: nil)
log_debug("compact", depth: log_depth.to_i) {"element: #{element.inspect}, ec: #{context.inspect}"}
# log_debug("compact", depth: log_depth.to_i) {"element: #{element.inspect}, ec: #{context.inspect}"}

# If the term definition for active property itself contains a context, use that for compacting values.
input_context = self.context

case element
when Array
#log_debug("") {"Array #{element.inspect}"}
# log_debug("") {"Array #{element.inspect}"}
result = element.map do |item|
compact(item, base: base, property: property, log_depth: log_depth.to_i + 1)
end.compact
Expand All @@ -38,10 +38,10 @@ def compact(element,
# member; otherwise the compacted value is element
if result.length == 1 &&
!context.as_array?(property) && @options[:compactArrays]
log_debug("=> extract single element", depth: log_depth.to_i) {result.first.inspect}
# log_debug("=> extract single element", depth: log_depth.to_i) {result.first.inspect}
result.first
else
log_debug("=> array result", depth: log_depth.to_i) {result.inspect}
# log_debug("=> array result", depth: log_depth.to_i) {result.inspect}
result
end
when Hash
Expand All @@ -52,7 +52,7 @@ def compact(element,

# Revert any previously type-scoped (non-preserved) context
if context.previous_context && !element.key?('@value') && element.keys != %w(@id)
log_debug("revert ec", depth: log_depth.to_i) {"previous context: #{context.previous_context.inspect}"}
# log_debug("revert ec", depth: log_depth.to_i) {"previous context: #{context.previous_context.inspect}"}
self.context = context.previous_context
end

Expand All @@ -61,13 +61,13 @@ def compact(element,
if td && !td.context.nil?
self.context = context.parse(td.context,
override_protected: true)
log_debug("prop-scoped", depth: log_depth.to_i) {"context: #{self.context.inspect}"}
# log_debug("prop-scoped", depth: log_depth.to_i) {"context: #{self.context.inspect}"}
end

if (element.key?('@id') || element.key?('@value')) && !element.key?('@annotation')
result = context.compact_value(property, element, base: @options[:base])
if !result.is_a?(Hash) || context.coerce(property) == '@json'
log_debug("", depth: log_depth.to_i) {"=> scalar result: #{result.inspect}"}
# log_debug("", depth: log_depth.to_i) {"=> scalar result: #{result.inspect}"}
return result
end
end
Expand All @@ -90,12 +90,12 @@ def compact(element,
each do |term|
term_context = input_context.term_definitions[term].context if input_context.term_definitions[term]
self.context = context.parse(term_context, propagate: false) unless term_context.nil?
log_debug("type-scoped", depth: log_depth.to_i) {"context: #{self.context.inspect}"}
# log_debug("type-scoped", depth: log_depth.to_i) {"context: #{self.context.inspect}"}
end

element.keys.opt_sort(ordered: @options[:ordered]).each do |expanded_property|
expanded_value = element[expanded_property]
log_debug("", depth: log_depth.to_i) {"#{expanded_property}: #{expanded_value.inspect}"}
# log_debug("", depth: log_depth.to_i) {"#{expanded_property}: #{expanded_value.inspect}"}

if expanded_property == '@id'
compacted_value = as_array(expanded_value).map do |expanded_id|
Expand Down Expand Up @@ -134,7 +134,7 @@ def compact(element,
compacted_value = compact(expanded_value, base: base,
property: '@reverse',
log_depth: log_depth.to_i + 1)
log_debug("@reverse", depth: log_depth.to_i) {"compacted_value: #{compacted_value.inspect}"}
# log_debug("@reverse", depth: log_depth.to_i) {"compacted_value: #{compacted_value.inspect}"}
# handle double-reversed properties
compacted_value.each do |prop, value|
if context.reverse?(prop)
Expand All @@ -146,7 +146,7 @@ def compact(element,

unless compacted_value.empty?
al = context.compact_iri('@reverse', vocab: true)
log_debug("", depth: log_depth.to_i) {"remainder: #{al} => #{compacted_value.inspect}"}
# log_debug("", depth: log_depth.to_i) {"remainder: #{al} => #{compacted_value.inspect}"}
result[al] = compacted_value
end
next
Expand All @@ -157,7 +157,7 @@ def compact(element,
compacted_value = compact(expanded_value, base: base,
property: property,
log_depth: log_depth.to_i + 1)
log_debug("@preserve", depth: log_depth.to_i) {"compacted_value: #{compacted_value.inspect}"}
# log_debug("@preserve", depth: log_depth.to_i) {"compacted_value: #{compacted_value.inspect}"}

unless compacted_value.is_a?(Array) && compacted_value.empty?
result['@preserve'] = compacted_value
Expand All @@ -166,14 +166,14 @@ def compact(element,
end

if expanded_property == '@index' && context.container(property).include?('@index')
log_debug("@index", depth: log_depth.to_i) {"drop @index"}
# log_debug("@index", depth: log_depth.to_i) {"drop @index"}
next
end

# Otherwise, if expanded property is @direction, @index, @value, or @language:
if EXPANDED_PROPERTY_DIRECTION_INDEX_LANGUAGE_VALUE.include?(expanded_property)
al = context.compact_iri(expanded_property, vocab: true)
log_debug(expanded_property, depth: log_depth.to_i) {"#{al} => #{expanded_value.inspect}"}
# log_debug(expanded_property, depth: log_depth.to_i) {"#{al} => #{expanded_value.inspect}"}
result[al] = expanded_value
next
end
Expand Down Expand Up @@ -223,7 +223,7 @@ def compact(element,
compacted_item = compact(value, base: base,
property: item_active_property,
log_depth: log_depth.to_i + 1)
log_debug("", depth: log_depth.to_i) {" => compacted key: #{item_active_property.inspect} for #{compacted_item.inspect}"}
# log_debug("", depth: log_depth.to_i) {" => compacted key: #{item_active_property.inspect} for #{compacted_item.inspect}"}

# handle @list
if list?(expanded_item)
Expand Down Expand Up @@ -345,7 +345,7 @@ def compact(element,
result
else
# For other types, the compacted value is the element value
log_debug("compact", depth: log_depth.to_i) {element.class.to_s}
# log_debug("compact", depth: log_depth.to_i) {element.class.to_s}
element
end

Expand Down

0 comments on commit 0786a2e

Please sign in to comment.