metanorma-standoc 1.10.7 → 1.11.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.
- checksums.yaml +4 -4
- data/README.adoc +19 -23
- data/Rakefile +1 -1
- data/lib/asciidoctor/standoc/base.rb +7 -4
- data/lib/asciidoctor/standoc/basicdoc.rng +21 -4
- data/lib/asciidoctor/standoc/blocks.rb +23 -23
- data/lib/asciidoctor/standoc/blocks_notes.rb +17 -22
- data/lib/asciidoctor/standoc/cleanup.rb +20 -11
- data/lib/asciidoctor/standoc/cleanup_image.rb +6 -7
- data/lib/asciidoctor/standoc/cleanup_inline.rb +45 -7
- data/lib/asciidoctor/standoc/cleanup_maths.rb +5 -6
- data/lib/asciidoctor/standoc/cleanup_ref.rb +5 -0
- data/lib/asciidoctor/standoc/cleanup_reqt.rb +2 -21
- data/lib/asciidoctor/standoc/cleanup_symbols.rb +48 -0
- data/lib/asciidoctor/standoc/cleanup_terms.rb +48 -77
- data/lib/asciidoctor/standoc/cleanup_terms_designations.rb +162 -0
- data/lib/asciidoctor/standoc/cleanup_text.rb +23 -0
- data/lib/asciidoctor/standoc/converter.rb +2 -0
- data/lib/asciidoctor/standoc/inline.rb +7 -5
- data/lib/asciidoctor/standoc/isodoc.rng +420 -76
- data/lib/asciidoctor/standoc/lists.rb +14 -16
- data/lib/asciidoctor/standoc/macros_plantuml.rb +29 -14
- data/lib/asciidoctor/standoc/macros_terms.rb +55 -8
- data/lib/asciidoctor/standoc/ref.rb +1 -1
- data/lib/asciidoctor/standoc/ref_sect.rb +26 -18
- data/lib/asciidoctor/standoc/reqt.rng +23 -2
- data/lib/asciidoctor/standoc/section.rb +13 -12
- data/lib/asciidoctor/standoc/term_lookup_cleanup.rb +50 -11
- data/lib/asciidoctor/standoc/terms.rb +12 -2
- data/lib/asciidoctor/standoc/utils.rb +36 -23
- data/lib/asciidoctor/standoc/validate.rb +45 -27
- data/lib/asciidoctor/standoc/validate_section.rb +5 -2
- data/lib/metanorma/standoc/version.rb +1 -1
- data/metanorma-standoc.gemspec +1 -1
- data/spec/asciidoctor/base_spec.rb +4 -3
- data/spec/asciidoctor/blocks_spec.rb +230 -49
- data/spec/asciidoctor/cleanup_sections_spec.rb +7 -7
- data/spec/asciidoctor/cleanup_spec.rb +105 -286
- data/spec/asciidoctor/cleanup_terms_spec.rb +1020 -0
- data/spec/asciidoctor/inline_spec.rb +2 -2
- data/spec/asciidoctor/lists_spec.rb +6 -6
- data/spec/asciidoctor/macros_plantuml_spec.rb +36 -1
- data/spec/asciidoctor/macros_spec.rb +190 -113
- data/spec/asciidoctor/refs_dl_spec.rb +4 -4
- data/spec/asciidoctor/refs_spec.rb +268 -108
- data/spec/asciidoctor/section_spec.rb +18 -18
- data/spec/asciidoctor/validate_spec.rb +87 -2
- data/spec/spec_helper.rb +8 -8
- data/spec/vcr_cassettes/dated_iso_ref_joint_iso_iec.yml +50 -50
- data/spec/vcr_cassettes/dated_iso_ref_joint_iso_iec1.yml +12 -12
- data/spec/vcr_cassettes/isobib_get_123.yml +13 -13
- data/spec/vcr_cassettes/isobib_get_123_1.yml +25 -25
- data/spec/vcr_cassettes/isobib_get_123_1_fr.yml +31 -31
- data/spec/vcr_cassettes/isobib_get_123_2001.yml +12 -12
- data/spec/vcr_cassettes/isobib_get_124.yml +11 -11
- data/spec/vcr_cassettes/rfcbib_get_rfc8341.yml +14 -14
- data/spec/vcr_cassettes/separates_iev_citations_by_top_level_clause.yml +45 -45
- metadata +8 -5
@@ -40,10 +40,9 @@ module Asciidoctor
|
|
40
40
|
end
|
41
41
|
|
42
42
|
def attr_code(attributes)
|
43
|
-
attributes
|
44
|
-
|
45
|
-
|
46
|
-
end.to_h
|
43
|
+
attributes.compact.transform_values do |v|
|
44
|
+
v.is_a?(String) ? HTMLEntities.new.decode(v) : v
|
45
|
+
end
|
47
46
|
end
|
48
47
|
|
49
48
|
# if the contents of node are blocks, output them to out;
|
@@ -56,7 +55,7 @@ module Asciidoctor
|
|
56
55
|
end
|
57
56
|
|
58
57
|
SUBCLAUSE_XPATH = "//clause[not(parent::sections)]"\
|
59
|
-
|
58
|
+
"[not(ancestor::boilerplate)]".freeze
|
60
59
|
|
61
60
|
def isodoc(lang, script, i18nyaml = nil)
|
62
61
|
conv = html_converter(EmptyAttr.new)
|
@@ -67,29 +66,43 @@ module Asciidoctor
|
|
67
66
|
|
68
67
|
def default_script(lang)
|
69
68
|
case lang
|
70
|
-
when "ar", "fa"
|
71
|
-
|
72
|
-
when "
|
73
|
-
|
74
|
-
when "
|
75
|
-
|
76
|
-
when "
|
77
|
-
|
78
|
-
when "
|
79
|
-
"Grek"
|
80
|
-
when "zh"
|
81
|
-
"Hans"
|
82
|
-
when "ko"
|
83
|
-
"Kore"
|
84
|
-
when "he"
|
85
|
-
"Hebr"
|
86
|
-
when "ja"
|
87
|
-
"Jpan"
|
69
|
+
when "ar", "fa" then "Arab"
|
70
|
+
when "ur" then "Aran"
|
71
|
+
when "ru", "bg" then "Cyrl"
|
72
|
+
when "hi" then "Deva"
|
73
|
+
when "el" then "Grek"
|
74
|
+
when "zh" then "Hans"
|
75
|
+
when "ko" then "Kore"
|
76
|
+
when "he" then "Hebr"
|
77
|
+
when "ja" then "Jpan"
|
88
78
|
else
|
89
79
|
"Latn"
|
90
80
|
end
|
91
81
|
end
|
92
82
|
|
83
|
+
def dl_to_attrs(elem, dlist, name)
|
84
|
+
e = dlist.at("./dt[text()='#{name}']") or return
|
85
|
+
val = e.at("./following::dd/p") || e.at("./following::dd") or return
|
86
|
+
elem[name] = val.text
|
87
|
+
end
|
88
|
+
|
89
|
+
def dl_to_elems(ins, elem, dlist, name)
|
90
|
+
a = elem.at("./#{name}[last()]")
|
91
|
+
ins = a if a
|
92
|
+
dlist.xpath("./dt[text()='#{name}']").each do |e|
|
93
|
+
v = e.at("./following::dd")
|
94
|
+
e = v.elements and e.size == 1 && e.first.name == "p" and v = e.first
|
95
|
+
v.name = name
|
96
|
+
ins.next = v
|
97
|
+
ins = ins.next
|
98
|
+
end
|
99
|
+
ins
|
100
|
+
end
|
101
|
+
|
102
|
+
def term_expr(elem)
|
103
|
+
"<expression><name>#{elem}</name></expression>"
|
104
|
+
end
|
105
|
+
|
93
106
|
class EmptyAttr
|
94
107
|
def attr(_any_attribute)
|
95
108
|
nil
|
@@ -7,8 +7,8 @@ require "iev"
|
|
7
7
|
module Asciidoctor
|
8
8
|
module Standoc
|
9
9
|
module Validate
|
10
|
-
SOURCELOCALITY = "./
|
11
|
-
|
10
|
+
SOURCELOCALITY = "./origin//locality[@type = 'clause']/"\
|
11
|
+
"referenceFrom".freeze
|
12
12
|
|
13
13
|
def init_iev
|
14
14
|
return nil if @no_isobib
|
@@ -21,24 +21,35 @@ module Asciidoctor
|
|
21
21
|
def iev_validate(xmldoc)
|
22
22
|
@iev = init_iev or return
|
23
23
|
xmldoc.xpath("//term").each do |t|
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
m << x&.text&.downcase
|
24
|
+
t.xpath(".//termsource").each do |src|
|
25
|
+
(/^IEC 60050-/.match(src&.at("./origin/@citeas")&.text) &&
|
26
|
+
loc = src.xpath(SOURCELOCALITY)&.text) or next
|
27
|
+
iev_validate1(t, loc, xmldoc)
|
29
28
|
end
|
30
|
-
pref.include?(iev.downcase) or
|
31
|
-
@log.add("Bibliography", t, %(Term "#{pref[0]}" does not match ) +
|
32
|
-
%(IEV #{loc} "#{iev}"))
|
33
29
|
end
|
34
30
|
end
|
35
31
|
|
32
|
+
def iev_validate1(term, loc, xmldoc)
|
33
|
+
iev = @iev.fetch(loc,
|
34
|
+
xmldoc&.at("//language")&.text || "en") or return
|
35
|
+
pref = term.xpath("./preferred//name").inject([]) do |m, x|
|
36
|
+
m << x&.text&.downcase
|
37
|
+
end
|
38
|
+
pref.include?(iev.downcase) or
|
39
|
+
@log.add("Bibliography", term, %(Term "#{pref[0]}" does not match ) +
|
40
|
+
%(IEV #{loc} "#{iev}"))
|
41
|
+
end
|
42
|
+
|
36
43
|
def content_validate(doc)
|
44
|
+
@fatalerror = []
|
45
|
+
xref_validate(doc)
|
37
46
|
section_validate(doc)
|
38
47
|
norm_ref_validate(doc)
|
39
48
|
repeat_id_validate(doc.root)
|
40
49
|
iev_validate(doc.root)
|
41
|
-
concept_validate(doc)
|
50
|
+
concept_validate(doc, "concept", "refterm")
|
51
|
+
concept_validate(doc, "related", "preferred//name")
|
52
|
+
@fatalerror.empty? or clean_abort(@fatalerror.join("\n"), doc.to_xml)
|
42
53
|
end
|
43
54
|
|
44
55
|
def norm_ref_validate(doc)
|
@@ -51,30 +62,30 @@ module Asciidoctor
|
|
51
62
|
"Numeric reference in normative references")
|
52
63
|
found = true
|
53
64
|
end
|
54
|
-
found and
|
55
|
-
clean_abort("Numeric reference in normative references", doc.to_xml)
|
65
|
+
found and @fatalerror << "Numeric reference in normative references"
|
56
66
|
end
|
57
67
|
|
58
|
-
def concept_validate(doc)
|
68
|
+
def concept_validate(doc, tag, refterm)
|
59
69
|
found = false
|
60
|
-
doc.xpath("
|
70
|
+
doc.xpath("//#{tag}/xref").each do |x|
|
61
71
|
next if doc.at("//term[@id = '#{x['target']}']")
|
62
72
|
next if doc.at("//definitions//dt[@id = '#{x['target']}']")
|
63
73
|
|
64
|
-
ref = x&.at("
|
65
|
-
@log.add("Anchors", x,
|
74
|
+
ref = x&.at("../#{refterm}")&.text
|
75
|
+
@log.add("Anchors", x,
|
76
|
+
"#{tag.capitalize} #{ref} is pointing to "\
|
66
77
|
"#{x['target']}, which is not a term or symbol")
|
67
78
|
found = true
|
68
79
|
end
|
69
|
-
found and
|
70
|
-
|
80
|
+
found and
|
81
|
+
@fatalerror << "#{tag.capitalize} not cross-referencing term or symbol"
|
71
82
|
end
|
72
83
|
|
73
84
|
def repeat_id_validate1(ids, elem)
|
74
85
|
if ids[elem["id"]]
|
75
86
|
@log.add("Anchors", elem, "Anchor #{elem['id']} has already been "\
|
76
|
-
|
77
|
-
|
87
|
+
"used at line #{ids[elem['id']]}")
|
88
|
+
@fatalerror << "Multiple instances of same ID: #{elem['id']}"
|
78
89
|
else
|
79
90
|
ids[elem["id"]] = elem.line
|
80
91
|
end
|
@@ -83,12 +94,8 @@ module Asciidoctor
|
|
83
94
|
|
84
95
|
def repeat_id_validate(doc)
|
85
96
|
ids = {}
|
86
|
-
|
87
|
-
|
88
|
-
ids = repeat_id_validate1(ids, x)
|
89
|
-
end
|
90
|
-
rescue StandardError => e
|
91
|
-
clean_abort(e.message, doc.to_xml)
|
97
|
+
doc.xpath("//*[@id]").each do |x|
|
98
|
+
ids = repeat_id_validate1(ids, x)
|
92
99
|
end
|
93
100
|
end
|
94
101
|
|
@@ -130,6 +137,17 @@ module Asciidoctor
|
|
130
137
|
doc
|
131
138
|
end
|
132
139
|
|
140
|
+
# manually check for xref/@target, xref/@to integrity
|
141
|
+
def xref_validate(doc)
|
142
|
+
ids = doc.xpath("//*/@id").each_with_object({}) { |x, m| m[x.text] = 1 }
|
143
|
+
doc.xpath("//xref/@target | //xref/@to").each do |x|
|
144
|
+
next if ids[x.text]
|
145
|
+
|
146
|
+
@log.add("Anchors", x.parent,
|
147
|
+
"Crossreference target #{x.text} is undefined")
|
148
|
+
end
|
149
|
+
end
|
150
|
+
|
133
151
|
def validate(doc)
|
134
152
|
content_validate(doc)
|
135
153
|
schema_validate(formattedstr_strip(doc.dup),
|
@@ -14,7 +14,8 @@ module Asciidoctor
|
|
14
14
|
callouts = x.elements.select { |e| e.name == "callout" }
|
15
15
|
annotations = x.elements.select { |e| e.name == "annotation" }
|
16
16
|
if callouts.size != annotations.size
|
17
|
-
|
17
|
+
@log.add("AsciiDoc Input", x,
|
18
|
+
"mismatch of callouts and annotations")
|
18
19
|
end
|
19
20
|
end
|
20
21
|
end
|
@@ -42,7 +43,9 @@ module Asciidoctor
|
|
42
43
|
root.xpath("//clause | //annex | //foreword | //introduction | "\
|
43
44
|
"//acknowledgements").each do |c|
|
44
45
|
next unless c.at("./clause")
|
45
|
-
next if c.elements.reject
|
46
|
+
next if c.elements.reject do |n|
|
47
|
+
%w(clause title).include? n.name
|
48
|
+
end.empty?
|
46
49
|
|
47
50
|
style_warning(c, "Hanging paragraph in clause")
|
48
51
|
end
|
data/metanorma-standoc.gemspec
CHANGED
@@ -28,7 +28,7 @@ Gem::Specification.new do |spec|
|
|
28
28
|
|
29
29
|
spec.add_dependency "asciidoctor", "~> 2.0.0"
|
30
30
|
spec.add_dependency "iev", "~> 0.2.1"
|
31
|
-
spec.add_dependency "isodoc", "~> 1.
|
31
|
+
spec.add_dependency "isodoc", "~> 1.8.0"
|
32
32
|
spec.add_dependency "metanorma-plugin-datastruct"
|
33
33
|
spec.add_dependency "metanorma-plugin-lutaml"
|
34
34
|
spec.add_dependency "ruby-jing"
|
@@ -959,14 +959,15 @@ QU1FOiB0ZXN0Cgo=
|
|
959
959
|
|
960
960
|
it "process mn2pdf attributes" do
|
961
961
|
node = Nokogiri::XML("<fake/>").at("fake")
|
962
|
-
node[
|
962
|
+
node[Asciidoctor::Standoc::Base::FONTS_MANIFEST] =
|
963
|
+
"passed/as/font/manifest/to/mn2pdf.jar"
|
963
964
|
|
964
965
|
options = Asciidoctor::Standoc::Converter
|
965
966
|
.new(:standoc, header_footer: true)
|
966
967
|
.doc_extract_attributes(node)
|
967
968
|
|
968
|
-
expect(options.dig(:mn2pdf, :
|
969
|
-
.to eq(node[
|
969
|
+
expect(options.dig(:mn2pdf, :font_manifest))
|
970
|
+
.to eq(node[Asciidoctor::Standoc::Base::FONTS_MANIFEST])
|
970
971
|
end
|
971
972
|
|
972
973
|
private
|