coradoc 2.0.28 → 2.0.30

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (53) hide show
  1. checksums.yaml +4 -4
  2. data/lib/coradoc/cli.rb +4 -1
  3. data/lib/coradoc/coradoc.rb +3 -0
  4. data/lib/coradoc/core_model/list_block.rb +45 -60
  5. data/lib/coradoc/errors.rb +19 -0
  6. data/lib/coradoc/format_module.rb +10 -0
  7. data/lib/coradoc/pipeline.rb +60 -1
  8. data/lib/coradoc/reference/address/anchor.rb +48 -0
  9. data/lib/coradoc/reference/address/doi.rb +40 -0
  10. data/lib/coradoc/reference/address/isbn.rb +39 -0
  11. data/lib/coradoc/reference/address/path.rb +66 -0
  12. data/lib/coradoc/reference/address/scoped_path.rb +47 -0
  13. data/lib/coradoc/reference/address/url.rb +41 -0
  14. data/lib/coradoc/reference/address.rb +153 -0
  15. data/lib/coradoc/reference/catalog/composite.rb +59 -0
  16. data/lib/coradoc/reference/catalog/local.rb +97 -0
  17. data/lib/coradoc/reference/catalog/memory_index.rb +59 -0
  18. data/lib/coradoc/reference/catalog.rb +33 -0
  19. data/lib/coradoc/reference/edge/citation_options.rb +16 -0
  20. data/lib/coradoc/reference/edge/footnote_ref_options.rb +13 -0
  21. data/lib/coradoc/reference/edge/image_ref_options.rb +15 -0
  22. data/lib/coradoc/reference/edge/include_options.rb +15 -0
  23. data/lib/coradoc/reference/edge/kind.rb +72 -0
  24. data/lib/coradoc/reference/edge/link_options.rb +12 -0
  25. data/lib/coradoc/reference/edge/navigation_options.rb +12 -0
  26. data/lib/coradoc/reference/edge/options.rb +13 -0
  27. data/lib/coradoc/reference/edge.rb +80 -0
  28. data/lib/coradoc/reference/edge_search.rb +128 -0
  29. data/lib/coradoc/reference/materializer/base.rb +44 -0
  30. data/lib/coradoc/reference/materializer/passthrough.rb +31 -0
  31. data/lib/coradoc/reference/materializer/registry.rb +116 -0
  32. data/lib/coradoc/reference/materializer.rb +14 -0
  33. data/lib/coradoc/reference/presentation/base.rb +47 -0
  34. data/lib/coradoc/reference/presentation/custom_hierarchy.rb +104 -0
  35. data/lib/coradoc/reference/presentation/page.rb +20 -0
  36. data/lib/coradoc/reference/presentation/single_document.rb +35 -0
  37. data/lib/coradoc/reference/presentation/split_pages.rb +118 -0
  38. data/lib/coradoc/reference/presentation.rb +16 -0
  39. data/lib/coradoc/reference/resolution.rb +184 -0
  40. data/lib/coradoc/reference/resolver/base.rb +15 -0
  41. data/lib/coradoc/reference/resolver/caching.rb +37 -0
  42. data/lib/coradoc/reference/resolver/catalog.rb +69 -0
  43. data/lib/coradoc/reference/resolver/chain.rb +33 -0
  44. data/lib/coradoc/reference/resolver.rb +20 -0
  45. data/lib/coradoc/reference/result/ambiguous.rb +23 -0
  46. data/lib/coradoc/reference/result/base.rb +46 -0
  47. data/lib/coradoc/reference/result/missing.rb +14 -0
  48. data/lib/coradoc/reference/result/resolved.rb +22 -0
  49. data/lib/coradoc/reference/result.rb +20 -0
  50. data/lib/coradoc/reference.rb +65 -0
  51. data/lib/coradoc/validation.rb +40 -0
  52. data/lib/coradoc/version.rb +1 -1
  53. metadata +44 -1
