kramdown-rfc2629 1.3.31 → 1.3.36
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/bin/kramdown-rfc-cache-i-d-bibxml +102 -0
- data/kramdown-rfc2629.gemspec +3 -2
- data/lib/kramdown-rfc2629.rb +94 -21
- metadata +4 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 1a7a8c78c412d9bf4830f3335bba088f220a983e391057bdf90cad5d716d2d2f
|
4
|
+
data.tar.gz: 8fbac5333fb0e14e732aac23ba11b9a110fe8ca9948e6aa89ce953e88c95a193
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 889c151d93059ebd22e6adb9b7bc295206056c70ae69adab2c300b736c9b3037d7a7ec1af865ff7aeba29af5a4d3ab82525aebbd1bcddb8fb9f8ad2b9ba5c0af
|
7
|
+
data.tar.gz: 9e067408ad82182fb0ae4f0461b0e47db3888d3839b6a1e2915333fd1acffa34c783b8a7185ebe8afdb56a64a89854638de1c1d6a2c781aa95c4c093e58793fb
|
@@ -0,0 +1,102 @@
|
|
1
|
+
#!/usr/bin/env ruby
|
2
|
+
# prerequisite:
|
3
|
+
# gem install net-http-persistent
|
4
|
+
#
|
5
|
+
# dumps all bibxml for current, "Active" I-Ds in cache
|
6
|
+
# reasonably efficient after initial call if the output is retained
|
7
|
+
#
|
8
|
+
# requires Ruby 2.4 or above because of "liberal_parsing" option
|
9
|
+
#
|
10
|
+
# uses ENV["KRAMDOWN_REFCACHEDIR"] for where you want to have your bibxml3 data
|
11
|
+
#
|
12
|
+
|
13
|
+
require 'csv'
|
14
|
+
require 'fileutils'
|
15
|
+
|
16
|
+
begin
|
17
|
+
require 'net/http/persistent'
|
18
|
+
rescue
|
19
|
+
warn "*** please install net-http-persistent:"
|
20
|
+
warn " gem install net-http-persistent"
|
21
|
+
warn "(prefix by sudo only if required)."
|
22
|
+
exit 72 # EX_OSFILE
|
23
|
+
end
|
24
|
+
|
25
|
+
|
26
|
+
TARGET_DIR = ENV["KRAMDOWN_REFCACHEDIR"] || (
|
27
|
+
path = File.expand_path("~/.cache/xml2rfc")
|
28
|
+
warn "*** set environment variable KRAMDOWN_REFCACHEDIR to #{path} to actually use the cache"
|
29
|
+
path
|
30
|
+
)
|
31
|
+
|
32
|
+
FileUtils.mkdir_p(TARGET_DIR)
|
33
|
+
FileUtils.chdir(TARGET_DIR)
|
34
|
+
|
35
|
+
$http = Net::HTTP::Persistent.new name: 'allid'
|
36
|
+
|
37
|
+
KRAMDOWN_PERSISTENT_VERBOSE = true
|
38
|
+
|
39
|
+
def get_and_write_resource_persistently(url, fn, age_verbose=false)
|
40
|
+
t1 = Time.now
|
41
|
+
response = $http.request(URI(url))
|
42
|
+
if response.code != "200"
|
43
|
+
raise "*** Status code #{response.code} while fetching #{url}"
|
44
|
+
else
|
45
|
+
File.write(fn, response.body)
|
46
|
+
end
|
47
|
+
t2 = Time.now
|
48
|
+
warn "#{url} -> #{fn} (#{"%.3f" % (t2 - t1)} s)" if KRAMDOWN_PERSISTENT_VERBOSE
|
49
|
+
if age_verbose
|
50
|
+
if age = response.get_fields("age")
|
51
|
+
warn "(working from a web cache, index is #{age.first} seconds stale)"
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
|
56
|
+
CLEAR_RET = "\e[K\r" # XXX all the world is ECMA-48 (ISO 6429), no?
|
57
|
+
|
58
|
+
def noisy(name)
|
59
|
+
print "#{name}...#{CLEAR_RET}"
|
60
|
+
end
|
61
|
+
def clear_noise
|
62
|
+
print CLEAR_RET
|
63
|
+
end
|
64
|
+
|
65
|
+
ALL_ID2_SOURCE = "https://www.ietf.org/id/all_id2.txt"
|
66
|
+
ALL_ID2_COPY = ".all_id2.txt"
|
67
|
+
|
68
|
+
get_and_write_resource_persistently(ALL_ID2_SOURCE, ALL_ID2_COPY, true) unless ENV["KRAMDOWN_DONT_REFRESH_ALL_ID2"]
|
69
|
+
ix = File.read(ALL_ID2_COPY).lines.grep_v(/^#/).join
|
70
|
+
|
71
|
+
csv = CSV.new(ix, col_sep: "\t", liberal_parsing: true)
|
72
|
+
|
73
|
+
drafts = csv.read
|
74
|
+
active = drafts.select { |d| d[2] == "Active" }
|
75
|
+
active_names = active.map { |a| a[0] }
|
76
|
+
puts "#{active_names.size} active drafts"
|
77
|
+
|
78
|
+
active_names.each do |name|
|
79
|
+
if name =~ /\Adraft-(.*)-(\d\d)\z/
|
80
|
+
namepart = $1
|
81
|
+
version = $2
|
82
|
+
name0 = "reference.I-D.#{namepart}.xml"
|
83
|
+
noisy(name0) if File.exists?(name0)
|
84
|
+
name1 = "reference.I-D.draft-#{namepart}-#{version}.xml"
|
85
|
+
if File.exists?(name1)
|
86
|
+
noisy(name1)
|
87
|
+
FileUtils.touch(name0) # because name1 already exists, we believe name0 is fresh
|
88
|
+
else
|
89
|
+
begin
|
90
|
+
url0 = "https://datatracker.ietf.org/doc/bibxml3/draft-#{namepart}/xml"
|
91
|
+
get_and_write_resource_persistently(url0, name0) # get name0 first
|
92
|
+
url1 = "https://datatracker.ietf.org/doc/bibxml3/draft-#{namepart}-#{version}/xml"
|
93
|
+
get_and_write_resource_persistently(url1, name1) # then name1 to mark this as updated
|
94
|
+
rescue => e
|
95
|
+
warn "*** #{name0}: #{e}"
|
96
|
+
end
|
97
|
+
end
|
98
|
+
else
|
99
|
+
warn "*** Malformed draft name: #{name}"
|
100
|
+
end
|
101
|
+
end
|
102
|
+
clear_noise
|
data/kramdown-rfc2629.gemspec
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
spec = Gem::Specification.new do |s|
|
2
2
|
s.name = 'kramdown-rfc2629'
|
3
|
-
s.version = '1.3.
|
3
|
+
s.version = '1.3.36'
|
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,8 @@ spec = Gem::Specification.new do |s|
|
|
9
9
|
s.add_dependency('json_pure', '~> 2.0')
|
10
10
|
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 data/math.json)
|
11
11
|
s.require_path = 'lib'
|
12
|
-
s.executables = ['kramdown-rfc2629', 'doilit', 'kramdown-rfc-extract-markdown',
|
12
|
+
s.executables = ['kramdown-rfc2629', 'doilit', 'kramdown-rfc-extract-markdown',
|
13
|
+
'kdrfc', 'kramdown-rfc-cache-i-d-bibxml']
|
13
14
|
s.required_ruby_version = '>= 2.3.0'
|
14
15
|
# s.requirements = 'wget'
|
15
16
|
# s.has_rdoc = true
|
data/lib/kramdown-rfc2629.rb
CHANGED
@@ -20,6 +20,7 @@ Kramdown::Parser::Html::Constants::HTML_SPAN_ELEMENTS.concat my_span_elements
|
|
20
20
|
require 'rexml/parsers/baseparser'
|
21
21
|
require 'open3' # for math
|
22
22
|
require 'json' # for math
|
23
|
+
require 'rexml/document' # for SVG and bibxml acrobatics
|
23
24
|
|
24
25
|
class Object
|
25
26
|
def deep_clone
|
@@ -178,6 +179,18 @@ module Kramdown
|
|
178
179
|
|
179
180
|
# :stopdoc:
|
180
181
|
|
182
|
+
KRAMDOWN_PERSISTENT = ENV["KRAMDOWN_PERSISTENT"]
|
183
|
+
KRAMDOWN_PERSISTENT_VERBOSE = /v/ === KRAMDOWN_PERSISTENT
|
184
|
+
|
185
|
+
if KRAMDOWN_PERSISTENT
|
186
|
+
begin
|
187
|
+
require 'net/http/persistent'
|
188
|
+
$http = Net::HTTP::Persistent.new name: 'kramdown-rfc'
|
189
|
+
rescue Exception => e
|
190
|
+
warn "** Can't set up persistent HTTP -- #{e}"
|
191
|
+
end
|
192
|
+
end
|
193
|
+
|
181
194
|
# Defines the amount of indentation used when nesting XML tags.
|
182
195
|
INDENTATION = 2
|
183
196
|
|
@@ -281,7 +294,6 @@ COLORS
|
|
281
294
|
end
|
282
295
|
|
283
296
|
def svg_clean(s) # expensive, risky
|
284
|
-
require "rexml/document"
|
285
297
|
d = REXML::Document.new(s)
|
286
298
|
REXML::XPath.each(d.root, "//*[@shape-rendering]") { |x| x.attributes["shape-rendering"] = nil } #; warn x.inspect }
|
287
299
|
REXML::XPath.each(d.root, "//*[@text-rendering]") { |x| x.attributes["text-rendering"] = nil } #; warn x.inspect }
|
@@ -361,9 +373,12 @@ COLORS
|
|
361
373
|
[result, result1] # text, svg
|
362
374
|
end
|
363
375
|
|
376
|
+
ARTWORK_TYPES = %w(ascii-art binary-art call-flow hex-dump svg)
|
377
|
+
|
364
378
|
def convert_codeblock(el, indent, opts)
|
365
379
|
# el.attr['anchor'] ||= saner_generate_id(el.value) -- no longer in 1.0.6
|
366
380
|
result = el.value
|
381
|
+
gi = el.attr.delete('gi')
|
367
382
|
blockclass = el.attr.delete('class')
|
368
383
|
if blockclass == 'language-tbreak'
|
369
384
|
result = result.lines.map {|line| [line.chomp, 0]}
|
@@ -390,7 +405,7 @@ COLORS
|
|
390
405
|
if md = cl.match(/\Alanguage-(.*)/)
|
391
406
|
t = artwork_attr["type"] = md[1] # XXX overwrite
|
392
407
|
else
|
393
|
-
$stderr.puts "*** Unimplemented
|
408
|
+
$stderr.puts "*** Unimplemented codeblock class: #{cl}"
|
394
409
|
end
|
395
410
|
end
|
396
411
|
end
|
@@ -399,17 +414,27 @@ COLORS
|
|
399
414
|
result[0,0] = "\n" unless result[0,1] == "\n"
|
400
415
|
end
|
401
416
|
el.attr.each do |k, v|
|
402
|
-
if md = k.match(/\
|
417
|
+
if md = k.match(/\A(?:artwork|sourcecode)-(.*)/)
|
403
418
|
el.attr.delete(k)
|
404
419
|
artwork_attr[md[1]] = v
|
405
420
|
end
|
406
421
|
end
|
407
422
|
case t
|
408
423
|
when "goat", "ditaa", "mscgen", "plantuml", "plantuml-utxt", "mermaid", "math"
|
424
|
+
if gi
|
425
|
+
warn "*** Can't set GI #{gi} for composite SVG artset"
|
426
|
+
end
|
409
427
|
result, result1 = memoize(:svg_tool_process, t, result)
|
410
428
|
"#{' '*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"
|
411
429
|
else
|
412
|
-
|
430
|
+
gi ||= (
|
431
|
+
if !$options.v3 || !t || ARTWORK_TYPES.include?(t) || artwork_attr["align"]
|
432
|
+
"artwork"
|
433
|
+
else
|
434
|
+
"sourcecode"
|
435
|
+
end
|
436
|
+
)
|
437
|
+
"#{' '*indent}<figure#{el_html_attributes(el)}><#{gi}#{html_attributes(artwork_attr)}><![CDATA[#{result}#{result =~ /\n\Z/ ? '' : "\n"}]]></#{gi}></figure>\n"
|
413
438
|
end
|
414
439
|
end
|
415
440
|
end
|
@@ -682,6 +707,34 @@ COLORS
|
|
682
707
|
KRAMDOWN_OFFLINE = ENV["KRAMDOWN_OFFLINE"]
|
683
708
|
KRAMDOWN_REFCACHE_REFETCH = ENV["KRAMDOWN_REFCACHE_REFETCH"]
|
684
709
|
|
710
|
+
def get_and_write_resource(url, fn)
|
711
|
+
options = {}
|
712
|
+
if ENV["KRAMDOWN_DONT_VERIFY_HTTPS"]
|
713
|
+
options[:ssl_verify_mode] = OpenSSL::SSL::VERIFY_NONE
|
714
|
+
end # workaround for OpenSSL on Windows...
|
715
|
+
# URI.open(url, **options) do |uf| # not portable to older versions
|
716
|
+
OpenURI.open_uri(url, **options) do |uf|
|
717
|
+
s = uf.read
|
718
|
+
if uf.status[0] != "200"
|
719
|
+
warn "*** Status code #{status} while fetching #{url}"
|
720
|
+
else
|
721
|
+
File.write(fn, s)
|
722
|
+
end
|
723
|
+
end
|
724
|
+
end
|
725
|
+
|
726
|
+
def get_and_write_resource_persistently(url, fn)
|
727
|
+
t1 = Time.now
|
728
|
+
response = $http.request(URI(url))
|
729
|
+
if response.code != "200"
|
730
|
+
raise "Status code #{response.code} while fetching #{url}"
|
731
|
+
else
|
732
|
+
File.write(fn, response.body)
|
733
|
+
end
|
734
|
+
t2 = Time.now
|
735
|
+
warn "(#{"%.3f" % (t2 - t1)} s)" if KRAMDOWN_PERSISTENT_VERBOSE
|
736
|
+
end
|
737
|
+
|
685
738
|
# this is now slightly dangerous as multiple urls could map to the same cachefile
|
686
739
|
def get_and_cache_resource(url, cachefile, tvalid = 7200, tn = Time.now)
|
687
740
|
fn = "#{REFCACHEDIR}/#{cachefile}"
|
@@ -710,18 +763,15 @@ COLORS
|
|
710
763
|
require 'timeout'
|
711
764
|
begin
|
712
765
|
Timeout::timeout(fetch_timeout) do
|
713
|
-
|
714
|
-
|
715
|
-
|
716
|
-
|
717
|
-
|
718
|
-
|
719
|
-
s = uf.read
|
720
|
-
if uf.status[0] != "200"
|
721
|
-
warn "*** Status code #{status} while fetching #{url}"
|
722
|
-
else
|
723
|
-
File.write(fn, s)
|
766
|
+
if $http
|
767
|
+
begin # belt and suspenders
|
768
|
+
get_and_write_resource_persistently(url, fn)
|
769
|
+
rescue Exception => e
|
770
|
+
warn "*** Can't get with persistent HTTP: #{e}"
|
771
|
+
get_and_write_resource(url, fn)
|
724
772
|
end
|
773
|
+
else
|
774
|
+
get_and_write_resource(url, fn)
|
725
775
|
end
|
726
776
|
end
|
727
777
|
rescue OpenURI::HTTPError, Errno::EHOSTUNREACH, Errno::ECONNREFUSED,
|
@@ -769,6 +819,8 @@ COLORS
|
|
769
819
|
|
770
820
|
KRAMDOWN_REFCACHETTL = (e = ENV["KRAMDOWN_REFCACHETTL"]) ? e.to_i : 3600
|
771
821
|
|
822
|
+
KRAMDOWN_NO_TARGETS = ENV['KRAMDOWN_NO_TARGETS']
|
823
|
+
|
772
824
|
def convert_img(el, indent, opts) # misuse the tag!
|
773
825
|
if a = el.attr
|
774
826
|
alt = a.delete('alt').strip
|
@@ -788,7 +840,7 @@ COLORS
|
|
788
840
|
to_insert = ""
|
789
841
|
src.scan(/(W3C|3GPP|[A-Z-]+)[.]?([A-Za-z_0-9.\/\+-]+)/) do |t, n|
|
790
842
|
fn = "reference.#{t}.#{n}.xml"
|
791
|
-
sub, ttl,
|
843
|
+
sub, ttl, _can_anchor, altproc = XML_RESOURCE_ORG_MAP[t]
|
792
844
|
ttl ||= KRAMDOWN_REFCACHETTL # everything but RFCs might change a lot
|
793
845
|
puts "*** Huh: #{fn}" unless sub
|
794
846
|
if altproc && !KRAMDOWN_USE_TOOLS_SERVER
|
@@ -802,10 +854,32 @@ COLORS
|
|
802
854
|
# end
|
803
855
|
to_insert = get_and_cache_resource(url, fn.gsub('/', '_'), ttl)
|
804
856
|
to_insert.scrub! rescue nil # only do this for Ruby >= 2.1
|
805
|
-
|
806
|
-
|
857
|
+
|
858
|
+
begin
|
859
|
+
d = REXML::Document.new(to_insert)
|
860
|
+
d.xml_decl.nowrite
|
861
|
+
d.root.attributes["anchor"] = anchor
|
862
|
+
if t == "RFC" or t == "I-D"
|
863
|
+
if KRAMDOWN_NO_TARGETS
|
864
|
+
d.root.attributes["target"] = nil
|
865
|
+
REXML::XPath.each(d.root, "/reference/format") { |x|
|
866
|
+
d.root.delete_element(x)
|
867
|
+
}
|
868
|
+
else
|
869
|
+
REXML::XPath.each(d.root, "/reference/format") { |x|
|
870
|
+
x.attributes["target"].sub!(%r{https?://www.ietf.org/internet-drafts/},
|
871
|
+
%{https://www.ietf.org/archive/id/}) if t == "I-D"
|
872
|
+
}
|
873
|
+
end
|
874
|
+
end
|
875
|
+
to_insert = d.to_s
|
876
|
+
rescue Exception => e
|
877
|
+
warn "** Can't manipulate reference XML: #{e}"
|
878
|
+
broken = true
|
879
|
+
to_insert = nil
|
880
|
+
end
|
807
881
|
# this may be a bit controversial: Don't break the build if reference is broken
|
808
|
-
if KRAMDOWN_OFFLINE
|
882
|
+
if KRAMDOWN_OFFLINE || broken
|
809
883
|
unless to_insert
|
810
884
|
to_insert = "<reference anchor='#{anchor}'> <front> <title>*** BROKEN REFERENCE ***</title> <author> <organization/> </author> <date/> </front> </reference>"
|
811
885
|
warn "*** KRAMDOWN_OFFLINE: Inserting broken reference for #{fn}"
|
@@ -814,8 +888,7 @@ COLORS
|
|
814
888
|
exit 66 unless to_insert # EX_NOINPUT
|
815
889
|
end
|
816
890
|
end
|
817
|
-
to_insert
|
818
|
-
.sub(/\banchor=(?:"[^"]+"|'[^']+')/, "anchor=\"#{anchor}\"")
|
891
|
+
to_insert
|
819
892
|
else
|
820
893
|
"<xref#{el_html_attributes(el)}>#{alt}</xref>"
|
821
894
|
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.
|
4
|
+
version: 1.3.36
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Carsten Bormann
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2021-02-
|
11
|
+
date: 2021-02-23 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: kramdown
|
@@ -61,6 +61,7 @@ executables:
|
|
61
61
|
- doilit
|
62
62
|
- kramdown-rfc-extract-markdown
|
63
63
|
- kdrfc
|
64
|
+
- kramdown-rfc-cache-i-d-bibxml
|
64
65
|
extensions: []
|
65
66
|
extra_rdoc_files: []
|
66
67
|
files:
|
@@ -68,6 +69,7 @@ files:
|
|
68
69
|
- README.md
|
69
70
|
- bin/doilit
|
70
71
|
- bin/kdrfc
|
72
|
+
- bin/kramdown-rfc-cache-i-d-bibxml
|
71
73
|
- bin/kramdown-rfc-extract-markdown
|
72
74
|
- bin/kramdown-rfc2629
|
73
75
|
- data/encoding-fallbacks.txt
|