devcenter-parser 2.2.4 → 2.2.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 +5 -5
- data/Gemfile.lock +14 -14
- data/devcenter-parser.gemspec +2 -2
- data/lib/devcenter-parser.rb +15 -10
- data/lib/devcenter-parser/header_id_generator.rb +7 -1
- data/lib/devcenter-parser/version.rb +1 -1
- data/test/devcenter-parser_test.rb +42 -6
- data/test/header_id_generator_test.rb +6 -0
- metadata +10 -11
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
|
-
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
2
|
+
SHA256:
|
3
|
+
metadata.gz: 251949c020f60adc81bbaa2dc0851b5d594486d74620db779cb8030ba8b41c45
|
4
|
+
data.tar.gz: e700ec53adb5a531eaaf93f7c70677aabaa6959e801b6fed79bf5ac7f8c559f4
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 9746c03c129900fbc006b96927cfd5f0ffd50169ffc444490e4f219b1a14aa46c8b764d81e21667b0c07a8d6f17cec5277f5da1956070c9b404c3e9af3b96968
|
7
|
+
data.tar.gz: d41b9cd6f6248178991096e1c2bbb26fdc1a9dfc6b9f02cb4a1e511a2f36de83b60a44b1e7c6a0218b5983713cd7aadb93d2214b0a5cad7e8c2f923dc59b4814
|
data/Gemfile.lock
CHANGED
@@ -1,27 +1,27 @@
|
|
1
1
|
PATH
|
2
2
|
remote: .
|
3
3
|
specs:
|
4
|
-
devcenter-parser (2.2.
|
4
|
+
devcenter-parser (2.2.10)
|
5
5
|
nokogiri (>= 1.7.1)
|
6
|
-
redcarpet (= 3.
|
7
|
-
sanitize (~>
|
6
|
+
redcarpet (= 3.5.0)
|
7
|
+
sanitize (~> 5.2.1)
|
8
8
|
|
9
9
|
GEM
|
10
10
|
remote: http://rubygems.org/
|
11
11
|
specs:
|
12
|
-
crass (1.0.
|
13
|
-
mini_portile2 (2.
|
12
|
+
crass (1.0.6)
|
13
|
+
mini_portile2 (2.4.0)
|
14
14
|
minitest (5.10.1)
|
15
|
-
nokogiri (1.
|
16
|
-
mini_portile2 (~> 2.
|
17
|
-
nokogumbo (
|
18
|
-
nokogiri
|
15
|
+
nokogiri (1.10.10)
|
16
|
+
mini_portile2 (~> 2.4.0)
|
17
|
+
nokogumbo (2.0.2)
|
18
|
+
nokogiri (~> 1.8, >= 1.8.4)
|
19
19
|
rake (12.0.0)
|
20
|
-
redcarpet (3.
|
21
|
-
sanitize (
|
20
|
+
redcarpet (3.5.0)
|
21
|
+
sanitize (5.2.1)
|
22
22
|
crass (~> 1.0.2)
|
23
|
-
nokogiri (>= 1.
|
24
|
-
nokogumbo (~>
|
23
|
+
nokogiri (>= 1.8.0)
|
24
|
+
nokogumbo (~> 2.0)
|
25
25
|
|
26
26
|
PLATFORMS
|
27
27
|
ruby
|
@@ -32,4 +32,4 @@ DEPENDENCIES
|
|
32
32
|
rake
|
33
33
|
|
34
34
|
BUNDLED WITH
|
35
|
-
1.
|
35
|
+
1.17.2
|
data/devcenter-parser.gemspec
CHANGED
@@ -15,8 +15,8 @@ Gem::Specification.new do |gem|
|
|
15
15
|
gem.require_paths = %w{ lib }
|
16
16
|
|
17
17
|
gem.add_runtime_dependency 'nokogiri', '>= 1.7.1'
|
18
|
-
gem.add_runtime_dependency 'redcarpet', '3.
|
19
|
-
gem.add_runtime_dependency 'sanitize', '~>
|
18
|
+
gem.add_runtime_dependency 'redcarpet', '3.5.0'
|
19
|
+
gem.add_runtime_dependency 'sanitize', '~>5.2.1'
|
20
20
|
|
21
21
|
gem.add_development_dependency 'minitest', '>2.0'
|
22
22
|
gem.add_development_dependency 'rake'
|
data/lib/devcenter-parser.rb
CHANGED
@@ -10,14 +10,14 @@ module DevcenterParser
|
|
10
10
|
class InvalidMarkdownError < Exception; end
|
11
11
|
class InvalidRawHTMLError < Exception; end
|
12
12
|
|
13
|
-
def self.to_html(markdown)
|
14
|
-
sanitize to_unsanitized_html(markdown)
|
13
|
+
def self.to_html(markdown, options = {})
|
14
|
+
sanitize to_unsanitized_html(markdown, options)
|
15
15
|
end
|
16
16
|
|
17
|
-
def self.to_unsanitized_html(markdown)
|
17
|
+
def self.to_unsanitized_html(markdown, options = {})
|
18
18
|
markdown = normalize_markdown(markdown)
|
19
19
|
doc = GitHubParser.parse(markdown)
|
20
|
-
doc_to_html(doc)
|
20
|
+
doc_to_html(doc, options)
|
21
21
|
rescue InvalidRawHTMLError => e
|
22
22
|
raise InvalidMarkdownError, e.message
|
23
23
|
end
|
@@ -28,9 +28,9 @@ module DevcenterParser
|
|
28
28
|
|
29
29
|
private
|
30
30
|
|
31
|
-
def self.doc_to_html(doc)
|
31
|
+
def self.doc_to_html(doc, options = {})
|
32
32
|
HeaderIdGenerator.apply!(doc)
|
33
|
-
convert_to_article_links_all_relative_links_with_missing_initial_slashes(doc)
|
33
|
+
convert_to_article_links_all_relative_links_with_missing_initial_slashes(doc, options)
|
34
34
|
html = doc.to_html(:encoding => 'utf-8')
|
35
35
|
verify_raw_html(html)
|
36
36
|
html
|
@@ -92,10 +92,15 @@ module DevcenterParser
|
|
92
92
|
@@sanitize_config = config.merge({remove_contents: true, allow_comments: true})
|
93
93
|
end
|
94
94
|
|
95
|
-
def self.convert_to_article_links_all_relative_links_with_missing_initial_slashes(doc)
|
95
|
+
def self.convert_to_article_links_all_relative_links_with_missing_initial_slashes(doc, options = {})
|
96
|
+
link_prefix = options[:link_prefix] || '/articles'
|
96
97
|
doc.css('a').each do |node|
|
97
|
-
|
98
|
-
|
98
|
+
next if node['href'].nil? || node['href'] =~ /\Ahttp|\A\/|\Amailto\:|\A#/
|
99
|
+
|
100
|
+
if node['href'].start_with? 'categories/'
|
101
|
+
node['href'] = "/#{node['href']}"
|
102
|
+
else
|
103
|
+
node['href'] = "#{link_prefix}/#{node['href']}".gsub('/articles/articles/', '/articles/')
|
99
104
|
end
|
100
105
|
end
|
101
106
|
end
|
@@ -124,7 +129,7 @@ module DevcenterParser
|
|
124
129
|
end
|
125
130
|
|
126
131
|
def self.iframe_has_invalid_src?(node)
|
127
|
-
node.attributes['src'].value !~
|
132
|
+
node.attributes['src'].value !~ /https:\/\/player.vimeo.com(.+)(&|\?)dnt=true/i && node.attributes['src'].value !~ /\Ahttps:\/\/www\.youtube-nocookie\.com\/embed/i
|
128
133
|
end
|
129
134
|
|
130
135
|
def self.iframe?(node)
|
@@ -72,7 +72,13 @@ class HeaderIdGenerator
|
|
72
72
|
end
|
73
73
|
|
74
74
|
def add_default_ids
|
75
|
-
@nodes_ids.each
|
75
|
+
@nodes_ids.each do |node, _|
|
76
|
+
if node['id'].to_s.empty?
|
77
|
+
@nodes_ids[node] = subheader_id(node.content)
|
78
|
+
else
|
79
|
+
@nodes_ids[node] = node['id']
|
80
|
+
end
|
81
|
+
end
|
76
82
|
end
|
77
83
|
|
78
84
|
def subheader_id(content)
|
@@ -42,11 +42,31 @@ describe 'DevcenterParser' do
|
|
42
42
|
assert_parsing_result md, html
|
43
43
|
end
|
44
44
|
|
45
|
-
it 'allows embedding vimeo videos' do
|
46
|
-
src = '<iframe src="https://player.vimeo.com/video/
|
45
|
+
it 'allows embedding vimeo videos when their do-no-track param is set to true' do
|
46
|
+
src = '<iframe src="https://player.vimeo.com/video/143343818?api=1&dnt=true&title=foo" width="50" height="281" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe>'
|
47
47
|
assert_parsing_result src, src
|
48
48
|
end
|
49
49
|
|
50
|
+
it 'allows embedding youtube videos from its no-cookies domain' do
|
51
|
+
src = '<iframe width="560" height="315" src="https://www.youtube-nocookie.com/embed/123456ABCDEF" frameborder="0" allowfullscreen=""></iframe>'
|
52
|
+
assert_parsing_result src, src
|
53
|
+
end
|
54
|
+
|
55
|
+
it 'removes youtube videos embedded from the with-cookies domain' do
|
56
|
+
src = '<iframe width="560" height="315" src="https://www.youtube.com/embed/123456ABCDEF" frameborder="0" allowfullscreen=""></iframe>'
|
57
|
+
assert_parsing_result src, ''
|
58
|
+
end
|
59
|
+
|
60
|
+
it 'does not allow embedding vimeo videos when their do-no-track param is set to something different than true' do
|
61
|
+
src = '<iframe src="https://player.vimeo.com/video/143343818?api=1&dnt=foo&title=foo" width="50" height="281" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe>'
|
62
|
+
assert_parsing_result src, ''
|
63
|
+
end
|
64
|
+
|
65
|
+
it 'does not allow embedding vimeo videos when their do-no-track param is not passed' do
|
66
|
+
src = '<iframe src="https://player.vimeo.com/video/143343818?api=1&&title=foo" width="50" height="281" frameborder="0" webkitallowfullscreen="" mozallowfullscreen="" allowfullscreen=""></iframe>'
|
67
|
+
assert_parsing_result src, ''
|
68
|
+
end
|
69
|
+
|
50
70
|
it 'allows images' do
|
51
71
|
src = '<p><img src="http://nav.heroku.com/images/logos/logo.png" alt="image"></p>'
|
52
72
|
assert_parsing_result src, src
|
@@ -234,7 +254,7 @@ And that's it.
|
|
234
254
|
more callout</p>
|
235
255
|
</div>
|
236
256
|
|
237
|
-
<p class="devcenter-parser-special-block-separator" style="display:none"
|
257
|
+
<p class="devcenter-parser-special-block-separator" style="display:none"> </p>
|
238
258
|
|
239
259
|
<blockquote>
|
240
260
|
<p>normal</p>
|
@@ -263,7 +283,7 @@ more callout</p>
|
|
263
283
|
<p>foo</p>
|
264
284
|
</div>
|
265
285
|
|
266
|
-
<p class="devcenter-parser-special-block-separator" style="display:none"
|
286
|
+
<p class="devcenter-parser-special-block-separator" style="display:none"> </p>
|
267
287
|
|
268
288
|
<div class="note">
|
269
289
|
<p>bar</p>
|
@@ -336,13 +356,21 @@ HTML
|
|
336
356
|
end
|
337
357
|
|
338
358
|
it 'converts relative links with missing initial slashes to article links' do
|
339
|
-
['foo', 'foo/bar', 'foo#bar', '123'].each do |href|
|
359
|
+
['foo', 'foo/bar', 'foo#bar', '123', 'categories'].each do |href|
|
340
360
|
md = "[link](#{href})"
|
341
361
|
html = "<p><a href=\"/articles/#{href}\">link</a></p>"
|
342
362
|
assert_parsing_result md, html
|
343
363
|
end
|
344
364
|
end
|
345
365
|
|
366
|
+
it 'ignores links with missing initial slashes IFF they start with `categories/`' do
|
367
|
+
['categories/foo', 'categories/foo/bar', 'categories/foo#bar', 'categories/123'].each do |href|
|
368
|
+
md = "[link](#{href})"
|
369
|
+
html = "<p><a href=\"/#{href}\">link</a></p>"
|
370
|
+
assert_parsing_result md, html
|
371
|
+
end
|
372
|
+
end
|
373
|
+
|
346
374
|
it 'converts "articles/foo relative links with missing initial slashes to article links' do
|
347
375
|
md = '[link](articles/foo)'
|
348
376
|
html = '<p><a href="/articles/foo">link</a></p>'
|
@@ -353,6 +381,14 @@ HTML
|
|
353
381
|
assert_parsing_result md, html
|
354
382
|
end
|
355
383
|
|
384
|
+
it 'adds a link prefix from options for relative dev center links' do
|
385
|
+
md = '[link](foo)'
|
386
|
+
expected = '<p><a href="/ja/articles/foo">link</a></p>'
|
387
|
+
|
388
|
+
result = DevcenterParser.to_html(md, { link_prefix: '/ja/articles' })
|
389
|
+
assert_equal expected.strip, result.strip, "Failed when parsing\n#{md}\n.\n\nExpected:\n#{expected}\n\nActual result:\n#{result}\n\n"
|
390
|
+
end
|
391
|
+
|
356
392
|
it 'does not alter relative links with initial slashes nor absolute links nor anchor links to the same doc' do
|
357
393
|
['http://foo.com', 'https://foo.com', '/foo', '/foo/bar', '/foo#bar', '#foo', '/123', 'mailto:foo@foobar.com'].each do |href|
|
358
394
|
md = "[link](#{href})"
|
@@ -380,7 +416,7 @@ HTML
|
|
380
416
|
<p>foo</p>
|
381
417
|
</blockquote>
|
382
418
|
|
383
|
-
<p class="devcenter-parser-special-block-separator" style="display:none"
|
419
|
+
<p class="devcenter-parser-special-block-separator" style="display:none"> </p>
|
384
420
|
|
385
421
|
<blockquote>
|
386
422
|
<p>bar</p>
|
@@ -13,6 +13,12 @@ describe 'HeaderIdGeneratorTest' do
|
|
13
13
|
assert_id result(html), 'h2', 'foo-bar-header-123'
|
14
14
|
end
|
15
15
|
|
16
|
+
it 'does not replace existing ids' do
|
17
|
+
html = '<h2 id="foo">Foo Bar</h2><p>Content</p><h3>Baz</h3>'
|
18
|
+
assert_id result(html), 'h2', 'foo'
|
19
|
+
assert_id result(html), 'h3', 'baz'
|
20
|
+
end
|
21
|
+
|
16
22
|
it 'generates ids replacing inner non-alphanum chars with dashes' do
|
17
23
|
['Foo Bar', 'Foo-Bar', 'Foo#bar', 'Foo##Bar', 'Foo##Bar', '-$Foo##Bar$-'].each do |title|
|
18
24
|
html = "<h2>#{title}</h2>"
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: devcenter-parser
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 2.2.
|
4
|
+
version: 2.2.10
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Heroku
|
8
|
-
autorequire:
|
8
|
+
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2020-11-05 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: nokogiri
|
@@ -30,28 +30,28 @@ dependencies:
|
|
30
30
|
requirements:
|
31
31
|
- - '='
|
32
32
|
- !ruby/object:Gem::Version
|
33
|
-
version: 3.
|
33
|
+
version: 3.5.0
|
34
34
|
type: :runtime
|
35
35
|
prerelease: false
|
36
36
|
version_requirements: !ruby/object:Gem::Requirement
|
37
37
|
requirements:
|
38
38
|
- - '='
|
39
39
|
- !ruby/object:Gem::Version
|
40
|
-
version: 3.
|
40
|
+
version: 3.5.0
|
41
41
|
- !ruby/object:Gem::Dependency
|
42
42
|
name: sanitize
|
43
43
|
requirement: !ruby/object:Gem::Requirement
|
44
44
|
requirements:
|
45
45
|
- - "~>"
|
46
46
|
- !ruby/object:Gem::Version
|
47
|
-
version:
|
47
|
+
version: 5.2.1
|
48
48
|
type: :runtime
|
49
49
|
prerelease: false
|
50
50
|
version_requirements: !ruby/object:Gem::Requirement
|
51
51
|
requirements:
|
52
52
|
- - "~>"
|
53
53
|
- !ruby/object:Gem::Version
|
54
|
-
version:
|
54
|
+
version: 5.2.1
|
55
55
|
- !ruby/object:Gem::Dependency
|
56
56
|
name: minitest
|
57
57
|
requirement: !ruby/object:Gem::Requirement
|
@@ -103,7 +103,7 @@ files:
|
|
103
103
|
homepage: https://devcenter.heroku.com
|
104
104
|
licenses: []
|
105
105
|
metadata: {}
|
106
|
-
post_install_message:
|
106
|
+
post_install_message:
|
107
107
|
rdoc_options: []
|
108
108
|
require_paths:
|
109
109
|
- lib
|
@@ -118,9 +118,8 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
118
118
|
- !ruby/object:Gem::Version
|
119
119
|
version: '0'
|
120
120
|
requirements: []
|
121
|
-
|
122
|
-
|
123
|
-
signing_key:
|
121
|
+
rubygems_version: 3.0.3
|
122
|
+
signing_key:
|
124
123
|
specification_version: 4
|
125
124
|
summary: Parser for Heroku Dev Center's content
|
126
125
|
test_files:
|