isodoc 3.5.0 → 3.5.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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: c07d19cb743ed84ffc6b1ae61b5b10ddb397cf1aa88781db27dbbd2c3aa63eee
4
- data.tar.gz: 6bd29f3cec7aea37250441b3b99f58b36b918641cd0dfc293a030b0ad3cf19c6
3
+ metadata.gz: ec71cedc759d905b416358b3accb10738478de4ca36ea037173bf615673e38ff
4
+ data.tar.gz: 6025a91f6810c7f7c901d2c91933000dce2ca94017e0b9978450f725f8e34649
5
5
  SHA512:
6
- metadata.gz: 72125bdfc8955528ed34b3c456018eecc21aa8cf987ba665b2c13797b02db992fdc9c221e759c623e0aeadf899cde559df337217aa1cb1981ec39b4e1e329d19
7
- data.tar.gz: 99236b9f69911c15144794681990944e61771cb238711f21b25d7045e469bb356af1a6098636f2941a1f68d1f64aacd8b31de2a958ca690361493cb1aea4f80f
6
+ metadata.gz: 807060d18211c7cff066d698336164501fefe85fc0ea649596419ed73ae8228211cee9df19eb90668a635fa06a52e32b7f5af8e20779ea90847cba71764b58fa
7
+ data.tar.gz: '0128d8924c4274f56b343026f42275f1ffd880ed844873fc7bd74f38b5d68fd1e6781a39a461bd65c19b913dd29a163b74ade0b2176f6f7df5b4da652ee8d3de'
data/isodoc.gemspec CHANGED
@@ -45,6 +45,8 @@ Gem::Specification.new do |spec|
45
45
  spec.add_dependency "uuidtools"
46
46
 
47
47
  spec.add_development_dependency "benchmark"
48
+ spec.add_development_dependency "bigdecimal"
49
+ spec.add_development_dependency "canon", "= 0.2.3"
48
50
  spec.add_development_dependency "debug"
49
51
  spec.add_development_dependency "equivalent-xml", "~> 0.6"
50
52
  spec.add_development_dependency "guard", "~> 2.14"
@@ -55,7 +57,5 @@ Gem::Specification.new do |spec|
55
57
  spec.add_development_dependency "sassc-embedded", "~> 1"
56
58
  spec.add_development_dependency "simplecov", "~> 0.15"
57
59
  spec.add_development_dependency "timecop", "~> 0.9"
58
- spec.add_development_dependency "canon" , "= 0.1.3"
59
- spec.add_development_dependency "openssl"
60
60
  # spec.metadata["rubygems_mfa_required"] = "true"
61
61
  end
@@ -115,10 +115,15 @@ module IsoDoc
115
115
  docxml_var_init(docxml)
116
116
  convert_i18n_init(docxml)
117
117
  metadata_init(@lang, @script, @locale, @i18n)
118
+ convert_xref_init
119
+ [docxml, filename, dir]
120
+ end
121
+
122
+ def convert_xref_init
118
123
  xref_init(@lang, @script, self, @i18n,
119
124
  { locale: @locale, bibrender: @bibrender })
125
+ @xrefs.reqt_models = @reqt_models
120
126
  @xrefs.klass.doctype = @doctype
121
- [docxml, filename, dir]
122
127
  end
123
128
 
124
129
  def convert_i18n_init(docxml)
@@ -126,7 +131,8 @@ module IsoDoc
126
131
  i18n_init(@lang, @script, @locale)
127
132
  @bibrender ||= bibrenderer
128
133
  @reqt_models = requirements_processor
