d-mark 1.0.0a2 → 1.0.0a3

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
  SHA1:
3
- metadata.gz: 686fe4c2cf9132e4bfd42debaac837d66b911c40
4
- data.tar.gz: 3649616bac8b3eccb25de17e433ecea93af77bc9
3
+ metadata.gz: b1542c550fe7394de16bd088b2b0adc7bc369419
4
+ data.tar.gz: 6601aacc0e5d8c9b5aae40309b8802acef9652dc
5
5
  SHA512:
6
- metadata.gz: b419728d8c5bf01674fb87c1401f6a47c8a7d90883efce6fce0de6612f50060f5cb3dcf740e77ce6601df04992e7a2ad050a209631e8062fc2e1b5e89c63745b
7
- data.tar.gz: 7404cc61b20b0c2fed2d7dd8fb76127e8c8ea30c6f42d2c6525297c027bf4d6b84a5deea1b311e621c305e9c82615f0ab0b8da187c6894ec690986e302edc166
6
+ metadata.gz: f5775a149e72d08f1ca5f24b3a2fd9f1ce78084fc790d6aa562db07912d0d19d62de09b1e1c3ff66636465bcf657ffb063345ddb6fa52a5bbce3ac1e989a0a55
7
+ data.tar.gz: c91e5b502cb9950561c257ba6f765d04d5b125c6f7ce965b336f843561a864050fcd217adb2b658b37f05c5ffbb70a56f8ca410159eabc72811f2639d34f5e1e
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- d-mark (1.0.0a2)
4
+ d-mark (1.0.0a3)
5
5
 
6
6
  GEM
7
7
  remote: https://rubygems.org/
@@ -46,7 +46,7 @@ GEM
46
46
  method_source (~> 0.8.1)
47
47
  slop (~> 3.4)
48
48
  rainbow (2.1.0)
49
- rake (10.5.0)
49
+ rake (11.1.0)
50
50
  rb-fsevent (0.9.7)
51
51
  rb-inotify (0.9.7)
52
52
  ffi (>= 0.5.0)
@@ -54,7 +54,7 @@ GEM
54
54
  rspec-core (~> 3.4.0)
55
55
  rspec-expectations (~> 3.4.0)
56
56
  rspec-mocks (~> 3.4.0)
57
- rspec-core (3.4.3)
57
+ rspec-core (3.4.4)
58
58
  rspec-support (~> 3.4.0)
59
59
  rspec-expectations (3.4.0)
60
60
  diff-lcs (>= 1.2.0, < 2.0)
@@ -63,12 +63,12 @@ GEM
63
63
  diff-lcs (>= 1.2.0, < 2.0)
64
64
  rspec-support (~> 3.4.0)
65
65
  rspec-support (3.4.1)
66
- rubocop (0.37.2)
67
- parser (>= 2.3.0.4, < 3.0)
66
+ rubocop (0.38.0)
67
+ parser (>= 2.3.0.6, < 3.0)
68
68
  powerpack (~> 0.1)
69
69
  rainbow (>= 1.99.1, < 3.0)
70
70
  ruby-progressbar (~> 1.7)
71
- unicode-display_width (~> 0.3)
71
+ unicode-display_width (~> 1.0, >= 1.0.1)
72
72
  ruby-progressbar (1.7.5)
73
73
  shellany (0.0.1)
74
74
  simplecov (0.11.2)
@@ -78,7 +78,7 @@ GEM
78
78
  simplecov-html (0.10.0)
79
79
  slop (3.6.0)
80
80
  thor (0.19.1)
81
- unicode-display_width (0.3.1)
81
+ unicode-display_width (1.0.2)
82
82
  url (0.3.2)
83
83
 
84
84
  PLATFORMS
@@ -94,4 +94,4 @@ DEPENDENCIES
94
94
  rubocop
95
95
 
96
96
  BUNDLED WITH
97
- 1.11.2
97
+ 1.12.5
data/NEWS.md CHANGED
@@ -1,5 +1,13 @@
1
1
  # D★Mark news
2
2
 
3
+ ## 1.0.0a3 (2016-07-03)
4
+
5
+ Changes:
6
+
7
+ * Dropped support for Ruby 2.1
8
+ * Removed CLI
9
+ * Changed `Translator` API to allow specialisation
10
+
3
11
  ## 1.0.0a2 (2016-03-06)
4
12
 
5
13
  Changes:
@@ -16,7 +16,7 @@ Here’s an example of D★Mark:
16
16
  ----
