kramdown-rfc2629 1.3.5 → 1.3.10

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: '01978871f76d690940f07e334a95f5c062159cefe031b4bb8a716d03ca6d775d'
4
- data.tar.gz: 59bd6e3fcb40cf3dbb0e0bb8bf82cd6f85c16468d63e87bf4070876c5e3bf62b
3
+ metadata.gz: 55399c42e77abc9fd6e071e0e56de872ea053b4d7aa4a4b3d1218570deb3593a
4
+ data.tar.gz: 0e8358cfaf63d47fe0f5b79de0ebc59809b1163d8cb0c33fd4bbb83116505510
5
5
  SHA512:
6
- metadata.gz: 1ecb98246f285e547d43c7db6ba7c226236f63fb4cec6b560baf11e6c64b48cf2b388a5ca34a89e7f0389b5237eacdf791ec72706a61bb715e8ef30332493d49
7
- data.tar.gz: 27291914e97a7001ff067c52c50b415bea02b2888ecea3288ffdf4907ca1eff0136acb3858d47a971031e391ae0be97ae935dd5b462cf8fdd955503127aa65f2
6
+ metadata.gz: 7c1ddd9f5c0ca683bd889815050f5979a662561cb599b801b557e9a1df457f6bc97a6118cb826120bcee5a39b6fbe3701c8f922501ae0ec58e64cdd6ca25e3a7
7
+ data.tar.gz: 1cc42537f1bf204f5257cfe7f71edcde433e5639cbfea83fe55730f61d00c8e8114d7806a9113582a6c68ace85d14a07ec9ccf582de1e8ea9500fb4e64f51414
data/README.md CHANGED
@@ -281,6 +281,31 @@ special support in XML2RFC), and HTML syntax of course.
281
281
  A number of more esoteric features have recently been added.
282
282
  (The minimum required version for each full feature is indicated.)
283
283
 
284
+ (1.3.x)
285
+ Slowly improving support for SVG generating tools for XML2RFCv3 (i.e.,
286
+ with `-3` flag).
287
+ These tools must be installed and callable from the command line.
288
+
289
+ The basic idea is to mark an input code block with one of the following
290
+ labels (language types), yielding some plaintext form in the .TXT
291
+ output and a graphical form in the .HTML output. The plaintext is the
292
+ input in some cases (e.g., ASCII art, `mscgen`), or some plaintext
293
+ output generated by the tool (e.g., `plantuml-utxt`).
294
+
295
+ Currently supported labels as of 1.3.9:
296
+
297
+ * goat, ditaa: ASCII (plaintext) art to figure conversion
298
+ * mscgen: Message Sequence Charts
299
+ * plantuml: widely used multi-purpose diagram generator
300
+ * plantuml-utxt: Like plantuml, except that a plantuml-generated
301
+ plaintext form is used
302
+ * mermaid: Very experimental; the conversion to SVG is prone to
303
+ generate black-on-black text in this version
304
+
305
+ Note that this feature does not play well with the CI (continuous
306
+ integration) support in Martin Thomson's [I-D Template][], as that may
307
+ not have the tools installed in its docker instance.
308
+
284
309
  (1.2.9:)
285
310
  The YAML header now allows specifying [kramdown_options][].
286
311
 
data/bin/doilit CHANGED
@@ -39,7 +39,7 @@ ARGV.each do |doi|
39
39
  warn "*** Usage: doilit [-c] [-v] [-h=handle|-x=xmlhandle] doi..."
40
40
  exit 1
41
41
  end
42
- cite = JSON.parse(open("https://dx.doi.org/#{doi}", ACCEPT_CITE_JSON).read)
42
+ cite = JSON.parse(URI("https://dx.doi.org/#{doi}").open(ACCEPT_CITE_JSON).read)
43
43
  puts cite.to_yaml if $verbose
44
44
  lit = {}
45
45
  ser = lit["seriesinfo"] = {}
data/bin/kdrfc CHANGED
@@ -3,6 +3,9 @@ require 'uri'
3
3
  require 'net/http'
4
4
  require 'open3'
5
5
 
