mn-requirements 0.2.2 → 0.3.0
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.
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 4f81b57e8350c7018f06bb68420de8d7b409b7f9ff4b81eb0d98d06f484e246e
|
4
|
+
data.tar.gz: 771ba5edb39491ad133dfc2d8cacaba2e11a0eba8b95389a2d834ddd84d0227a
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 38d500ecb762b731b2ef373c55c67b0cfef8e4a93bfcf4619d629c6fe69fae635c4362502bf3235a94f3b5cfbab7248fcd5e7110c42640916bd4e3b3b33e21dc
|
7
|
+
data.tar.gz: 8d5c5b770acd55b9b0006345f3c743e863239257c353626e4f56f0cb50dc218f9512338080e30bec75160e89b61bf85b747296ead049480812625799cc3fc74e
|
@@ -197,9 +197,9 @@ module Metanorma
|
|
197
197
|
end
|
198
198
|
|
199
199
|
def requirement_description_parse(node, out)
|
200
|
-
lbl = "
|
201
|
-
recommend_class(node.parent) == "
|
202
|
-
lbl = "
|
200
|
+
lbl = "description"
|
201
|
+
recommend_class(node.parent) == "recommend" and
|
202
|
+
lbl = "statement"
|
203
203
|
out << "<tr><th>#{@labels['modspec'][lbl]}</th>" \
|
204
204
|
"<td>#{node.children.to_xml}</td></tr>"
|
205
205
|
out
|
@@ -1,3 +1,10 @@
|
|
1
|
+
class Nokogiri::XML::Document
|
2
|
+
def reqt_iter(&block)
|
3
|
+
xpath("//xmlns:requirement | //xmlns:recommendation | //xmlns:permission")
|
4
|
+
.each_with_object({}, &block)
|
5
|
+
end
|
6
|
+
end
|
7
|
+
|
1
8
|
module Metanorma
|
2
9
|
class Requirements
|
3
10
|
class Modspec < Default
|
@@ -36,10 +43,9 @@ module Metanorma
|
|
36
43
|
end
|
37
44
|
|
38
45
|
def reqtlabels(doc)
|
39
|
-
doc.
|
40
|
-
.
|
41
|
-
|
42
|
-
end
|
46
|
+
doc.reqt_iter do |r, m|
|
47
|
+
l = r.at(ns("./identifier"))&.text and m[l] = r["id"]
|
48
|
+
end
|
43
49
|
end
|
44
50
|
|
45
51
|
# embedded reqts xref to reqts via label lookup
|
@@ -64,30 +70,23 @@ module Metanorma
|
|
64
70
|
end
|
65
71
|
|
66
72
|
def reqt_ids(docxml)
|
67
|
-
docxml.
|
68
|
-
.
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
end
|
73
|
+
docxml.reqt_iter do |r, m|
|
74
|
+
id = r.at(ns("./identifier")) or next
|
75
|
+
m[id.text] =
|
76
|
+
{ id: r["id"], lbl: @xrefs.anchor(r["id"], :xref, false) }
|
77
|
+
end
|
73
78
|
end
|
74
79
|
|
75
80
|
def reqt_links_test(docxml)
|
76
|
-
docxml.
|
77
|
-
.each_with_object({}) do |r, m|
|
78
|
-
reqt_links_test1(r, m)
|
79
|
-
end
|
81
|
+
docxml.reqt_iter { |r, m| reqt_links_test1(r, m) }
|
80
82
|
end
|
81
83
|
|
82
84
|
def reqt_links_test1(reqt, acc)
|
83
|
-
|
84
|
-
verification).include?(reqt["type"])
|
85
|
-
|
85
|
+
%w(conformanceclass verification).include?(reqt["type"]) or return
|
86
86
|
subj = reqt_extract_target(reqt)
|
87
87
|
id = reqt.at(ns("./identifier")) or return
|
88
88
|
lbl = @xrefs.anchor(@reqt_ids[id.text.strip][:id], :xref, false)
|
89
|
-
|
90
|
-
|
89
|
+
(subj && lbl) or return
|
91
90
|
acc[subj.text] = { lbl: lbl, id: reqt["id"] }
|
92
91
|
end
|
93
92
|
|
@@ -110,23 +109,20 @@ module Metanorma
|
|
110
109
|
|
111
110
|
# we have not implemented multiple levels of nesting of classes
|
112
111
|
def reqt_links_class(docxml)
|
113
|
-
docxml.
|
114
|
-
.
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
.each do |r1|
|
120
|
-
m = reqt_links_class1(id, r, r1, m)
|
121
|
-
end
|
112
|
+
docxml.reqt_iter do |r, m|
|
113
|
+
%w(class conformanceclass).include?(r["type"]) or next
|
114
|
+
id = r.at(ns("./identifier")) or next
|
115
|
+
r.xpath(ns("./requirement | ./recommendation | ./permission"))
|
116
|
+
.each do |r1|
|
117
|
+
m = reqt_links_class1(id, r, r1, m)
|
122
118
|
end
|
119
|
+
end
|
123
120
|
end
|
124
121
|
|
125
122
|
def reqt_links_class1(id, parent_reqt, reqt, acc)
|
126
123
|
id1 = reqt.at(ns("./identifier")) or return acc
|
127
124
|
lbl = @xrefs.anchor(@reqt_ids[id.text.strip][:id], :xref, false)
|
128
|
-
return acc
|
129
|
-
|
125
|
+
lbl or return acc
|
130
126
|
acc[id1.text] = { lbl: lbl, id: parent_reqt["id"] }
|
131
127
|
acc
|
132
128
|
end
|
@@ -139,10 +135,7 @@ module Metanorma
|
|
139
135
|
end
|
140
136
|
|
141
137
|
def reqt_id_base_init(docxml)
|
142
|
-
docxml.
|
143
|
-
.each_with_object({}) do |r, m|
|
144
|
-
m[r["id"]] = reqt_extract_id_base(r)&.text
|
145
|
-
end
|
138
|
+
docxml.reqt_iter { |r, m| m[r["id"]] = reqt_extract_id_base(r)&.text }
|
146
139
|
end
|
147
140
|
|
148
141
|
def reqt_id_base_inherit(ret, class2reqt)
|
@@ -1,10 +1,15 @@
|
|
1
|
+
require "tsort"
|
2
|
+
|
1
3
|
module Metanorma
|
2
4
|
class Requirements
|
3
5
|
class Modspec < Default
|
4
6
|
def validate(reqt, log)
|
7
|
+
@fatalerrors = []
|
5
8
|
@log ||= log
|
6
9
|
@ids ||= reqt_links(reqt.document)
|
10
|
+
reqt_cycles_validate
|
7
11
|
reqt_link_validate(reqt)
|
12
|
+
@fatalerrors
|
8
13
|
end
|
9
14
|
|
10
15
|
def nested_reqt?(reqt)
|
@@ -109,17 +114,26 @@ module Metanorma
|
|
109
114
|
.each_with_object({ id: {}, class: {}, label: {} }) do |r, m|
|
110
115
|
next if nested_reqt?(r)
|
111
116
|
|
112
|
-
reqt_links1(r, m)
|
117
|
+
reqt_links1(r, m, type2validate(r), reqt_links_struct(r))
|
113
118
|
end
|
114
119
|
end
|
115
120
|
|
116
|
-
def reqt_links1(reqt, hash)
|
117
|
-
|
118
|
-
a = reqt_links_struct(reqt)
|
119
|
-
hash[:id][reqt["id"]] = a
|
121
|
+
def reqt_links1(reqt, hash, type, struct)
|
122
|
+
hash[:id][reqt["id"]] = struct
|
120
123
|
hash[:class][type] ||= []
|
121
|
-
hash[:class][type] <<
|
122
|
-
hash
|
124
|
+
hash[:class][type] << struct
|
125
|
+
reqt_links1_label(reqt, hash, struct)
|
126
|
+
end
|
127
|
+
|
128
|
+
def reqt_links1_label(reqt, hash, struct)
|
129
|
+
return hash unless struct[:label]
|
130
|
+
|
131
|
+
if hash[:label][struct[:label]]
|
132
|
+
msg = "Modspec identifier #{struct[:label]} is used more than once"
|
133
|
+
@log.add("Requirements", reqt, msg)
|
134
|
+
@fatalerrors << msg
|
135
|
+
end
|
136
|
+
hash[:label][struct[:label]] = reqt["id"]
|
123
137
|
hash
|
124
138
|
end
|
125
139
|
|
@@ -140,6 +154,54 @@ module Metanorma
|
|
140
154
|
indirect_dependency: classif_tag(reqt, "indirect-dependency"),
|
141
155
|
implements: classif_tag(reqt, "implements") }
|
142
156
|
end
|
157
|
+
|
158
|
+
def reqt_cycles_validate
|
159
|
+
@cycles_validated and return
|
160
|
+
@cycles_validated = true
|
161
|
+
%i(child dependency indirect_dependency implements).each do |x|
|
162
|
+
reqt_cycles_validate1(x)
|
163
|
+
end
|
164
|
+
end
|
165
|
+
|
166
|
+
def reqt_cycles_validate1(link)
|
167
|
+
arr = TSHash.new(@ids[:id].values)
|
168
|
+
arr.link = link
|
169
|
+
TSort.each_strongly_connected_component(
|
170
|
+
lambda { |&b| arr.tsort_each_node(&b) },
|
171
|
+
lambda { |n, &b| arr.tsort_each_child(n, &b) },
|
172
|
+
) do |c|
|
173
|
+
c.size == 1 and next
|
174
|
+
log_cycle(link, c)
|
175
|
+
end
|
176
|
+
end
|
177
|
+
|
178
|
+
def log_cycle(link, path)
|
179
|
+
@log.add("Requirements", nil, <<~MSG
|
180
|
+
Cycle in Modspec linkages through #{link}: #{(path << path.first).join(' => ')}
|
181
|
+
MSG
|
182
|
+
)
|
183
|
+
end
|
184
|
+
|
185
|
+
class TSHash
|
186
|
+
include TSort
|
187
|
+
attr_accessor :link
|
188
|
+
|
189
|
+
def initialize(arr)
|
190
|
+
@hash = arr.each_with_object({}) do |v, m|
|
191
|
+
m[v[:label]] = v
|
192
|
+
end
|
193
|
+
end
|
194
|
+
|
195
|
+
def tsort_each_node(&block)
|
196
|
+
@hash.keys.each(&block)
|
197
|
+
end
|
198
|
+
|
199
|
+
def tsort_each_child(node, &block)
|
200
|
+
(@hash[node] || {})[@link]&.each(&block)
|
201
|
+
end
|
202
|
+
end
|
203
|
+
|
204
|
+
def reqt_cycles_validate_dependency; end
|
143
205
|
end
|
144
206
|
end
|
145
207
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: mn-requirements
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.3.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Ribose Inc.
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2022-11-
|
11
|
+
date: 2022-11-24 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: isodoc-i18n
|