17
17
  para. This a paragraph; an element in block form containing some text.
18
18
 
19
- note[only=web]. This is a note that will %emph{only} show up on web.
19
+ note[only=web]. This is a note that will %em{only} show up on web.
20
20
  ----
21
21
 
22
22
  For details, see the http://ddfreyne.github.io/d-mark/[D★Mark web page].
data/Rakefile CHANGED
@@ -12,7 +12,3 @@ RuboCop::RakeTask.new(:rubocop) do |task|
12
12
  end
13
13
 
14
14
  task default: [:spec, :rubocop]
15
-
16
- rule 'doc.html' => 'doc.dmark' do |t|
17
- sh "bundle exec ruby samples/doc2html.rb #{t.source} #{t.name}"
18
- end
@@ -20,7 +20,7 @@ Gem::Specification.new do |s|
20
20
  s.rdoc_options = ['--main', 'README.adoc']
21
21
  s.extra_rdoc_files = ['LICENSE', 'README.adoc', 'NEWS.md']
22
22
 
23
- s.required_ruby_version = '>= 2.1.0'
23
+ s.required_ruby_version = '>= 2.2.0'
24
24
 
25
25
  s.add_development_dependency('bundler', '>= 1.11.2', '< 2.0')
26
26
  end
@@ -356,7 +356,7 @@ module DMark
356
356
  advance
357
357
  char.to_s
358
358
  when nil, "\n"
359
- raise_parse_error("expected something after %")
359
+ raise_parse_error('expected something after %')
360
360
  else
361
361
  read_inline_element
362
362
  end
@@ -1,28 +1,57 @@
1
1
  module DMark
2
2
  class Translator
3
- attr_reader :out
3
+ class UnhandledNode < StandardError
4
+ attr_reader :node
4
5
 
5
- def initialize(nodes)
6
- @nodes = nodes
6
+ def initialize(node)
7
+ @node = node
8
+ end
9
+
10
+ def message
11
+ case @node
12
+ when String
13
+ 'Unhandled string node'
14
+ when DMark::ElementNode
15
+ "Unhandled element node #{@node.name.inspect}"
16
+ else
17
+ "Unhandled node #{@node.inspect}"
18
+ end
19
+ end
20
+ end
21
+
22
+ def self.translate(nodes, context = {})
23
+ new.translate(nodes, context)
24
+ end
7
25
 
8
- @out = ''
26
+ def translate(nodes, context = {})
27
+ [nodes.map { |node| handle(node, context) }].flatten.join('')
9
28
  end
10
29
 
11
- def run
12
- @nodes.each do |node|
13
- handle(node)
30
+ def handle(node, context = {})
31
+ case node
32
+ when String
33
+ handle_string(node, context)
34
+ when DMark::ElementNode
35
+ handle_element(node, context)
36
+ else
37
+ raise ArgumentError, "Cannot handle #{node.class}"
14
38
  end
15
- @out
16
39
  end
17
40
 
18
- private
41
+ # @abstract
42
+ def handle_string(string, _context)
43
+ raise DMark::Translator::UnhandledNode.new(string)
44
+ end
19
45
 
20
- def handle(_node)
21
- raise NotImplementedError
46
+ # @abstract
47
+ def handle_element(element, _context)
48
+ raise DMark::Translator::UnhandledNode.new(element)
22
49
  end
23
50
 
24
- def handle_children(node)
25
- node.children.each { |child| handle(child) }
51
+ private
52
+
53
+ def handle_children(node, context)
54
+ node.children.map { |child| handle(child, context) }
26
55
  end
27
56
  end
28
57
  end
@@ -1,3 +1,3 @@
1
1
  module DMark
2
- VERSION = '1.0.0a2'.freeze
2
+ VERSION = '1.0.0a3'.freeze
3
3
  end
