modspec 0.1.4 → 0.2.1

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 (46) hide show
  1. checksums.yaml +4 -4
  2. data/.github/workflows/rake.yml +4 -0
  3. data/.github/workflows/release.yml +5 -0
  4. data/.rubocop.yml +18 -6
  5. data/.rubocop_todo.yml +108 -76
  6. data/CLAUDE.md +61 -0
  7. data/Gemfile +4 -3
  8. data/lib/modspec/conformance_class.rb +4 -8
  9. data/lib/modspec/conformance_test.rb +19 -5
  10. data/lib/modspec/identifier.rb +0 -1
  11. data/lib/modspec/normative_statement.rb +3 -39
  12. data/lib/modspec/normative_statements_class.rb +3 -3
  13. data/lib/modspec/suite.rb +73 -82
  14. data/lib/modspec/version.rb +1 -1
  15. data/lib/modspec.rb +8 -22
  16. data/modspec.gemspec +3 -2
  17. data/spec/conformance_class.liquid +2 -2
  18. data/spec/fixtures/advanced-json-rc.yaml +5 -7
  19. data/spec/fixtures/advanced-rc.yaml +12 -14
  20. data/spec/fixtures/basic-quaternion-json-rc.yaml +5 -7
  21. data/spec/fixtures/basic-quaternion-json-strict-rc.yaml +4 -5
  22. data/spec/fixtures/basic-quaternion-rc.yaml +7 -8
  23. data/spec/fixtures/basic-ypr-json-rc.yaml +5 -8
  24. data/spec/fixtures/basic-ypr-rc.yaml +7 -7
  25. data/spec/fixtures/chain-json-rc.yaml +5 -7
  26. data/spec/fixtures/chain-rc.yaml +11 -13
  27. data/spec/fixtures/frame-spec-rc.yaml +10 -10
  28. data/spec/fixtures/global-rc.yaml +7 -4
  29. data/spec/fixtures/graph-json-rc.yaml +5 -7
  30. data/spec/fixtures/graph-rc.yaml +11 -13
  31. data/spec/fixtures/series-irregular-json-rc.yaml +5 -7
  32. data/spec/fixtures/series-irregular-rc.yaml +13 -15
  33. data/spec/fixtures/series-regular-json-rc.yaml +5 -7
  34. data/spec/fixtures/series-regular-rc.yaml +15 -17
  35. data/spec/fixtures/stream-json-rc.yaml +9 -11
  36. data/spec/fixtures/stream-rc.yaml +10 -12
  37. data/spec/fixtures/tangent-point-rc.yaml +10 -11
  38. data/spec/fixtures/time-rc.yaml +6 -8
  39. data/spec/modspec/conformance_class_spec.rb +44 -35
  40. data/spec/modspec/conformance_test_spec.rb +26 -7
  41. data/spec/modspec/normative_statement_spec.rb +16 -12
  42. data/spec/modspec/normative_statements_class_spec.rb +18 -6
  43. data/spec/modspec/suite_spec.rb +198 -37
  44. data/spec/modspec_spec.rb +7 -7
  45. data/spec/spec_helper.rb +1 -0
  46. metadata +6 -4
data/lib/modspec/suite.rb CHANGED
@@ -6,14 +6,16 @@ module Modspec
6
6
  class Suite < Lutaml::Model::Serializable
7
7
  attribute :identifier, Identifier
8
8
  attribute :name, :string
9
- attribute :normative_statements_classes, NormativeStatementsClass, collection: true
9
+ attribute :normative_statements_classes, NormativeStatementsClass,
10
+ collection: true
10
11
  attribute :conformance_classes, ConformanceClass, collection: true
11
12
 
12
13
  xml do
13
- root "suite"
14
+ element "suite"
14
15
  map_attribute "identifier", to: :identifier
15
16
  map_element "name", to: :name
16
- map_element "normative-statements-classes", to: :normative_statements_classes
17
+ map_element "normative-statements-classes",
18
+ to: :normative_statements_classes
17
19
  map_element "conformance-classes", to: :conformance_classes