@@ -0,0 +1,184 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Coradoc
4
+ module Reference
5
+ # Orchestrator: resolves every Edge in the tree via the Resolver,
6
+ # enforces the missing/ambiguous policies, and — only when asked
7
+ # to materialize — rebuilds the tree with rendered inline nodes
8
+ # via the Presentation layout and the Materializer registry.
9
+ #
10
+ # Two-step contract:
11
+ # - +materialize: false+ validates references and returns the
12
+ # INPUT document (never mutated, never copied).
13
+ # - +materialize: true+ returns a NEW document. Untouched subtrees
14
+ # are shared with the input (structural sharing) — treat both as
15
+ # immutable.
16
+ #
17
+ # Wired from the public API +Coradoc.resolve_references+.
18
+ class Resolution
19
+ attr_reader :catalog, :presentation, :resolver, :missing_policy,
20
+ :ambiguous_policy, :materialize_policy, :format,
21
+ :materializer_registry
22
+
23
+ def initialize(catalog:, presentation:, missing:, ambiguous:,
24
+ materialize:, resolver: nil, format: nil,
25
+ materializer_registry: default_registry)
26
+ @catalog = catalog
27
+ @presentation = presentation
28
+ @missing_policy = missing
29
+ @ambiguous_policy = ambiguous
30
+ @materialize_policy = materialize
31
+ @format = format
32
+ @materializer_registry = materializer_registry
33
+ @resolver = resolver || Resolver::Catalog.new(
34
+ catalog: catalog, ambiguous: ambiguous, missing: missing
35
+ )
36
+ end
37
+
38
+ def call(document)
39
+ results = resolve_all_edges(document)
40
+ report_missing(results)
41
+ return document unless materialize_policy
42
+
43
+ materialize_tree(document, results)
44
+ end
45
+
46
+ private
47
+
48
+ # Keyed by the Edge itself (value equality), so every distinct
49
+ # edge gets its own Result while identical edges resolve once.
50
+ def resolve_all_edges(document)
51
+ results = {}
52
+ EdgeSearch.each_edge(document) do |_parent, edge|
53
+ results[edge] = resolver.resolve(edge)
54
+ end
55
+ results
56
+ end
57
+
58
+ def report_missing(results)
59
+ results.each_value do |result|
60
+ next unless result.missing?
61
+
62
+ case missing_policy
63
+ when :error
64
+ raise Coradoc::Reference::MissingReferenceError.new(
65
+ address: result.address
66
+ )
67
+ when :warn
68
+ Coradoc::Logger.warn("Reference not found: #{result.address}")
69
+ end
70
+ end
71
+ end
72
+
73
+ def materialize_tree(document, results)
74
+ pages = presentation.layout(document)
75
+ ReplaceWalker.new(
76
+ pages: pages,
77
+ results: results,
78
+ presentation: presentation,
79
+ registry: materializer_registry,
80
+ missing_policy: missing_policy,
81
+ format: format
82
+ ).visit(document)
83
+ end
84
+
85
+ def default_registry
86
+ Materializer::Registry.new
87
+ end
88
+
89
+ # Rebuilds the tree, replacing every Edge-bearing node with the
90
+ # materializer's output. The walker is single-purpose and only
91
+ # lives inside Resolution — no need for a separate file.
92
+ class ReplaceWalker
93
+ attr_reader :pages, :results, :presentation, :registry,
94
+ :missing_policy, :format
95
+
96
+ def initialize(pages:, results:, presentation:, registry:,
97
+ missing_policy:, format:)
98
+ @pages = pages
99
+ @results = results
100
+ @presentation = presentation
101
+ @registry = registry
102
+ @missing_policy = missing_policy
103
+ @format = format
104
+ end
105
+
106
+ def visit(node)
107
+ return node unless node.is_a?(Coradoc::CoreModel::Base)
108
+
109
+ replaced = replace_node(node)
110
+ return replaced unless replaced.is_a?(Coradoc::CoreModel::HasChildren)
111
+
112
+ rebuild_children_of(replaced)
113
+ end
114
+
115
+ private
116
+
117
+ def replace_node(node)
118
+ edges = EdgeSearch.edges_for(node)
119
+ return node if edges.empty?
120
+
121
+ materialize_edge(node, edges.first)
122
+ end
123
+
124
+ def materialize_edge(node, edge)
125
+ result = results[edge]
126
+ return drop_or_keep(node) if result.nil? || result.missing?
127
+
128
+ invoke_materializer(node, edge, result)
129
+ end
130
+
131
+ # :silent drops the unresolved node; :warn (already logged) and
132
+ # :passthrough keep the original node so round-tripping is safe.
133
+ def drop_or_keep(node)
134
+ return nil if missing_policy == :silent
135
+
136
+ node
137
+ end
138
+
139
+ def invoke_materializer(node, edge, result)
140
+ klass = lookup_materializer(edge)
141
+ return node unless klass
142
+
143
+ klass.new.materialize(
144
+ edge: edge,
145
+ result: result,
146
+ node: node,
147
+ presentation: presentation,
148
+ pages: pages
149
+ )
150
+ end
151
+
152
+ def lookup_materializer(edge)
153
+ registry.lookup(
154
+ kind: edge.kind.to_sym,
155
+ presentation: presentation.key,
156
+ format: format || :any
157
+ )
158
+ end
159
+
160
+ def rebuild_children_of(node)
161
+ children = node.children
162
+ return node unless children
163
+ return node if children.empty?
164
+
165
+ new_children = children.filter_map { |c| visit(c) }
166
+ rebuild_with(node, new_children)
167
+ end
168
+
169
+ def rebuild_with(node, new_children)
170
+ return node if identical_children?(new_children, node.children)
171
+
172
+ duplicate = node.dup
173
+ duplicate.children = new_children
174
+ duplicate
175
+ end
176
+
177
+ def identical_children?(new_children, old_children)
178
+ new_children.length == old_children.length &&
179
+ new_children.each_with_index.all? { |c, i| c.equal?(old_children[i]) }
180
+ end
181
+ end
182
+ end
183
+ end
184
+ end
@@ -0,0 +1,15 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Coradoc
4
+ module Reference
5
+ module Resolver
6
+ # Protocol base. Concrete resolvers implement +#resolve(edge)+
7
+ # and return a Result sum type instance — never +nil+.
8
+ class Base
9
+ def resolve(edge)
10
+ raise NotImplementedError
11
+ end
12
+ end
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,37 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Coradoc
4
+ module Reference
5
+ module Resolver
6
+ # Wraps another resolver with an address-keyed memoization cache.
7
+ # Addresses are value types, so cache keys are stable across calls.
8
+ # Use to avoid re-asking the catalog for the same Edge.address.
9
+ class Caching < Resolver::Base
10
+ attr_reader :inner
11
+
12
+ def initialize(inner:)
13
+ super()
14
+ @inner = inner
15
+ @cache = {}
16
+ end
17
+
18
+ def resolve(edge)
19
+ cached = if @cache.key?(edge.address)
20
+ @cache[edge.address]
21
+ else
22
+ @cache[edge.address] = @inner.resolve(edge)
23
+ end
24
+ cached.for_edge(edge)
25
+ end
26
+
27
+ def clear!
28
+ @cache.clear
29
+ end
30
+
31
+ def size
32
+ @cache.size
33
+ end
34
+ end
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,69 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Coradoc
4
+ module Reference
5
+ module Resolver
6
+ # Asks one catalog. Applies the +ambiguous:+ policy in-line.
7
+ # Does NOT apply the +missing:+ policy — that's the caller's
8
+ # call (Resolution orchestrator) — but it does surface the
9
+ # Missing Result so the caller can decide.
10
+ class Catalog < Resolver::Base
11
+ attr_reader :catalog, :ambiguous_policy, :missing_policy
12
+
13
+ def initialize(catalog:, ambiguous: :disambiguate, missing: :warn)
14
+ super()
15
+ @catalog = catalog
16
+ @ambiguous_policy = ambiguous
17
+ @missing_policy = missing
18
+ end
19
+
20
+ def resolve(edge)
21
+ address = edge.address
22
+ return missing_for(edge, address) unless catalog.recognizes_scheme?(address.scheme)
23
+
24
+ result = catalog.lookup(address)
25
+ return missing_for(edge, address) if result.nil?
26
+
27
+ return resolved_for(edge, address, result) unless result.is_a?(Array)
28
+
29
+ resolve_ambiguous(edge, address, result)
30
+ end
31
+
32
+ private
33
+
34
+ def resolved_for(edge, address, target)
35
+ Coradoc::Reference::Result::Resolved.build(
36
+ edge: edge, address: address, target: target
37
+ )
38
+ end
39
+
40
+ def resolve_ambiguous(edge, address, candidates)
41
+ return ambiguous_error(address, candidates) if ambiguous_policy == :error
42
+ return resolved_for(edge, address, candidates.first) if ambiguous_policy == :first
43
+
44
+ # :disambiguate — warn, then deterministically take the first
45
+ Coradoc::Logger.warn(
46
+ "Reference #{address} is ambiguous " \
47
+ "(#{candidates.size} candidates); using first"
48
+ )
49
+ resolved_for(edge, address, candidates.first)
50
+ end
51
+
52
+ def ambiguous_error(address, candidates)
53
+ raise Coradoc::Reference::AmbiguousReferenceError,
54
+ "Address #{address} matched #{candidates.size} candidates"
55
+ end
56
+
57
+ def missing_for(edge, address)
58
+ case missing_policy
59
+ when :error
60
+ raise Coradoc::Reference::MissingReferenceError,
61
+ "Address #{address} not found"
62
+ else
63
+ Coradoc::Reference::Result::Missing.build(edge: edge, address: address)
64
+ end
65
+ end
66
+ end
67
+ end
68
+ end
69
+ end
@@ -0,0 +1,33 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Coradoc
4
+ module Reference
5
+ module Resolver
6
+ # Tries each child resolver in order. First non-Missing result
7
+ # wins (Resolved or Ambiguous short-circuit). Use to combine a
8
+ # local catalog with a remote one without composite catalog
9
+ # indirection.
10
+ class Chain < Resolver::Base
11
+ attr_reader :resolvers
12
+
13
+ def initialize(*resolvers)
14
+ super()
15
+ @resolvers = resolvers.flatten
16
+ end
17
+
18
+ def resolve(edge)
19
+ last = nil
20
+ @resolvers.each do |resolver|
21
+ result = resolver.resolve(edge)
22
+ return result unless result.is_a?(Coradoc::Reference::Result::Missing)
23
+
24
+ last = result
25
+ end
26
+ last || Coradoc::Reference::Result::Missing.build(
27
+ edge: edge, address: edge.address
28
+ )
29
+ end
30
+ end
31
+ end
32
+ end
33
+ end
@@ -0,0 +1,20 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Coradoc
4
+ module Reference
5
+ # Kind-agnostic resolver: given an Edge, ask the catalog, return a
6
+ # Result. Never materializes, never slices, never orders.
7
+ #
8
+ # resolver = Resolver::Catalog.new(catalog: catalog, ambiguous: :first, missing: :warn)
9
+ # case resolver.resolve(edge)
10
+ # in Result::Resolved => r ; use_target(r.target)
11
+ # in Result::Missing ; warn("could not resolve #{edge.address}")
12
+ # end
13
+ module Resolver
14
+ autoload :Base, "#{__dir__}/resolver/base"
15
+ autoload :Catalog, "#{__dir__}/resolver/catalog"
16
+ autoload :Chain, "#{__dir__}/resolver/chain"
17
+ autoload :Caching, "#{__dir__}/resolver/caching"
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,23 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Coradoc
4
+ module Reference
5
+ module Result
6
+ # Multiple candidates matched. The catalog returned an Array.
7
+ # Callers' +ambiguous:+ policy decides what to do.
8
+ class Ambiguous < Base
9
+ attribute :candidates, Coradoc::CoreModel::Base, collection: true
10
+
11
+ def self.build(edge:, address:, candidates:)
12
+ new(edge: edge, address: address, candidates: candidates)
13
+ end
14
+
15
+ private
16
+
17
+ def result_data
18
+ { candidates: candidates }
19
+ end
20
+ end
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,46 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'lutaml/model'
4
+
5
+ module Coradoc
6
+ module Reference
7
+ module Result
8
+ # Base class for resolution outcomes. Subclasses are value types.
9
+ # Every Result carries the Edge that asked — so callers can log,
10
+ # trace, and re-route without re-resolving.
11
+ class Base < Lutaml::Model::Serializable
12
+ attribute :edge, Coradoc::Reference::Edge
13
+ attribute :address, Coradoc::Reference::Address
14
+
15
+ def resolved?
16
+ is_a?(Result::Resolved)
17
+ end
18
+
19
+ def ambiguous?
20
+ is_a?(Result::Ambiguous)
21
+ end
22
+
23
+ def missing?
24
+ is_a?(Result::Missing)
25
+ end
26
+
27
+ # This Result as seen by +edge+. Returns self when the edge is
28
+ # value-equal to the one embedded; otherwise rebuilds the same
29
+ # outcome (target/candidates preserved) for the asking edge.
30
+ # Used by caching resolvers so two edges sharing an Address
31
+ # never see each other's identity.
32
+ def for_edge(edge)
33
+ return self if self.edge == edge
34
+
35
+ self.class.build(edge: edge, address: address, **result_data)
36
+ end
37
+
38
+ private
39
+
40
+ def result_data
41
+ {}
42
+ end
43
+ end
44
+ end
45
+ end
46
+ end
@@ -0,0 +1,14 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Coradoc
4
+ module Reference
5
+ module Result
6
+ # No catalog knows this address. Caller's +missing:+ policy decides.
7
+ class Missing < Base
8
+ def self.build(edge:, address:)
9
+ new(edge: edge, address: address)
10
+ end
11
+ end
12
+ end
13
+ end
14
+ end
@@ -0,0 +1,22 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Coradoc
4
+ module Reference
5
+ module Result
6
+ # Catalog knew the address; exactly one Content was returned.
7
+ class Resolved < Base
8
+ attribute :target, Coradoc::CoreModel::Base
9
+
10
+ def self.build(edge:, address:, target:)
11
+ new(edge: edge, address: address, target: target)
12
+ end
13
+
14
+ private
15
+
16
+ def result_data
17
+ { target: target }
18
+ end
19
+ end
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,20 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Coradoc
4
+ module Reference
5
+ # Sum type for resolution outcomes. Callers pattern-match on the
6
+ # concrete subclass — never check +nil+.
7
+ #
8
+ # case resolver.resolve(edge)
9
+ # in Result::Resolved => r # have the target
10
+ # in Result::Ambiguous => a # multiple candidates
11
+ # in Result::Missing => m # catalog does not know
12
+ # end
13
+ module Result
14
+ autoload :Base, "#{__dir__}/result/base"
15
+ autoload :Resolved, "#{__dir__}/result/resolved"
16
+ autoload :Ambiguous, "#{__dir__}/result/ambiguous"
17
+ autoload :Missing, "#{__dir__}/result/missing"
18
+ end
19
+ end
20
+ end
@@ -0,0 +1,65 @@
1
+ # frozen_string_literal: true
2
+
3
+ require 'coradoc/errors'
4
+
5
+ module Coradoc
6
+ # Unified content-graph reference resolution.
7
+ #
8
+ # Every referenceable thing in a document is a Content node; every
9
+ # reference is a directed Edge with a kind. The four primitives:
10
+ #
11
+ # Content — CoreModel::Base with an id (already on Base).
12
+ # Document — Content that contains Content (composite).
13
+ # Reference::Edge — directed {source Content, target Address, kind}.
14
+ # Reference::Address — scheme-aware locator (anchor, path, url, ...).
15
+ #
16
+ # Same Content graph → N Presentations → M Materializers. The public
17
+ # entry point is +Coradoc.resolve_references+.
18
+ module Reference
19
+ # Base class for reference-resolution errors. All subclasses inherit
20
+ # from here so callers can rescue the family with one +rescue+ clause.
21
+ class Error < Coradoc::Error; end
22
+
23
+ # Raised when no catalog knew the requested Address and the
24
+ # +missing:+ policy is :error.
25
+ class MissingReferenceError < Error
26
+ attr_reader :address
27
+
28
+ def initialize(message = nil, address: nil)
29
+ @address = address
30
+ super(message || "Reference not found: #{address}")
31
+ end
32
+ end
33
+
34
+ # Raised when multiple catalogs matched an Address and the
35
+ # +ambiguous:+ policy is :error.
36
+ class AmbiguousReferenceError < Error
37
+ attr_reader :address, :candidates
38
+
39
+ def initialize(message = nil, address: nil, candidates: nil)
40
+ @address = address
41
+ @candidates = candidates
42
+ super(message || "Reference is ambiguous: #{address}")
43
+ end
44
+ end
45
+
46
+ # Raised when the catalog index is malformed — a programmer
47
+ # error, not a runtime condition. Surfaces as a clear message
48
+ # rather than a vague NoMethodError.
49
+ class InvalidCatalogError < Error; end
50
+
51
+ # Raised when building an Edge whose kind was never registered.
52
+ # External kinds register via +Edge.register_kind+ (OCP).
53
+ class UnknownKindError < Error; end
54
+
55
+ autoload :Address, "#{__dir__}/reference/address"
56
+ autoload :Edge, "#{__dir__}/reference/edge"
57
+ autoload :Catalog, "#{__dir__}/reference/catalog"
58
+ autoload :Result, "#{__dir__}/reference/result"
59
+ autoload :Resolver, "#{__dir__}/reference/resolver"
60
+ autoload :Presentation, "#{__dir__}/reference/presentation"
61
+ autoload :Materializer, "#{__dir__}/reference/materializer"
62
+ autoload :EdgeSearch, "#{__dir__}/reference/edge_search"
63
+ autoload :Resolution, "#{__dir__}/reference/resolution"
64
+ end
65
+ end
@@ -28,6 +28,46 @@ module Coradoc
28
28
  # end