@@ -0,0 +1,65 @@
1
+ require 'd-mark'
2
+
3
+ module DMarkBook
4
+ module Translators
5
+ class HTML < DMark::Translator
6
+ def handle_string(node)
7
+ [html_escape(node)]
8
+ end
9
+
10
+ def handle_element(node, path)
11
+ case node.name
12
+ when 'p', 'dl', 'dt', 'dd', 'ol', 'ul', 'li', 'code', 'kbd', 'blockquote'
13
+ wrap(node.name) { handle_children(node, path) }
14
+ when 'h'
15
+ depth = path.count { |node| node.name == 'section' } + 1
16
+ wrap("h#{depth}") { handle_children(node, path) }
17
+ when 'section'
18
+ wrap('section', id: id_for_section(node)) { handle_children(node, path) }
19
+ when 'em'
20
+ wrap('em') { handle_children(node, path) }
21
+ when 'link'
22
+ wrap('a', href: node.attributes['target']) { handle_children(node, path) }
23
+ when 'listing'
24
+ wrap('pre') { wrap('code') { handle_children(node, path) } }
25
+ else
26
+ raise DMark::Translator::UnhandledNode.new(node)
27
+ end
28
+ end
29
+
30
+ def wrap(name, params = {})
31
+ params_string = params.map { |k, v| " #{k}=\"#{html_escape(v)}\"" }.join('')
32
+ ["<#{name}#{params_string}>", yield, "</#{name}>"]
33
+ end
34
+
35
+ def html_escape(s)
36
+ s.gsub('&', '&amp;').gsub('<', '&lt;')
37
+ end
38
+
39
+ def id_for_section(node)
40
+ header = node.children.find { |c| c.name == 'h' }
41
+ text = header.children.join('')
42
+ text.downcase.gsub(/[^a-zA-Z-]/, '-')
43
+ end
44
+ end
45
+ end
46
+ end
47
+
48
+ class SpecialHTML < DMarkBook::Translators::HTML
49
+ def handle_element(node, depths)
50
+ case node.name
51
+ when 'firstterm', 'prompt', 'filename'
52
+ wrap('span', class: node.name) { handle_children(node, depths) }
53
+ when 'note', 'todo'
54
+ wrap('div', class: node.name) { handle_children(node, depths) }
55
+ else
56
+ super
57
+ end
58
+ end
59
+ end
60
+
61
+ content = File.readlines('site/content/index.dmark').drop(4).join
62
+ parser = DMark::Parser.new(content)
63
+ tree = parser.parse
64
+
65
+ puts SpecialHTML.new.translate(tree)
@@ -1 +1 @@
1
- p. I’m a %em{trivial} example!
1
+ #p I’m a %em{trivial} example!
@@ -44,7 +44,8 @@ describe 'DMark::Parser#parser' do
44
44
  'p', {},
45
45
  [
46
46
  element('foo', {}, ['}'])
47
- ])
47
+ ]
48
+ )
48
49
  ]
49
50
  end
50
51
 
@@ -161,8 +162,8 @@ describe 'DMark::Parser#parser' do
161
162
  end
162
163
 
163
164
  it 'parses inline element in data lines' do
164
- expect(parse("#p\n %emph{donkey}")).to eq [
165
- element('p', {}, [element('emph', {}, ['donkey'])])
165
+ expect(parse("#p\n %em{donkey}")).to eq [
166
+ element('p', {}, [element('em', {}, ['donkey'])])
166
167
  ]
167
168
  end
168
169
 
@@ -1,5 +1,5 @@
1
1
  describe DMark::Translator do
2
- let(:translator) { translator_class.new(nodes) }
2
+ let(:translator) { translator_class.new }
3
3
  let(:translator_class) { described_class }
4
4
 
5
5
  let(:nodes) do
@@ -7,39 +7,95 @@ describe DMark::Translator do
7
7
  DMark::ElementNode.new(
8
8
  'para',
9
9
  { 'only' => 'web', 'animal' => 'donkey' },
10
- ['Hi!']
10
+ [
11
+ DMark::ElementNode.new('em', {}, ['Hello']),
12
+ ' world!'
13
+ ]
11
14
  )
12
15
  ]
13
16
  end
14
17
 
15
- describe '#run' do
16
- subject { translator.run }
17
-
18
+ shared_examples 'translates' do
18
19
  context 'translator base class' do
19
- it 'raises NotImplementedError' do
20
- expect { subject }.to raise_error(NotImplementedError)
20
+ it 'raises error' do
21
+ expect { subject }.to raise_error(
22
+ DMark::Translator::UnhandledNode,
23
+ 'Unhandled element node "para"'
24
+ )
21
25
  end
22
26
  end
23
27
 
24
28
  context 'custom translator' do
25
29
  let(:translator_class) do
26
30
  Class.new(described_class) do