18
20
  end
19
21
 
@@ -24,13 +26,20 @@ module Modspec
24
26
  errors.concat(validate_cycles)
25
27
  errors.concat(validate_label_uniqueness)
26
28
  errors.concat(validate_dependencies)
27
- errors.concat(normative_statements_classes.flat_map { |n| n.validate(self) }) unless normative_statements_classes.nil?
29
+ unless normative_statements_classes.nil?
30
+ errors.concat(normative_statements_classes.flat_map do |n|
31
+ n.validate(self)
32
+ end)
33
+ end
28
34
  errors.concat(conformance_classes.flat_map(&:validate)) unless conformance_classes.nil?
29
35
  errors
30
36
  end
31
37
 
32
38
  def combine(other_suite)
33
- raise ArgumentError, "Argument must be a Modspec::Suite" unless other_suite.is_a?(Modspec::Suite)
39
+ unless other_suite.is_a?(Modspec::Suite)
40
+ raise ArgumentError,
41
+ "Argument must be a Modspec::Suite"
42
+ end
34
43
 
35
44
  combined_suite = dup
36
45
  combined_suite.all_identifiers = nil
@@ -45,9 +54,9 @@ module Modspec
45
54
  end
46
55
 
47
56
  # Ensure uniqueness of identifiers
48
- combined_suite.normative_statements_classes.uniq!(&:identifier) if combined_suite.normative_statements_classes
57
+ combined_suite.normative_statements_classes&.uniq!(&:identifier)
49
58
 
50
- combined_suite.conformance_classes.uniq!(&:identifier) if combined_suite.conformance_classes
59
+ combined_suite.conformance_classes&.uniq!(&:identifier)
51
60
 
52
61
  combined_suite.name = "#{name} + #{other_suite.name}"
53
62
 
@@ -69,8 +78,10 @@ module Modspec
69
78
  attr_writer :all_identifiers
70
79
 
71
80
  def resolve_conflicts(other_suite)
72
- resolve_conflicts_for(normative_statements_classes, other_suite.normative_statements_classes)
73
- resolve_conflicts_for(conformance_classes, other_suite.conformance_classes)
81
+ resolve_conflicts_for(normative_statements_classes,
82
+ other_suite.normative_statements_classes)
83
+ resolve_conflicts_for(conformance_classes,
84
+ other_suite.conformance_classes)
74
85
  end
75
86
 
76
87
  def self.from_yaml_files(*files)
@@ -84,18 +95,17 @@ module Modspec
84
95
  end
85
96
 
86
97
  def setup_relationships
87
- all_requirements = if normative_statements_classes
88
- normative_statements_classes.flat_map(&:normative_statements)
89
- else
90
- []
91
- end
98
+ return unless normative_statements_classes && conformance_classes
92
99
 
93
- return unless conformance_classes
100
+ req_index = normative_statements_classes
101
+ .flat_map(&:normative_statements)
102
+ .to_h { |r| [r.identifier.to_s, r] }
94
103
 
95
104
  conformance_classes.each do |cc|
96
105
  cc.tests.each do |ct|
97
- ct.corresponding_requirements = all_requirements.select do |r|
98
- ct.targets.map(&:to_s).include?(r.identifier.to_s)
106
+ targets = Array(ct.targets).map(&:to_s)
107
+ ct.corresponding_requirements = targets.filter_map do |t|
108
+ req_index[t]
99
109
  end
100
110
  ct.parent_class = cc
101
111
  end
@@ -108,7 +118,9 @@ module Modspec
108
118
  return if self_collection.nil? || other_collection.nil?
109
119
 
110
120
  other_collection.each do |other_item|
111
- existing_item = self_collection.find { |item| item.identifier == other_item.identifier }
121
+ existing_item = self_collection.find do |item|
122
+ item.identifier == other_item.identifier
123
+ end
112
124
  if existing_item
113
125
  # Merge attributes of conflicting items