6
+ # try to get this from gemspec.
7
+ KDRFC_VERSION=Gem.loaded_specs["kramdown-rfc2629"].version rescue "unknown-version"
8
+
6
9
  def v3_flag?
7
10
  $options.v3 ? ["--v3"] : []
8
11
  end
@@ -46,16 +49,21 @@ def process_xml_locally(input, output, *flags)
46
49
  end
47
50
  end
48
51
 
52
+ XML2RFC_WEBSERVICE = ENV["KRAMDOWN_XML2RFC_WEBSERVICE"] ||
53
+ 'http://xml2rfc.tools.ietf.org/cgi-bin/xml2rfc-dev.cgi'
54
+
55
+
49
56
  def process_xml_remotely(input, output)
50
57
  warn "* converting remotely from xml #{input} to txt #{output}" if $options.verbose
51
- url = URI('http://xml2rfc.tools.ietf.org/cgi-bin/xml2rfc.cgi')
58
+ url = URI(XML2RFC_WEBSERVICE)
52
59
  req = Net::HTTP::Post.new(url)
53
- req.set_form([["modeAsFormat", "txt/#{"v3" if $options.v3}ascii"],
54
- ["type", "binary"],
55
- ["input", File.open(input),
56
- {filename: "input.xml",
57
- content_type: "text/plain"}]],
58
- 'multipart/form-data')
60
+ form = [["modeAsFormat", "txt/#{"v3" if $options.v3}ascii"],
61
+ ["type", "binary"],
62
+ ["input", File.open(input),
63
+ {filename: "input.xml",
64
+ content_type: "text/plain"}]]
65
+ diag = ["url/form: ", url, form].inspect
66
+ req.set_form(form, 'multipart/form-data')
59
67
  res = Net::HTTP::start(url.hostname, url.port,
60
68
  :use_ssl => url.scheme == 'https' ) {|http|
61
69
  http.request(req)
@@ -69,12 +77,12 @@ def process_xml_remotely(input, output)
69
77
  end
70
78
  warn "* #{output} written" if $options.verbose
71
79
  else
72
- warn "*** HTTP response has unexpected content_type #{res.content_type} with status #{res.code}"
80
+ warn "*** HTTP response has unexpected content_type #{res.content_type} with status #{res.code}, #{diag}"
73
81
  warn res.body
74
82
  exit 1
75
83
  end
76
84
  else
77
- warn "*** HTTP response: #{res.code}"
85
+ warn "*** HTTP response: #{res.code}, #{diag}"
78
86
  exit 1
79
87
  end
80
88
  end
@@ -85,8 +93,18 @@ require 'ostruct'
85
93
  $options = OpenStruct.new
86
94
  $options.txt = true # default
87
95
  op = OptionParser.new do |opts|
88
- opts.banner = "Usage: kdrfc [options] file.md|file.mkd|file.xml"
89
-
96
+ opts.banner = <<BANNER
97
+ Usage: kdrfc [options] file.md|file.mkd|file.xml
98
+ Version: #{KDRFC_VERSION}
99
+ BANNER
100
+ opts.on("-V", "--version", "Show version and exit") do |v|
101
+ puts "kdrfc, from kramdown-rfc2629 #{KDRFC_VERSION}"
102
+ exit
103
+ end
104
+ opts.on("-H", "--help", "Show option summary and exit") do |v|
105
+ puts opts
106
+ exit
107
+ end
90
108
  opts.on("-v", "--[no-]verbose", "Run verbosely") do |v|
91
109
  $options.verbose = v
92
110
  end
@@ -1,4 +1,4 @@
1
- #!/usr/bin/env ruby2.1
1
+ #!/usr/bin/env ruby
2
2
  # -*- coding: utf-8 -*-
3
3
  require 'kramdown-rfc2629'
4
4
  require 'kramdown-rfc/parameterset'
@@ -7,6 +7,9 @@ require 'yaml'
7
7
  require 'erb'
8
8
  require 'date'
9
9
 
10
+ # try to get this from gemspec.
11
+ KDRFC_VERSION=Gem.loaded_specs["kramdown-rfc2629"].version rescue "unknown-version"
12
+
10
13
  Encoding.default_external = "UTF-8" # wake up, smell the coffee
11
14
 
12
15
  def boilerplate(key)
@@ -287,8 +290,18 @@ require 'ostruct'
287
290
 
288
291
  $options = OpenStruct.new
289
292
  op = OptionParser.new do |opts|
290
- opts.banner = "Usage: kramdown-rfc2629 [options] file.md|file.mkd > file.xml"
291
-
293
+ opts.banner = <<BANNER
294
+ Usage: kramdown-rfc2629 [options] file.md|file.mkd > file.xml
295
+ Version: #{KDRFC_VERSION}
296
+ BANNER
297
+ opts.on("-V", "--version", "Show version and exit") do |v|
298
+ puts "kramdown-rfc2629 #{KDRFC_VERSION}"
299
+ exit
300
+ end
301
+ opts.on("-H", "--help", "Show option summary and exit") do |v|
302
+ puts opts
303
+ exit
304
+ end
292
305
  opts.on("-v", "--[no-]verbose", "Run verbosely") do |v|
293
306
  $options.verbose = v
294
307
  end
@@ -1,6 +1,6 @@
1
1
  spec = Gem::Specification.new do |s|
2
2
  s.name = 'kramdown-rfc2629'
3
- s.version = '1.3.5'
3
+ s.version = '1.3.10'
4
4
  s.summary = "Kramdown extension for generating RFC 7749 XML."
5
5
  s.description = %{An RFC7749 (XML2RFC) generating backend for Thomas Leitner's
6
6
  "kramdown" markdown parser. Mostly useful for RFC writers.}
@@ -9,7 +9,6 @@ spec = Gem::Specification.new do |s|
9
9
  s.files = Dir['lib/**/*.rb'] + %w(README.md LICENSE kramdown-rfc2629.gemspec bin/kdrfc bin/kramdown-rfc2629 bin/doilit bin/kramdown-rfc-extract-markdown data/kramdown-rfc2629.erb data/encoding-fallbacks.txt)
10
10
  s.require_path = 'lib'
11
11
  s.executables = ['kramdown-rfc2629', 'doilit', 'kramdown-rfc-extract-markdown', 'kdrfc']
12
- s.default_executable = 'kramdown-rfc2629'
13
12
  s.required_ruby_version = '>= 2.3.0'
14
13
  # s.requirements = 'wget'
15
14
  # s.has_rdoc = true
@@ -150,6 +150,110 @@ module Kramdown
150
150
  generate_id(value).gsub(/-+/, '-')
151
151
  end
152
152
 
153
+ SVG_COLORS = Hash.new {|h, k| k}
154
+ <<COLORS.each_line {|l| k, v = l.chomp.split; SVG_COLORS[k] = v}
155
+ black #000000
156
+ silver #C0C0C0
157
+ gray #808080
158
+ white #FFFFFF
159
+ maroon #800000
160
+ red #FF0000
161
+ purple #800080
162
+ fuchsia #FF00FF
163
+ green #008000
164
+ lime #00FF00
165
+ olive #808000
166
+ yellow #FFFF00
167
+ navy #000080
168
+ blue #0000FF
169
+ teal #008080
170
+ aqua #00FFFF
171
+ COLORS
172
+
173
+ def svg_munch_id(id)
174
+ id.gsub(/[^-._A-Za-z0-9]/) {|x| "_%02X" % x.ord}
175
+ end
176
+
177
+ def self.hex_to_lin(h)
178
+ h.to_i(16)**2.22 # approximating sRGB gamma
179
+ end
180
+ define_method :hex_to_lin, &method(:hex_to_lin)
181
+
182
+ B_W_THRESHOLD = hex_to_lin("a4") # a little brighter than 1/2 0xFF -> white
183
+
184
+ def svg_munch_color(c, fill)
185
+ c = SVG_COLORS[c]
186
+ case c
187
+ when /\A#(..)(..)(..)\z/
188
+ if hex_to_lin($1)*0.2126 + hex_to_lin($2)*0.7152 + hex_to_lin($3)*0.0722 >= B_W_THRESHOLD
189
+ 'white'
190
+ else
191
+ 'black'
192
+ end
193
+ when 'none'
194
+ 'none' if fill # delete for stroke
195
+ else
196
+ c
197
+ end
198
+ end
199
+
200
+ def svg_clean(s) # expensive, risky
201
+ require "rexml/document"
202
+ d = REXML::Document.new(s)
203
+ REXML::XPath.each(d.root, "//*[@shape-rendering]") { |x| x.attributes["shape-rendering"] = nil } #; warn x.inspect }
204
+ REXML::XPath.each(d.root, "//*[@text-rendering]") { |x| x.attributes["text-rendering"] = nil } #; warn x.inspect }
205
+ REXML::XPath.each(d.root, "//*[@stroke]") { |x| x.attributes["stroke"] = svg_munch_color(x.attributes["stroke"], false) }
206
+ REXML::XPath.each(d.root, "//*[@fill]") { |x| x.attributes["fill"] = svg_munch_color(x.attributes["fill"], true) }
207
+ REXML::XPath.each(d.root, "//*[@id]") { |x| x.attributes["id"] = svg_munch_id(x.attributes["id"]) }
208
+ ## REXML::XPath.each(d.root, "//rect") { |x| x.attributes["style"] = "fill:none;stroke:black;stroke-width:1" unless x.attributes["style"] }
209
+ d.to_s
210
+ end
211
+
212
+ def memoize(meth, *args)
213
+ require 'digest'
214
+ Dir.mkdir(REFCACHEDIR) unless Dir.exists?(REFCACHEDIR)
215
+ kdrfc_version = Gem.loaded_specs["kramdown-rfc2629"].version.to_s.gsub('.', '_') rescue "UNKNOWN"
216
+ fn = "#{REFCACHEDIR}/kdrfc-#{kdrfc_version}-#{meth}-#{Digest::SHA256.hexdigest(Marshal.dump(args))[0...40]}.cache"
217
+ begin
218
+ out = Marshal.load(File.binread(fn))
219
+ rescue StandardError => e
220
+ # warn e.inspect
221
+ out = method(meth).call(*args)
222
+ File.binwrite(fn, Marshal.dump(out))
223
+ end
224
+ out
225
+ end
226
+
227
+ def svg_tool_process(t, result)
228
+ require 'tempfile'
229
+ file = Tempfile.new("kramdown-rfc")
230
+ file.write(result)
231
+ file.close
232
+ case t
233
+ when "goat"
234
+ result1, _s = Open3.capture2("goat #{file.path}", stdin_data: result);
235
+ when "ditaa" # XXX: This needs some form of option-setting
236
+ result1, _s = Open3.capture2("ditaa #{file.path} --svg -o -", stdin_data: result);
237
+ when "mscgen"
238
+ result1, _s = Open3.capture2("mscgen -T svg -i #{file.path} -o -", stdin_data: result);
239
+ when "mermaid"
240
+ result1, _s = Open3.capture2("mmdc -i #{file.path}", stdin_data: result); # -b transparent
241
+ outpath = file.path + ".svg"
242
+ result1 = File.read(outpath)
243
+ File.unlink(outpath)
244
+ when "plantuml", "plantuml-utxt"
245
+ plantuml = "@startuml\n#{result}\n@enduml"
246
+ result1, _s = Open3.capture2("plantuml -pipe -tsvg", stdin_data: plantuml);
247
+ result, _s = Open3.capture2("plantuml -pipe -tutxt", stdin_data: plantuml) if t == "plantuml-utxt"
248
+ end
249
+ # warn ["goat:", result1.inspect]
250
+ file.unlink
251
+ result1 = svg_clean(result1) unless t == "goat"
252
+ result1, _s = Open3.capture2("svgcheck -qa", stdin_data: result1);
253
+ # warn ["svgcheck:", result1.inspect]
254
+ [result, result1]
255
+ end
256
+
153
257
  def convert_codeblock(el, indent, opts)
154
258
  # el.attr['anchor'] ||= saner_generate_id(el.value) -- no longer in 1.0.6
155
259
  result = el.value
@@ -194,16 +298,8 @@ module Kramdown
194
298
  end
195
299
  end
196
300
  case t
197
- when "goat"
198
- require 'tempfile'
199
- file = Tempfile.new("kramdown-rfc")
200
- file.write(result)
201
- file.close
202
- result1, _s = Open3.capture2("goat #{file.path}", stdin_data: result);
203
- # warn ["goat:", result1.inspect]
204
- file.unlink
205
- result1, _s = Open3.capture2("svgcheck -qa", stdin_data: result1);
206
- # warn ["svgcheck:", result1.inspect]
301
+ when "goat", "ditaa", "mscgen", "plantuml", "plantuml-utxt", "mermaid"
302
+ result, result1 = memoize(:svg_tool_process, t, result)
207
303
  "#{' '*indent}<figure#{el_html_attributes(el)}><artset><artwork #{html_attributes(artwork_attr.merge("type"=> "svg"))}>#{result1.sub(/.*?<svg/m, "<svg")}</artwork><artwork #{html_attributes(artwork_attr.merge("type"=> "ascii-art"))}><![CDATA[#{result}#{result =~ /\n\Z/ ? '' : "\n"}]]></artwork></artset></figure>\n"
208
304
  else
209
305
  "#{' '*indent}<figure#{el_html_attributes(el)}><artwork#{html_attributes(artwork_attr)}><![CDATA[#{result}#{result =~ /\n\Z/ ? '' : "\n"}]]></artwork></figure>\n"
@@ -486,7 +582,7 @@ module Kramdown
486
582
  begin
487
583
  File.read(fn) # this blows up if no cache available after fetch attempt
488
584
  rescue Errno::ENOENT => e
489
- warn "*** #{e} for ${fn}"
585
+ warn "*** #{e} for #{fn}"
490
586
  end
491
587
  end
492
588
 
@@ -538,7 +634,7 @@ module Kramdown
538
634
  fn = "reference.#{t}.#{n}.xml"
539
635
  sub, ttl, can_anchor = XML_RESOURCE_ORG_MAP[t]
540
636
  ttl ||= KRAMDOWN_REFCACHETTL # everything but RFCs might change a lot
541
- puts "Huh: ${fn}" unless sub
637
+ puts "*** Huh: #{fn}" unless sub
542
638
  url = "#{XML_RESOURCE_ORG_PREFIX}/#{sub}/#{fn}"
543
639
  if can_anchor # create anchor server-side for stand_alone: false
544
640
  url << "?anchor=#{anchor}"
@@ -548,7 +644,10 @@ module Kramdown
548
644
  to_insert.scrub! rescue nil # only do this for Ruby >= 2.1
549
645
  # this may be a bit controversial: Don't break the build if reference is broken
550
646
  if KRAMDOWN_OFFLINE
551
- to_insert ||= "<reference anchor='#{anchor}'> <front> <title>*** BROKEN REFERENCE ***</title> <author> <organization/> </author> <date/> </front> </reference>"
647
+ unless to_insert
648
+ to_insert = "<reference anchor='#{anchor}'> <front> <title>*** BROKEN REFERENCE ***</title> <author> <organization/> </author> <date/> </front> </reference>"
649
+ warn "*** KRAMDOWN_OFFLINE: Inserting broken reference for #{fn}"
650
+ end
552
651
  else
553
652
  exit 66 unless to_insert # EX_NOINPUT
554
653
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: kramdown-rfc2629
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.3.5
4
+ version: 1.3.10
5
5
  platform: ruby
6
6
  authors:
7
7
  - Carsten Bormann
8
- autorequire:
8
+ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-04-19 00:00:00.000000000 Z
11
+ date: 2020-07-25 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: kramdown
@@ -67,7 +67,7 @@ homepage: http://github.com/cabo/kramdown-rfc2629
67
67
  licenses:
68
68
  - MIT
69
69
  metadata: {}
70
- post_install_message:
70
+ post_install_message:
71
71
  rdoc_options: []
72
72
  require_paths:
73
73
  - lib
@@ -83,7 +83,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
83
83
  version: '0'
84
84
  requirements: []
85
85
  rubygems_version: 3.1.2
86
- signing_key:
86
+ signing_key:
87
87
  specification_version: 4
88
88
  summary: Kramdown extension for generating RFC 7749 XML.
89
89
  test_files: []