129
- .new({ default: "default", lang: @lang, script: @script,
134
+ .new({ conv: presentation_xml_converter, default: "default",
135
+ lang: @lang, script: @script,
130
136
  locale: @locale, labels: @i18n.get,
131
137
  modspecidentifierbase: @modspecidentifierbase })
132
138
  end
@@ -136,6 +136,22 @@ module IsoDoc
136
136
  end
137
137
 
138
138
  def symbols_cleanup(docxml); end
139
+
140
+ # Atomic group (?>...) prevents catastrophic backtracking across `>`
141
+ # characters. Quoted alternatives listed first so `/` inside
142
+ # attribute values (e.g. URLs in href="...") is consumed as part
143
+ # of the quoted string, not rejected by [^>/].
144
+ def empty_tags(html)
145
+ void_elements = %w[area base br col embed hr img input link meta
146
+ source track wbr]
147
+ html.gsub(%r{<(\w+)((?>"[^"]*"|'[^']*'|[^>/])*)\s*/>}) do
148
+ if void_elements.include?($1)
149
+ $&
150
+ else
151
+ "<#{$1}#{$2}></#{$1}>"
152
+ end
153
+ end
154
+ end
139
155
  end
140
156
  end
141
157
  end
@@ -234,7 +234,7 @@ module IsoDoc
234
234
  CSV.parse_line(processed, quote_char: "'")
235
235
  .each_with_object({}) do |x, acc|
236
236
  x.gsub!(COMMA_PLACEHOLDER, ",")
237
- m = /^(.+?)=(.+)?$/.match(x) or next
237
+ m = /^(.+?)=(.*)?$/.match(x) or next
238
238
  acc[m[1].to_sym] = m[2].sub(/^(["'])(.+)\1$/, "\\2")
239
239
  end
240
240
  end
@@ -18,6 +18,14 @@ module IsoDoc
18
18
  super
19
19
  end
20
20
 
21
+ # Apply empty_tags even when postprocess is skipped (debug mode),
22
+ # so convert1's output is valid HTML5 (non-void self-closing tags
23
+ # expanded: <a id="_"/> -> <a id="_"></a>). Idempotent: running
24
+ # again in postprocess#toHTML is a no-op.
25
+ def convert1(docxml, filename, dir)
26
+ empty_tags(super)
27
+ end
28
+
21
29
  def convert(filename, file = nil, debug = false, output_filename = nil)
22
30
  ret = super
23
31
  Dir.exist?(tmpimagedir) and Dir["#{tmpimagedir}/*"].empty? and
@@ -16,7 +16,7 @@ module IsoDoc
16
16
  def toHTML(result, filename)
17
17
  result = from_xhtml(html_cleanup(to_xhtml(result)))
18
18
  result = from_xhtml(move_images(resize_images(to_xhtml(result))))
19
- result = html5(script_cdata(inject_script(result)))
19
+ result = html5(empty_tags(script_cdata(inject_script(result))))
20
20
  # Unescape &#x26; to & in href attributes after all Nokogiri processing
21
21
  result = unescape_amp_in_hrefs(result)
22
22
  File.open(filename, "w:UTF-8") { |f| f.write(result) }
data/lib/isodoc/init.rb CHANGED
@@ -10,8 +10,12 @@ module IsoDoc
10
10
  end
11
11
 
12
12
  def i18n_init(lang, script, locale, i18nyaml = nil)
13
- @i18n = I18n.new(lang, script, locale: locale,
14
- i18nyaml: i18nyaml || @i18nyaml)
13
+ payload = i18nyaml || @i18nyaml
14
+ @i18n = if payload.is_a?(Hash)
15
+ I18n.new(lang, script, locale: locale, i18nhash: payload)
16
+ else
17
+ I18n.new(lang, script, locale: locale, i18nyaml: payload)
18
+ end
15
19
  end
16
20
 
17
21
  def l10n(expr, lang = @lang, script = @script, opt = {})
@@ -19,6 +23,13 @@ module IsoDoc
19
23
  @i18n.l10n(expr, lang, script, opt)
20
24
  end
21
25
 
26
+ def presentation_xml_converter
27
+ parts = self.class.name.split("::")
28
+ parts[-1] = "PresentationXMLConvert"
29
+ Object.const_get(parts.join("::"))
30
+ .new(language: @lang, script: @script)
31
+ end
32
+
22
33
  def docxml_var_init(docxml)
23
34
  doctype_init(docxml)
24
35
  toc_init(docxml)
@@ -27,8 +38,8 @@ module IsoDoc
27
38
  def doctype_init(docxml)
28
39
  @doctype = docxml.at(ns("//bibdata/ext/doctype"))&.text
29
40
  @subdoctype = docxml.at(ns("//bibdata/ext/subdoctype"))&.text
30
- @docscheme = docxml.at(ns("//metanorma-extension/presentation-metadata/"\
31
- "document-scheme"))&.text
41
+ @docscheme = docxml.at(ns("//metanorma-extension/presentation-metadata/" \
42
+ "document-scheme"))&.text
32
43
  end
33
44
 
34
45
  def toc_init(docxml)
@@ -73,12 +84,12 @@ module IsoDoc
73
84
  def log_messages
74
85
  # rubocop:disable Naming/VariableNumber
75
86
  {
76
- "STANDOC_36": { category: "Anchors",
77
- error: "ID %s has already been used at line %s",
78
- severity: 0 },
79
- "ISODOC_1": { category: "Crossreferences",
80
- error: "Anchor %s pointed to by %s " \
81
- "is not defined in the document", severity: 1 },
87
+ STANDOC_36: { category: "Anchors",
88
+ error: "ID %s has already been used at line %s",
89
+ severity: 0 },
90
+ ISODOC_1: { category: "Crossreferences",
91
+ error: "Anchor %s pointed to by %s " \
92
+ "is not defined in the document", severity: 1 },
82
93
  }
83
94
  # rubocop:enable Naming/VariableNumber
84
95
  end
@@ -42,7 +42,7 @@ module IsoDoc
42
42
 
43
43
  def concept_dup_cleanup_orig(node)
44
44
  node.xpath(".//xmlns:semx[xmlns:fmt-xref | xmlns:fmt-eref | " \
45
- "xmlns:fmt-origin | xmlns:fmt-link]").each(&:remove)
45
+ "xmlns:fmt-origin | xmlns:fmt-link]").each(&:remove)
46
46
  node.xpath(ns(".//xref | .//eref | .//origin | .//link")).each do |x|
47
47
  x["original-id"] or next
48
48
  x["id"] = x["original-id"]
@@ -6,12 +6,12 @@ module IsoDoc
6
6
  def citeas(xmldoc)
7
7
  xmldoc.xpath(ns("//fmt-eref | //fmt-origin | //fmt-link"))
8
8
  .each do |e|
9
- sem_xml_descendant?(e) and next
10
- e["bibitemid"] && e["citeas"] or next
11
- a = @xrefs.anchor(e["bibitemid"], :xref, false) or next
12
- e["citeas"] = citeas_cleanup(a)
13
- # link generated in collection postprocessing from eref
14
- e.name == "fmt-link" && e.text.empty? and e.children = e["citeas"]
9
+ sem_xml_descendant?(e) and next
10
+ (e["bibitemid"] && e["citeas"]) or next
11
+ a = @xrefs.anchor(e["bibitemid"], :xref, false) or next
12
+ e["citeas"] = citeas_cleanup(a)
13
+ # link generated in collection postprocessing from eref
14
+ e.name == "fmt-link" && e.text.empty? and e.children = e["citeas"]
15
15
  end
16
16
  end
17
17
 
@@ -42,24 +42,35 @@ module IsoDoc
42
42
  end
43
43
 
44
44
  def resolve_eref_connectives(locs)
45
+ locs = resolve_eref_connectives1(locs)
46
+ locs.size < 3 and return locs.map do |x|
47
+ x[:custom] || x[:conn] || x[:ref]
48
+ end
49
+ locs = resolve_eref_connectives_split(locs)
50
+ locs = locs.each_slice(2).with_object([]) do |a, m|
51
+ m << { custom: a[0][:custom], conn: a[0][:conn], label: a.dig(1, :ref) }
52
+ end
53
+ [", ", combine_conn(locs)]
54
+ end
55
+
56
+ def resolve_eref_connectives1(locs)
45
57
  locs = escape_l10n(locs)
46
58
  locs = resolve_comma_connectives(locs)
47
- locs = resolve_to_connectives(locs)
48
- locs.size < 3 and return locs.map { |x| x[:custom] || x[:conn] || x[:ref] }
49
- locs = locs.each_with_object([]) do |x, m|
50
- if m.empty? then m << x
59
+ resolve_to_connectives(locs)
60
+ end
61
+
62
+ def resolve_eref_connectives_split(locs)
63
+ locs.each_with_object([]) do |x, m|
64
+ if m.empty?
65
+ m << x
51
66
  elsif m[-1][:conn] && x[:conn]
52
67
  m[-1][:conn] += x[:conn]
53
68
  x[:custom] and m[-1][:custom] = x[:custom]
54
- elsif m[-1][:conn] && x[:conn]
69
+ elsif m[-1][:conn] && x[:conn]
55
70
  m[-1][:ref] += x[:ref]
56
- else m << x
71
+ else m << x
57
72
  end
58
73
  end
59
- locs = locs.each_slice(2).with_object([]) do |a, m|
60
- m << { custom: a[0][:custom], conn: a[0][:conn], label: a.dig(1, :ref) }
61
- end
62
- [", ", combine_conn(locs)]
63
74
  end
64
75
 
65
76
  XREF_CONNECTIVES = %w(from to or and).freeze
@@ -82,7 +93,8 @@ module IsoDoc
82
93
 
83
94
  def resolve_comma_connectives1(locs, locs1, add)
84
95
  if [", ", " ", ""].include?(locs.dig(1, :conn)) && locs.size > 2
85
- add += [locs[0][:ref], locs[1][:custom] || locs[1][:conn], locs[2][:ref]].join
96
+ add += [locs[0][:ref], locs[1][:custom] || locs[1][:conn],
97
+ locs[2][:ref]].join
86
98
  locs.shift(3)
87
99
  else
88
100
  locs1 << add unless add.empty?
@@ -101,14 +113,12 @@ module IsoDoc
101
113
  c = locs[1][:custom] and x = conn_sub(x, c)
102
114
  locs1 << { ref: connectives_spans(x) }
103
115
  locs.shift(3)
116
+ elsif locs[0][:conn] == "from" && locs[0][:custom]
117
+ locs1 << { conn: locs[0][:custom] }
118
+ locs.shift # strip "from" and English
119
+ # TODO languages with obligatory "from"
104
120
  else
105
- if locs[0][:conn] == "from" && locs[0][:custom] # strip "from" and English
106
- # TODO languages with obligatory "from"
107
- locs1 << { conn: locs[0][:custom] }
108
- locs.shift
109
- else
110
- locs1 << locs.shift
111
- end
121
+ locs1 << locs.shift
112
122
  end
113
123
  end
114
124
  locs1
@@ -118,14 +128,15 @@ module IsoDoc
118
128
  docxml.xpath(ns("//display-text")).each { |f| f.replace(f.children) }
119
129
  docxml.xpath(ns("//fmt-eref | //fmt-origin[not(.//termref)]"))
120
130
  .each do |e|
121
- sem_xml_descendant?(e) and next
122
- href = eref_target(e) or next
123
- e.xpath(ns("./locality | ./localityStack")).each(&:remove)
124
- if %w(short).include?(e["style"]) then eref2linkshort(e, href)
125
- elsif href[:type] == :anchor || %w(full).include?(e["style"])
126
- eref2xref(e)
127
- else eref2link1(e, href)
128
- end
131
+ sem_xml_descendant?(e) and next
132
+ href = eref_target(e) or next
133
+ e.xpath(ns("./locality | ./localityStack")).each(&:remove)
134
+ if %w(short).include?(e["style"])
135
+ eref2linkshort(e, href)
136
+ elsif href[:type] == :anchor || %w(full).include?(e["style"])
137
+ eref2xref(e)
138
+ else eref2link1(e, href)
139
+ end
129
140
  end
130
141
  end
131
142
 
@@ -44,20 +44,24 @@ module IsoDoc
44
44
  def implicit_number_formatter(num, locale)
45
45
  num.ancestors("formula").empty? or return
46
46
  ## by default, no formatting in formulas
47
- fmt = { significant: num_totaldigits(num.text) }.compact
47
+ fmt = { significant: num_totaldigits(num.text, 10) }.compact
48
48
  n = normalise_number(num.text)
49
49
  @numfmt.localized_number(n, locale:, format: fmt,
50
50
  precision: num_precision(num.text))
51
51
  end
52
52
 
53
53
  def numberformat_type(ret)
54
- %i(precision significant digit_count group_digits fraction_group_digits)
54
+ %i(precision significant digit_count group_digits fraction_group_digits
55
+ base)
55
56
  .each do |i|
56
- ret[i] &&= ret[i].to_i
57
- end
58
- %i(notation exponent_sign number_sign locale).each do |i|
57
+ ret[i] &&= ret[i].to_i
58
+ end
59
+ %i(notation exponent_sign number_sign locale hex_capital).each do |i|
59
60
  ret[i] &&= ret[i].to_sym
60
61
  end
62
+ %i(base_prefix base_suffix).each do |i|
63
+ ["", "nil"].include?(ret[i]) and ret[i] = nil
64
+ end
61
65
  ret
62
66
  end
63
67
 
@@ -76,14 +80,17 @@ module IsoDoc
76
80
  v.is_a?(String) ? HTMLEntities.new.decode(v) : v
77
81
  end.merge(fmt)
78
82
  symbols = large_notation_fmt(symbols, num.text)
79
- [symbols[:precision] || num_precision(num.text), symbols,
80
- explicit_number_formatter_signif(num, symbols)]
83
+ significant = explicit_number_formatter_signif(num, symbols)
84
+ precision = symbols[:precision] || num_precision(num.text) ||
85
+ num_precision_from_significant(num.text, significant,
86
+ (symbols[:base] || 10).to_i)
87
+ [precision, symbols, significant]
81
88
  end
82
89
 
83
90
  def explicit_number_formatter_signif(num, symbols)
84
91
  signif = symbols[:significant]
85
92
  (symbols.keys & %i(precision digit_count)).empty? and
86
- signif ||= num_totaldigits(num.text)
93
+ signif ||= num_totaldigits(num.text, (symbols[:base] || 10).to_i)
87
94
  signif
88
95
  end
89
96
 
@@ -117,16 +124,56 @@ module IsoDoc
117
124
  precision
118
125
  end
119
126
 
120
- def num_totaldigits(num)
127
+ def num_totaldigits(num, base = 10)
121
128
  totaldigits = nil
122
129
  /\.(?=\d+e)/.match?(num) and
123
130
  totaldigits = twitter_cldr_localiser_symbols[:significant] ||
124
- # [^.]* and [^e]* exclude their respective delimiters,
125
- # preventing polynomial backtracking.
126
- num.sub(/\A0\./, ".").sub(/\A[^.]*\./, "").sub(/e[^e]*\z/, "").size
131
+ num_totaldigits_compute(num, base)
127
132
  totaldigits
128
133
  end
129
134
 
135
+ # In base 10, total significant digits = source mantissa length.
136
+ # In other bases, the converted value may have fewer digits. Per
137
+ # https://github.com/metanorma/isodoc/issues/788: if the source has
138
+ # no fractional part after E-notation expansion, return the
139
+ # length of the integer in the target base (e.g. 123 -> 7B = 2
140
+ # digits, not 3); if the source has a fractional part, preserve
141
+ # the source mantissa length so Plurimath pads the converted
142
+ # fraction (e.g. 123.25 -> 7B.400, 123.0 -> 7B.00).
143
+ def num_totaldigits_compute(num, base)
144
+ # [^.]* and [^e]* exclude their respective delimiters,
145
+ # preventing polynomial backtracking.
146
+ mantissa = num.sub(/\A0\./, ".").sub(/\A[^.]*\./, "")
147
+ .sub(/e[^e]*\z/, "")
148
+ return mantissa.size if base == 10
149
+
150
+ m = num.match(/\A-?0?\.(\d+)e(-?\d+)\z/)
151
+ if m && m[1].length <= m[2].to_i
152
+ BigDecimal(num).to_i.abs.to_s(base).length
153
+ else
154
+ mantissa.size
155
+ end
156
+ end
157
+
158
+ # When base != 10 and the source is in E-notation, derive the
159
+ # target-base fractional digit count from the total significant
160
+ # digit count we computed. Plurimath's default precision_from()
161
+ # returns the decimal fractional digit count, which
162
+ # Numbers::Fraction#change_base then uses as the target-base
163
+ # fractional digit count -- producing too few fractional digits
164
+ # in non-decimal bases. Workaround pending upstream fix; see
165
+ # https://github.com/metanorma/isodoc/issues/788.
166
+ def num_precision_from_significant(num, significant, base)
167
+ base == 10 and return nil
168
+ significant.nil? and return nil
169
+ /\.(?=\d+e)/.match?(num) or return nil
170
+ m = num.match(/\A-?0?\.(\d+)e(-?\d+)\z/) or return nil
171
+ m[1].length <= m[2].to_i and return 0
172
+ val = BigDecimal(num).abs
173
+ integer_len = val.to_i.zero? ? 0 : val.to_i.to_s(base).length
174
+ [significant - integer_len, 0].max
175
+ end
176
+
130
177
  def twitter_cldr_localiser_symbols
131
178
  {}
132
179
  end
@@ -1,3 +1,3 @@
1
1
  module IsoDoc
2
- VERSION = "3.5.0".freeze
2
+ VERSION = "3.5.1".freeze
3
3
  end
@@ -13,7 +13,17 @@ module IsoDoc
13
13
  html.add_namespace("m", "http://schemas.microsoft.com/office/2004/12/omml")
14
14
  end
15
15
 
16
+ # Apply empty_tags even when postprocess is skipped (debug mode),
17
+ # so convert1's output is valid HTML5 (non-void self-closing tags
18
+ # expanded: <a id="_"/> -> <a id="_"></a>). Idempotent: running
19
+ # again in postprocess#toHTML is a no-op.
20
+ def convert1(docxml, filename, dir)
21
+ empty_tags(super)
22
+ end
23
+
16
24
  def define_head(head, filename, _dir)
25
+ head.meta "http-equiv": "Content-Type",
26
+ content: "text/html; charset=UTF-8"
17
27
  head.style do |style|
18
28
  loc = File.join(File.dirname(__FILE__), "..", "base_style",
19
29
  "metanorma_word.scss")
@@ -20,7 +20,7 @@ module IsoDoc
20
20
  result = from_xhtml(word_cleanup(result))
21
21
  .gsub("-DOUBLE_HYPHEN_ESCAPE-", "--")
22
22
  # Unescape &#x26; to & in href attributes after all Nokogiri processing
23
- unescape_amp_in_hrefs(result)
23
+ unescape_amp_in_hrefs(empty_tags(result))
24
24
  end
25
25
 
26
26
  def toWord(result, filename, dir, header)
@@ -41,7 +41,7 @@ module IsoDoc
41
41
  xmlns:v="urn:schemas-microsoft-com:vml" xmlns:o="urn:schemas-microsoft-com:office:office"
42
42
  xmlns:w="urn:schemas-microsoft-com:office:word"
43
43
  xmlns:m="http://schemas.microsoft.com/office/2004/12/omml">
44
- <head> <title></title> <meta charset="UTF-8" /> </head>
44
+ <head> <title></title> <meta charset="UTF-8"/> </head>
45
45
  <body> </body> </html>
46
46
  HERE
47
47
 
data/lib/isodoc/xref.rb CHANGED
@@ -17,6 +17,7 @@ module IsoDoc
17
17
  include Function::Utils
18
18
 
19
19
  attr_reader :klass
20
+ attr_accessor :reqt_models
20
21
 
21
22
  # Note: if bibrender is no passed in, do not parse references
22
23
  def initialize(lang, script, klass, i18n, options = {})
@@ -27,9 +28,6 @@ module IsoDoc
27
28
  @options = options
28
29
  initialize_i18n(i18n)
29
30
  @klass.bibrender ||= options[:bibrender]
30
- @reqt_models = @klass.requirements_processor
31
- .new({ default: "default", lang:, script:,
32
- labels: @i18n.get })
33
31
  end
34
32
 
35
33
  def initialize_empty
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: isodoc
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.5.0
4
+ version: 3.5.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Ribose Inc.
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2026-04-13 00:00:00.000000000 Z
11
+ date: 2026-04-27 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: base64
@@ -192,6 +192,34 @@ dependencies:
192
192
  - - ">="
193
193
  - !ruby/object:Gem::Version
194
194
  version: '0'
195
+ - !ruby/object:Gem::Dependency
196
+ name: bigdecimal
197
+ requirement: !ruby/object:Gem::Requirement
198
+ requirements:
199
+ - - ">="
200
+ - !ruby/object:Gem::Version
201
+ version: '0'
202
+ type: :development
203
+ prerelease: false
204
+ version_requirements: !ruby/object:Gem::Requirement
205
+ requirements:
206
+ - - ">="
207
+ - !ruby/object:Gem::Version
208
+ version: '0'
209
+ - !ruby/object:Gem::Dependency
210
+ name: canon
211
+ requirement: !ruby/object:Gem::Requirement
212
+ requirements:
213
+ - - '='
214
+ - !ruby/object:Gem::Version
215
+ version: 0.2.3
216
+ type: :development
217
+ prerelease: false
218
+ version_requirements: !ruby/object:Gem::Requirement
219
+ requirements:
220
+ - - '='
221
+ - !ruby/object:Gem::Version
222
+ version: 0.2.3
195
223
  - !ruby/object:Gem::Dependency
196
224
  name: debug
197
225
  requirement: !ruby/object:Gem::Requirement
@@ -332,34 +360,6 @@ dependencies:
332
360
  - - "~>"
333
361
  - !ruby/object:Gem::Version
334
362
  version: '0.9'
335
- - !ruby/object:Gem::Dependency
336
- name: canon
337
- requirement: !ruby/object:Gem::Requirement
338
- requirements:
339
- - - '='
340
- - !ruby/object:Gem::Version
341
- version: 0.1.3
342
- type: :development
343
- prerelease: false
344
- version_requirements: !ruby/object:Gem::Requirement
345
- requirements:
346
- - - '='
347
- - !ruby/object:Gem::Version
348
- version: 0.1.3
349
- - !ruby/object:Gem::Dependency
350
- name: openssl
351
- requirement: !ruby/object:Gem::Requirement
352
- requirements:
353
- - - ">="
354
- - !ruby/object:Gem::Version
355
- version: '0'
356
- type: :development
357
- prerelease: false
358
- version_requirements: !ruby/object:Gem::Requirement
359
- requirements:
360
- - - ">="
361
- - !ruby/object:Gem::Version
362
- version: '0'
363
363
  description: |
364
364
  isodoc converts documents in the IsoDoc document model into
365
365
  Microsoft Word and HTML.