114
126
  merge_attributes(existing_item, other_item)
@@ -133,7 +145,7 @@ module Modspec
133
145
  def validate_cycles
134
146
  graph = build_dependency_graph
135
147
  cycles = detect_cycles(graph)
136
- cycles.map { |cycle| "Cycle detected: #{cycle.join(" -> ")}" }
148
+ cycles.map { |cycle| "Cycle detected: #{cycle.join(' -> ')}" }
137
149
  end
138
150
 
139
151
  # Combine all statements into a single array
@@ -158,14 +170,14 @@ module Modspec
158
170
 
159
171
  all_statements.each do |statement|
160
172
  id = statement.identifier.to_s
161
- graph[id] = Set.new
173
+ deps = Set.new
162
174
 
163
- # Define all dependency-like properties to check
164
- dependency_properties = %i[dependencies indirect_dependency implements targets]
165
-
166
- dependency_properties.each do |property|
167
- graph[id].merge(statement.send(property).map(&:to_s)) if statement.respond_to?(property) && !statement.send(property).nil?
175
+ %i[dependencies indirect_dependency implements targets].each do |prop|
176
+ refs = statement.send(prop) if statement.respond_to?(prop)
177
+ deps.merge(refs.map(&:to_s)) if refs
168
178
  end
179
+
180
+ graph[id] = deps
169
181
  end
170
182
 
171
183
  graph
@@ -191,19 +203,14 @@ module Modspec
191
203
  recursion_stack.add(node)
192
204
  path.push(node)
193
205
 
194
- # Check if the node exists in the graph and has dependencies
195
- if graph[node]
196
- graph[node].each do |neighbor|
197
- if !visited.include?(neighbor)
198
- cycle = detect_cycle_util(neighbor, graph, visited, recursion_stack, path)
199
- return cycle if cycle
200
- elsif recursion_stack.include?(neighbor)
201
- return path[path.index(neighbor)..] + [neighbor]
202
- end
206
+ graph[node]&.each do |neighbor|
207
+ if !visited.include?(neighbor)
208
+ cycle = detect_cycle_util(neighbor, graph, visited,
209
+ recursion_stack, path)
210
+ return cycle if cycle
211
+ elsif recursion_stack.include?(neighbor)
212
+ return path[path.index(neighbor)..] + [neighbor]
203
213
  end
204
- else
205
- # If the node doesn't exist in the graph, log a warning
206
- puts "Warning: Node #{node} referenced but not found in the graph"
207
214
  end
208
215
 
209
216
  path.pop
@@ -225,24 +232,24 @@ module Modspec
225
232
  end
226
233
 
227
234
  def validate_dependencies
228
- all_identifiers = collect_all_identifiers
235
+ all_ids = collect_all_identifiers
229
236
 
230
237
  errors = []
231
- if normative_statements_classes
232
- normative_statements_classes.each do |nsc|
233
- errors.concat(validate_class_dependencies(nsc, all_identifiers))
234
- nsc.normative_statements.each do |ns|
235
- errors.concat(validate_statement_dependencies(ns, all_identifiers))
236
- end
238
+ normative_statements_classes&.each do |nsc|
239
+ errors.concat(validate_refs(nsc, all_ids, :dependencies))
240
+ errors.concat(validate_refs(nsc, all_ids, :implements))
241
+ nsc.normative_statements.each do |ns|
242
+ errors.concat(validate_refs(ns, all_ids, :dependencies))
243
+ errors.concat(validate_refs(ns, all_ids, :indirect_dependency))
244
+ errors.concat(validate_refs(ns, all_ids, :implements))
237
245
  end
238
246
  end
239
247
 
240
- if conformance_classes
241
- conformance_classes.each do |cc|
242
- errors.concat(validate_class_dependencies(cc, all_identifiers))
243
- cc.tests.each do |ct|
244
- errors.concat(validate_test_targets(ct, all_identifiers))
245
- end
248
+ conformance_classes&.each do |cc|
249
+ errors.concat(validate_refs(cc, all_ids, :dependencies))
250
+ cc.tests.each do |ct|
251
+ errors.concat(validate_refs(ct, all_ids, :dependencies))
252
+ errors.concat(validate_refs(ct, all_ids, :targets))
246
253
  end