29
29
  #
30
30
  module Validation
31
+ module_function
32
+
33
+ # Targets of every unresolved +include::+ edge in the tree
34
+ # (deduplicated, in document order). A document is "unresolved"
35
+ # when it was parsed in graph mode and never went through
36
+ # +Coradoc.resolve_includes+.
37
+ def unresolved_include_targets(model)
38
+ targets = []
39
+ walk_nodes(model) do |node|
40
+ targets << node.target if node.is_a?(Coradoc::CoreModel::Include)
41
+ end
42
+ targets.uniq
43
+ end
44
+
45
+ # Serialization boundary check: formats that cannot represent an
46
+ # unresolved include edge (FormatModule::Interface
47
+ # #preserves_unresolved_includes? == false) must not silently drop
48
+ # the content — raise UnresolvedIncludesError instead, pointing at
49
+ # the hydration step (resolve_includes).
50
+ def guard_unresolved_includes!(model, format_module)
51
+ return if format_module.preserves_unresolved_includes?
52
+
53
+ targets = unresolved_include_targets(model)
54
+ return if targets.empty?
55
+
56
+ raise Coradoc::UnresolvedIncludesError, targets
57
+ end
58
+
59
+ def walk_nodes(node, &block)
60
+ return unless node.is_a?(Coradoc::CoreModel::Base)
61
+
62
+ yield node
63
+ return unless node.is_a?(Coradoc::CoreModel::HasChildren)
64
+
65
+ children = node.children
66
+ return unless children
67
+
68
+ children.each { |child| walk_nodes(child, &block) }
69
+ end
70
+
31
71
  # A single validation error