27
- def handle(node)
28
- case node
29
- when String
30
- out << node
31
- when DMark::ElementNode
32
- out << "<#{node.name}"
33
- out << node.attributes.map { |k, v| ' ' + [k, v].join('=') }.join
34
- out << '>'
35
- handle_children(node)
36
- out << "</#{node.name}>"
31
+ def handle_string(string, _context)
32
+ [string]
33
+ end
34
+
35
+ def handle_element(element, context)
36
+ [
37
+ "<#{element.name}",
38
+ element.attributes.map { |k, v| ' ' + [k, v].join('=') }.join,
39
+ '>',
40
+ handle_children(element, context),
41
+ "</#{element.name}>"
42
+ ]
43
+ end
44
+ end
45
+ end
46
+
47
+ it { is_expected.to eql('<para only=web animal=donkey><em>Hello</em> world!</para>') }
48
+
49
+ context 'doing something with context' do
50
+ let(:translator_class) do
51
+ Class.new(described_class) do
52
+ def handle_string(string, context)
53
+ [string, " [parent=#{context[:kind]}]"]
54
+ end
55
+
56
+ def handle_element(element, context)
57
+ [
58
+ "<#{element.name}",
59
+ element.attributes.map { |k, v| ' ' + [k, v].join('=') }.join,
60
+ '>',
61
+ handle_children(element, context.merge(kind: element.name)),
62
+ "</#{element.name}>"
63
+ ]
37
64
  end
38
65
  end
39
66
  end
67
+
68
+ it { is_expected.to eql('<para only=web animal=donkey><em>Hello [parent=em]</em> world! [parent=para]</para>') }
40
69
  end
70
+ end
71
+ end
72
+
73
+ shared_examples 'errors on unknown type' do
74
+ it 'raises' do
75
+ expect { subject }.to raise_error(
76
+ ArgumentError,
77
+ 'Cannot handle Symbol'
78
+ )
79
+ end
80
+ end
81
+
82
+ describe '.translate' do
83
+ subject { translator_class.translate(nodes) }
84
+ include_examples 'translates'
85
+
86
+ context 'unrecognised type' do
87
+ subject { translator_class.translate([:donkey]) }
88
+ include_examples 'errors on unknown type'
89
+ end
90
+ end
91
+
92
+ describe '#translate' do
93
+ subject { translator.translate(nodes) }
94
+ include_examples 'translates'
41
95
 
42
- it { is_expected.to eql('<para only=web animal=donkey>Hi!</para>') }
96
+ context 'unrecognised type' do
97
+ subject { translator.translate([:donkey]) }
98
+ include_examples 'errors on unknown type'
43
99
  end
44
100
  end
45
101
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: d-mark
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.0a2
4
+ version: 1.0.0a3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Denis Defreyne
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2016-03-06 00:00:00.000000000 Z
11
+ date: 2016-07-03 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -49,11 +49,11 @@ files:
49
49
  - Rakefile
50
50
  - d-mark.gemspec
51
51
  - lib/d-mark.rb
52
- - lib/d-mark/cli.rb
53
52
  - lib/d-mark/element_node.rb
54
53
  - lib/d-mark/parser.rb
55
54
  - lib/d-mark/translator.rb
56
55
  - lib/d-mark/version.rb
56
+ - samples/test.rb
57
57
  - samples/trivial.dmark
58
58
  - samples/trivial.rb
59
59
  - spec/d-mark/element_node_spec.rb
@@ -74,7 +74,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
74
74
  requirements:
75
75
  - - ">="
76
76
  - !ruby/object:Gem::Version
77
- version: 2.1.0
77
+ version: 2.2.0
78
78
  required_rubygems_version: !ruby/object:Gem::Requirement
79
79
  requirements:
80
80
  - - ">"
@@ -82,7 +82,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
82
82
  version: 1.3.1
83
83
  requirements: []
84
84
  rubyforge_project:
85
- rubygems_version: 2.5.2
85
+ rubygems_version: 2.6.6
86
86
  signing_key:
87
87
  specification_version: 4
88
88
  summary: markup language for writing text
@@ -1,28 +0,0 @@
1
- require_relative '../d-mark'
2
-
3
- data = File.read(ARGV[0]).strip
4
-
5
- parser = DMark::Parser.new(data)
6
- begin
7
- before = Time.now
8
- result = parser.parse
9
- after = Time.now
10
- result.each do |tree|
11
- puts tree.inspect
12
- puts
13
- end
14
- puts "parse duration: #{(after - before).to_f}s"
15
- rescue => e
16
- case e
17
- when DMark::Parser::ParserError
18
- line = data.lines[e.line_nr]
19
-
20
- puts "\e[31mError:\e[0m #{e.message}}"
21
- puts
22
- puts line
23
- puts "\e[31m" + ' ' * e.col_nr + '↑' + "\e[0m"
24
- exit 1
25
- else
26
- raise e
27
- end
28
- end