247
254
  end
248
255
 
@@ -252,49 +259,33 @@ module Modspec
252
259
  def collect_all_identifiers
253
260
  identifiers = {}
254
261
 
255
- if normative_statements_classes
256
- normative_statements_classes.each do |nsc|
257
- identifiers[nsc.identifier.to_s] = nsc
258
- nsc.normative_statements.each do |ns|
259
- identifiers[ns.identifier.to_s] = ns
260
- end
262
+ normative_statements_classes&.each do |nsc|
263
+ identifiers[nsc.identifier.to_s] = nsc
264
+ nsc.normative_statements.each do |ns|
265
+ identifiers[ns.identifier.to_s] = ns
261
266
  end
262
267
  end
263
268
 
264
- if conformance_classes
265
- conformance_classes.each do |cc|
266
- identifiers[cc.identifier.to_s] = cc
267
- cc.tests.each do |ct|
268
- identifiers[ct.identifier.to_s] = ct
269
- end
269
+ conformance_classes&.each do |cc|
270
+ identifiers[cc.identifier.to_s] = cc
271
+ cc.tests.each do |ct|
272
+ identifiers[ct.identifier.to_s] = ct
270
273
  end
271
274
  end
272
275
 
273
276
  identifiers
274
277
  end
275
278
 
276
- def validate_class_dependencies(klass, all_identifiers)
277
- errors = []
278
- klass.dependencies&.each do |dep|
279
- errors << "Invalid dependency #{dep} in #{klass.identifier}" unless all_identifiers.key?(dep.to_s)
280
- end
281
- errors
282
- end
283
-
284
- def validate_statement_dependencies(statement, all_identifiers)
285
- errors = []
286
- statement.dependencies&.each do |dep|
287
- errors << "Invalid dependency #{dep} in #{statement.identifier}" unless all_identifiers.key?(dep.to_s)
288
- end
289
- errors
290
- end
279
+ def validate_refs(obj, all_ids, property)
280
+ refs = obj.send(property)
281
+ return [] unless refs
291
282
 
292
- def validate_test_targets(test, all_identifiers)
293
- errors = []
294
- test.targets&.each do |target|
295
- errors << "Invalid target #{target} in #{test.identifier}" unless all_identifiers.key?(target.to_s)
283
+ refs.filter_map do |ref|
284
+ unless all_ids.key?(ref.to_s)
285
+ "Invalid #{property.to_s.tr('_',
286
+ ' ')} #{ref} in #{obj.identifier}"
287
+ end
296
288
  end
297
- errors
298
289
  end
299
290
  end
300
291
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Modspec
4
- VERSION = "0.1.4"
4
+ VERSION = "0.2.1"
5
5
  end
data/lib/modspec.rb CHANGED
@@ -2,28 +2,14 @@
2
2
 
3
3
  require_relative "modspec/version"
4
4
  require "lutaml/model"
5
+ require "set"
5
6
 
6
7
  module Modspec