32
72
  class Error
33
73
  attr_reader :path, :message, :code, :element
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Coradoc
4
- VERSION = '2.0.28'
4
+ VERSION = '2.0.30'
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: coradoc
3
3
  version: !ruby/object:Gem::Version
4
- version: 2.0.28
4
+ version: 2.0.30
5
5
  platform: ruby
6
6
  authors:
7
7
  - Ribose Inc.
@@ -131,6 +131,49 @@ files:
131
131
  - lib/coradoc/performance_regression.rb
132
132
  - lib/coradoc/pipeline.rb
133
133
  - lib/coradoc/query.rb
134
+ - lib/coradoc/reference.rb
135
+ - lib/coradoc/reference/address.rb
136
+ - lib/coradoc/reference/address/anchor.rb
137
+ - lib/coradoc/reference/address/doi.rb
138
+ - lib/coradoc/reference/address/isbn.rb
139
+ - lib/coradoc/reference/address/path.rb
140
+ - lib/coradoc/reference/address/scoped_path.rb
141
+ - lib/coradoc/reference/address/url.rb
142
+ - lib/coradoc/reference/catalog.rb
143
+ - lib/coradoc/reference/catalog/composite.rb
144
+ - lib/coradoc/reference/catalog/local.rb
145
+ - lib/coradoc/reference/catalog/memory_index.rb
146
+ - lib/coradoc/reference/edge.rb
147
+ - lib/coradoc/reference/edge/citation_options.rb
148
+ - lib/coradoc/reference/edge/footnote_ref_options.rb
149
+ - lib/coradoc/reference/edge/image_ref_options.rb
150
+ - lib/coradoc/reference/edge/include_options.rb
151
+ - lib/coradoc/reference/edge/kind.rb
152
+ - lib/coradoc/reference/edge/link_options.rb
153
+ - lib/coradoc/reference/edge/navigation_options.rb
154
+ - lib/coradoc/reference/edge/options.rb
155
+ - lib/coradoc/reference/edge_search.rb
156
+ - lib/coradoc/reference/materializer.rb
157
+ - lib/coradoc/reference/materializer/base.rb
158
+ - lib/coradoc/reference/materializer/passthrough.rb
159
+ - lib/coradoc/reference/materializer/registry.rb
160
+ - lib/coradoc/reference/presentation.rb
161
+ - lib/coradoc/reference/presentation/base.rb
162
+ - lib/coradoc/reference/presentation/custom_hierarchy.rb
163
+ - lib/coradoc/reference/presentation/page.rb
164
+ - lib/coradoc/reference/presentation/single_document.rb
165
+ - lib/coradoc/reference/presentation/split_pages.rb
166
+ - lib/coradoc/reference/resolution.rb
167
+ - lib/coradoc/reference/resolver.rb
168
+ - lib/coradoc/reference/resolver/base.rb
169
+ - lib/coradoc/reference/resolver/caching.rb
170
+ - lib/coradoc/reference/resolver/catalog.rb
171
+ - lib/coradoc/reference/resolver/chain.rb
172
+ - lib/coradoc/reference/result.rb
173
+ - lib/coradoc/reference/result/ambiguous.rb
174
+ - lib/coradoc/reference/result/base.rb
175
+ - lib/coradoc/reference/result/missing.rb
176
+ - lib/coradoc/reference/result/resolved.rb
134
177
  - lib/coradoc/registry.rb
135
178
  - lib/coradoc/relative_path.rb
136
179
  - lib/coradoc/resolve_includes.rb