7
- class Error < StandardError; end
8
-
9
- # Your code goes here...
10
- end
11
-
12
- require_relative "modspec/identifier"
13
- require_relative "modspec/normative_statement"
14
- require_relative "modspec/normative_statements_class"
15
- require_relative "modspec/conformance_test"
16
- require_relative "modspec/conformance_class"
17
- require_relative "modspec/suite"
18
-
19
- require "lutaml/model/xml_adapter/nokogiri_adapter"
20
- require "lutaml/model/json_adapter/standard_json_adapter"
21
- require "lutaml/model/toml_adapter/toml_rb_adapter"
22
- require "lutaml/model/yaml_adapter/standard_yaml_adapter"
23
-
24
- Lutaml::Model::Config.configure do |config|
25
- config.xml_adapter = Lutaml::Model::XmlAdapter::NokogiriAdapter
26
- config.yaml_adapter = Lutaml::Model::YamlAdapter::StandardYamlAdapter
27
- config.json_adapter = Lutaml::Model::JsonAdapter::StandardJsonAdapter
28
- config.toml_adapter = Lutaml::Model::TomlAdapter::TomlRbAdapter
8
+ autoload :Identifier, "modspec/identifier"
9
+ autoload :NormativeStatement, "modspec/normative_statement"
10
+ autoload :NormativeStatementPart, "modspec/normative_statement"
11
+ autoload :NormativeStatementsClass, "modspec/normative_statements_class"
12
+ autoload :ConformanceTest, "modspec/conformance_test"
13
+ autoload :ConformanceClass, "modspec/conformance_class"
14
+ autoload :Suite, "modspec/suite"
29
15
  end
data/modspec.gemspec CHANGED
@@ -20,16 +20,17 @@ Gem::Specification.new do |spec|
20
20
  spec.metadata["homepage_uri"] = spec.homepage
21
21
  spec.metadata["source_code_uri"] = spec.homepage
22
22
  spec.metadata["bug_tracker_uri"] = "#{spec.homepage}/issues"
23
+ spec.metadata["rubygems_mfa_required"] = "true"
23
24
 
24
25
  # Specify which files should be added to the gem when it is released.
25
26
  spec.files = all_files_in_git
26
- .reject { |f| f.match(%r{\A(?:test|features|bin|\.)/}) }
27
+ .reject { |f| f.match(%r{\A(?:test|features|bin|\.)/}) }
27
28
 
28
29
  spec.bindir = "exe"
29
30
  spec.executables = spec.files.grep(%r{\Aexe/}) { |f| File.basename(f) }
30
31
  spec.require_paths = ["lib"]
31
32
 
32
- spec.add_dependency "lutaml-model", "~>0.7"
33
+ spec.add_dependency "lutaml-model", "~> 0.8.0"
33
34
  spec.add_dependency "nokogiri"
34
35
  spec.add_dependency "toml-rb"
35
36
  end
@@ -80,11 +80,11 @@ guidance::
80
80
  test-purpose:: {{test.purpose}}
81
81
  {% endif %}
82
82
 
83
- {% if {{test.method}} %}
83
+ {% if {{test.test_method}} %}
84
84
  test-method::
85
85
  +
86
86
  --
87
- {{test.method}}
87
+ {{test.test_method}}
88
88
  --
89
89
  {% endif %}
90
90
 
@@ -1,16 +1,14 @@
1
1
  ---
2
2
  normative_statements_classes:
3
3
  - name: JSON encoding of Advanced SDU
4
- identifier: /req/advanced-encoding-json
5
- description: |
6
- Requirements for the JSON encoding of a Advanced SDU.
4
+ identifier: "/req/advanced-encoding-json"
5
+ description: 'Requirements for the JSON encoding of a Advanced SDU.'
7
6
  implements:
8
- - /req/advanced
9
-
7
+ - "/req/advanced"
10
8
  normative_statements:
11
-
12
9
  - name: Specification as JSON schema
13
- identifier: /req/advanced-encoding-json/definition
10
+ identifier: "/req/advanced-encoding-json/definition"
14
11
  statement: |
15
12
  A JSON-encoded Advanced GeoPose SHALL conform to the
16
13
  Advanced JSON-Schema 2019-9 definition (<<advanced_geopose_json_schema>>).
14
+ obligation: requirement
@@ -1,37 +1,34 @@
1
1
  ---
2
2
  normative_statements_classes:
3
3
  - name: Advanced logical model SDU
4
- identifier: /req/advanced
4
+ identifier: "/req/advanced"
5
5
  description: |
6
6
  The Advanced Target has a more general structure than Basic-YPR and
7
7
  Basic-Quaternion, supporting flexible specification of Outer Frame and a
8
8
  Valid Time.
9
-
10
9
  dependencies:
11
- - /req/global
12
- - /req/frame-spec
13
- - /req/time
10
+ - "/req/global"
11
+ - "/req/frame-spec"
12
+ - "/req/time"
14
13
  normative_statements:
15
-
16
14
  - name: Expression of valid time as GeoPose_Instant
17
- identifier: /req/advanced/valid-time
15
+ identifier: "/req/advanced/valid-time"
18
16
  dependencies:
19
- - /req/time/instant
20
-
17
+ - "/req/time/instant"
21
18
  statement: |
22
19
  The `Advanced.validTime` attribute shall be represented by a
23
20
  `GeoPose_Instant` object.
24
-
21
+ obligation: requirement
25
22
  - name: Expression of outer frame
26
- identifier: /req/advanced/frame-spec
23
+ identifier: "/req/advanced/frame-spec"
27
24
  dependencies:
28
- - /req/frame-spec
25
+ - "/req/frame-spec"
29
26
  statement: |
30
27
  The `Advanced.frameSpecification` attribute shall represent an explicit
31
28
  frame specification with the `ExplicitFrameSpec` object.
32
-
29
+ obligation: requirement
33
30
  - name: Expression of inner frame
34
- identifier: /req/advanced/quaternion
31
+ identifier: "/req/advanced/quaternion"
35
32
  statement: |
36
33
  The `Advanced.quaternion` attribute shall contain a quaternion expressed
37
34
  using the UnitQuaternion datatype value expressed as four real numbers,
@@ -41,3 +38,4 @@ normative_statements_classes:
41
38
  SHALL be applied to an initial reference frame oriented East-North-Up
42
39
  (ENU) coordinate system where the coordinate axes East, North, and Up
43
40
  correspond to the axes X, Y, Z.
41
+ obligation: requirement
@@ -1,17 +1,15 @@
1
1
  ---
2
2
  normative_statements_classes:
3
3
  - name: Permissive JSON encoding of Basic-Quaternion SDU
4
- identifier: /req/basic-quaternion-encoding-json
5
- description: |
6
- Requirements for the JSON encoding of a Basic-Quaternion SDU.
4
+ identifier: "/req/basic-quaternion-encoding-json"
5
+ description: 'Requirements for the JSON encoding of a Basic-Quaternion SDU.'
7
6
  implements:
8
- - /req/basic-quaternion
9
-
7
+ - "/req/basic-quaternion"
10
8
  normative_statements:
11
-
12
9
  - name: Specification as JSON schema
13
- identifier: /req/basic-quaternion-encoding-json/definition
10
+ identifier: "/req/basic-quaternion-encoding-json/definition"
14
11
  statement: |
15
12
  A JSON-encoded Basic-Quaternion GeoPose SHALL conform to the
16
13
  Basic-Quaternion JSON-Schema 2019-9 definition
17
14
  (<<basic_quaternion_permissive_json_schema>>).
15
+ obligation: requirement
@@ -1,19 +1,18 @@
1
1
  ---
2
2
  normative_statements_classes:
3
3
  - name: Strict JSON encoding of Basic-Quaternion SDU
4
- identifier: /req/basic-quaternion-encoding-json-strict
4
+ identifier: "/req/basic-quaternion-encoding-json-strict"
5
5
  description: |
6
6
  Requirements for the JSON encoding of a Basic-Quaternion SDU in strict mode.
7
7
  The strict encoding does not allow specification of JSON elements outside of
8
8
  the schema.
9
9
  implements:
10
- - /req/basic-quaternion
11
-
10
+ - "/req/basic-quaternion"
12
11
  normative_statements:
13
-
14
12
  - name: Specification as JSON schema
15
- identifier: /req/basic-quaternion-encoding-json-strict/definition
13
+ identifier: "/req/basic-quaternion-encoding-json-strict/definition"
16
14
  statement: |
17
15
  A JSON-encoded Basic-Quaternion GeoPose SHALL conform to the
18
16
  strict Basic-Quaternion JSON-Schema 2019-9 definition
19
17
  (<<basic_quaternion_strict_json_schema>>).
18
+ obligation: requirement
@@ -1,26 +1,24 @@
1
1
  ---
2
2
  normative_statements_classes:
3
3
  - name: Basic-Quaternion logical model SDU
4
- identifier: /req/basic-quaternion
4
+ identifier: "/req/basic-quaternion"
5
5
  description: |
6
6
  The Basic-Quaternion Target has a simple structure with no options. Position
7
7
  is specified as a point in an LTP-ENU frame and rotation is specified as a
8
8
  unit quaternion.
9
-
10
9
  dependencies:
11
- - /req/global
12
- - /req/tangent-point
10
+ - "/req/global"
11
+ - "/req/tangent-point"
13
12
  normative_statements:
14
-
15
13
  - name: Expression of outer frame
16
- identifier: /req/basic-quaternion/position
14
+ identifier: "/req/basic-quaternion/position"
17
15
  statement: |
18
16
  The `Basic_Quaternion.position` attribute shall represent the outer frame,
19
17
  specified by an implicit WGS-84 CRS and an implicit EPSG 4461-CS (LTP-ENU)
20
18
  coordinate system and explicit parameters to define the tangent point.
21
-
19
+ obligation: requirement
22
20
  - name: Expression of inner frame
23
- identifier: /req/basic-quaternion/quaternion
21
+ identifier: "/req/basic-quaternion/quaternion"
24
22
  statement: |
25
23
  The `Basic_Quaternion.quaternion` attribute shall represent the inner
26
24
  frame, which shall be a rotation-only transformation using a unit
@@ -32,3 +30,4 @@ normative_statements_classes:
32
30
  quaternion shall be applied to an initial reference frame oriented
33
31
  East-North-Up (ENU) coordinate system where the coordinate axes East,
34
32
  North, and Up correspond to the axes X, Y, Z.
33
+ obligation: requirement
@@ -1,21 +1,18 @@
1
1
  ---
2
2
  normative_statements_classes:
3
3
  - name: JSON encoding of Basic-YPR SDU
4
- identifier: /req/basic-ypr-encoding-json
5
- description: |
6
- Requirements for the JSON encoding of a Basic-YPR SDU.
4
+ identifier: "/req/basic-ypr-encoding-json"
5
+ description: 'Requirements for the JSON encoding of a Basic-YPR SDU.'
7
6
  implements:
8
- - /req/basic-ypr
9
-
7
+ - "/req/basic-ypr"
10
8
  normative_statements:
11
-
12
9
  - name: Specification as JSON schema
13
- identifier: /req/basic-ypr-encoding-json/definition
10
+ identifier: "/req/basic-ypr-encoding-json/definition"
14
11
  statement: |
15
12
  A JSON-encoded Basic-YPR GeoPose SHALL conform to the Basic-YPR
16
13
  JSON-Schema 2019-9 definition (<<basic_ypr_json_schema>>).
17
-
18
14
  guidance:
19
15
  - |
20
16
  This JSON encoding is extensible because the JSON-Schema
21
17
  "additionalProperties" property is set to the default value of *true*.
18
+ obligation: requirement
@@ -1,25 +1,24 @@
1
1
  ---
2
2
  normative_statements_classes:
3
3
  - name: Basic-YPR logical model SDU
4
- identifier: /req/basic-ypr
4
+ identifier: "/req/basic-ypr"
5
5
  description: |
6
6
  The Basic-YPR Target has a simple structure with no options. Position is
7
7
  specified as a point in an LTP-ENU frame and rotation is specified by yaw,
8
8
  pitch, and roll angles specified in decimal degrees.
9
9
  dependencies:
10
- - /req/global
11
- - /req/tangent-point
10
+ - "/req/global"
11
+ - "/req/tangent-point"
12
12
  normative_statements:
13
-
14
13
  - name: Expression of outer frame
15
- identifier: /req/basic-ypr/position
14
+ identifier: "/req/basic-ypr/position"
16
15
  statement: |
17
16
  The `Basic_YPR.position` attribute shall represent the outer frame,
18
17
  specified by an implicit WGS-84 CRS and an implicit EPSG 4461-CS (LTP-ENU)
19
18
  coordinate system and explicit parameters to define the tangent point.
20
-
19
+ obligation: requirement
21
20
  - name: Expression of inner frame
22
- identifier: /req/basic-ypr/angles
21
+ identifier: "/req/basic-ypr/angles"
23
22
  statement: |
24
23
  The `Basic_YPR.angles` attribute shall represent the inner frame,
25
24
  which is a rotation-only transformation with Yaw, Pitch, and Roll (YPR)
@@ -30,3 +29,4 @@ normative_statements_classes:
30
29
  x, applied in that order, corresponding to the conventional Yaw, Pitch,
31
30
  and Roll angles. The unit of measure SHALL be the degree and the angles
32
31
  represented as signed real number values.
32
+ obligation: requirement
@@ -1,16 +1,13 @@
1
1
  ---
2
2
  normative_statements_classes:
3
3
  - name: JSON encoding of Chain SDU
4
- identifier: /req/chain-encoding-json
5
- description: |
6
- Requirements for the JSON encoding of a Chain SDU.
4
+ identifier: "/req/chain-encoding-json"
5
+ description: 'Requirements for the JSON encoding of a Chain SDU.'
7
6
  implements:
8
- - /req/chain
9
-
7
+ - "/req/chain"
10
8
  normative_statements:
11
-
12
9
  - name: Specification as JSON schema
13
- identifier: /req/chain-encoding-json/definition
10
+ identifier: "/req/chain-encoding-json/definition"
14
11
  statement: |
15
12
  A JSON-encoded GeoPose Chain SHALL conform to the GeoPose Chain
16
13
  JSON-Schema 2019-9 definition (<<chain_json_schema>>).
@@ -18,3 +15,4 @@ normative_statements_classes:
18
15
  - |
19
16
  This JSON encoding is extensible because the JSON-Schema
20
17
  "additionalProperties" property is set to the default value of *true*.
18
+ obligation: requirement
@@ -1,36 +1,34 @@
1
1
  ---
2
2
  normative_statements_classes:
3
3
  - name: Chain logical model SDU
4
- identifier: /req/chain
4
+ identifier: "/req/chain"
5
5
  description: |
6
6
  The Chain Target supports relationships between a linear sequence of pose
7
7
  relationships. The first frame in the sequence must be an Outer Frame.
8
-
9
8
  dependencies:
10
- - /req/global
11
- - /req/frame-spec
12
- - /req/time
13
-
9
+ - "/req/global"
10
+ - "/req/frame-spec"
11
+ - "/req/time"
14
12
  normative_statements:
15
-
16
13
  - name: Expression of valid time as GeoPose_Instant
17
- identifier: /req/chain/valid-time
14
+ identifier: "/req/chain/valid-time"
18
15
  dependencies:
19
- - /req/time/instant
16
+ - "/req/time/instant"
20
17
  statement: |
21
18
  The `Chain.validTime` attribute shall be represented by a
22
19
  `GeoPose_Instant` object.
23
-
20
+ obligation: requirement
24
21
  - name: Specification of initial frame
25
- identifier: /req/chain/initial-frame
22
+ identifier: "/req/chain/initial-frame"
26
23
  statement: |
27
24
  The `Chain.outerFrame` attribute shall represent the first frame in the
28
25
  sequence with the `ExplicitFrameSpec` object.
29
-
26
+ obligation: requirement
30
27
  - name: Chain of frame specifications
31
- identifier: /req/chain/frame-chain
28
+ identifier: "/req/chain/frame-chain"
32
29
  statement: |
33
30
  The `Chain.frameChain` attribute shall represent a list of explicit
34
31
  frame specifications with an array of `ExplicitFrameSpec` objects.
35
32
  Each index value shall be a distinct integer value between 0 and one less
36
33
  than the number of elements in the frameChain property.
34
+ obligation: requirement