commonmarker 1.0.4-x86_64-darwin → 1.1.1-x86_64-darwin

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 3f8bdb0d1594193853b5e1a7f5a160ead547498fe468efb9a3db6cad4cab8911
4
- data.tar.gz: 1f10f7715d8362c1f55a9e7f487879dd59465f5bae50c875dc22eeefbc1a30a1
3
+ metadata.gz: f563c7b91449cf84465a9b93cc3dacd699574c44f54e6e4b3e570a4e59a48907
4
+ data.tar.gz: 60f6d1c6507343e1e282d77adfe0ba49a04ba477453468b5904aef9641f3721a
5
5
  SHA512:
6
- metadata.gz: 80ad543e3c9c49e3237ecf4af565d3d8d4b8d7642f54cea517ae945f97a2a492a332c3e09fbbb498925254c343a2ca57c27c5800dc2f48728da211798f87aeac
7
- data.tar.gz: e036eff2ab43939a09cc81a19215778fb88c8a3a2e6ed04b7bf7aef67112a09fa846a89a943b06fe8928aaa727a97bd24649c771bd0dbff30860e3f325587c39
6
+ metadata.gz: 9cc2f94d6a65bcd8f0b9141e3c684df2dcd7c5bafc14e80062012205af0b155a09fc5b1b90b91b09d3bd665a4cb580e9d07f1d99576dc3cb187e12ffd008c744
7
+ data.tar.gz: eab789639e6977c3914092c92d3cb1c25453cc4df1ceaa55e5e6e7bc46587103633a9434e0c5db10b62da63e3c1a06bfb785da691ad5f7ff2c5cf6b109c86713
data/README.md CHANGED
@@ -1,8 +1,5 @@
1
1
  # Commonmarker
2
2
 
3
- > **Note**
4
- > This README refers to the behavior in the new 1.0.0.pre gem.
5
-
6
3
  Ruby wrapper for Rust's [comrak](https://github.com/kivikakk/comrak) crate.
7
4
 
8
5
  It passes all of the CommonMark test suite, and is therefore spec-complete. It also includes extensions to the CommonMark spec as documented in the [GitHub Flavored Markdown spec](http://github.github.com/gfm/), such as support for tables, strikethroughs, and autolinking.
@@ -34,10 +31,108 @@ require 'commonmarker'
34
31
  Commonmarker.to_html('"Hi *there*"', options: {
35
32
  parse: { smart: true }
36
33
  })
37
- # <p>“Hi <em>there</em>”</p>\n
34
+ # => <p>“Hi <em>there</em>”</p>\n
35
+ ```
36
+
37
+ (The second argument is optional--[see below](#options-and-plugins) for more information.)
38
+
39
+ ### Generating a document
40
+
41
+ You can also parse a string to receive a `:document` node. You can then print that node to HTML, iterate over the children, and do other fun node stuff. For example:
42
+
43
+ ```ruby
44
+ require 'commonmarker'
45
+
46
+ doc = Commonmarker.parse("*Hello* world", options: {
47
+ parse: { smart: true }
48
+ })
49
+ puts(doc.to_html) # => <p><em>Hello</em> world</p>\n
50
+
51
+ doc.walk do |node|
52
+ puts node.type # => [:document, :paragraph, :emph, :text, :text]
53
+ end
38
54
  ```
39
55
 
40
- The second argument is optional--[see below](#options) for more information.
56
+ (The second argument is optional--[see below](#options-and-plugins) for more information.)
57
+
58
+ When it comes to modifying the document, you can perform the following operations:
59
+
60
+ - `insert_before`
61
+ - `insert_after`
62
+ - `prepend_child`
63
+ - `append_child`
64
+ - `delete`
65
+
66
+ You can also get the source position of a node by calling `source_position`:
67
+
68
+ ```ruby
69
+ doc = Commonmarker.parse("*Hello* world")
70
+ puts doc.first_child.first_child.source_position
71
+ # => {:start_line=>1, :start_column=>1, :end_line=>1, :end_column=>7}
72
+ ```
73
+
74
+ You can also modify the following attributes:
75
+
76
+ - `url`
77
+ - `title`
78
+ - `header_level`
79
+ - `list_type`
80
+ - `list_start`
81
+ - `list_tight`
82
+ - `fence_info`
83
+
84
+ #### Example: Walking the AST
85
+
86
+ You can use `walk` or `each` to iterate over nodes:
87
+
88
+ - `walk` will iterate on a node and recursively iterate on a node's children.
89
+ - `each` will iterate on a node and its children, but no further.
90
+
91
+ ```ruby
92
+ require 'commonmarker'
93
+
94
+ # parse some string
95
+ doc = Commonmarker.parse("# The site\n\n [GitHub](https://www.github.com)")
96
+
97
+ # Walk tree and print out URLs for links
98
+ doc.walk do |node|
99
+ if node.type == :link
100
+ printf("URL = %s\n", node.url)
101
+ end
102
+ end
103
+ # => URL = https://www.github.com
104
+
105
+ # Transform links to regular text
106
+ doc.walk do |node|
107
+ if node.type == :link
108
+ node.insert_before(node.first_child)
109
+ node.delete
110
+ end
111
+ end
112
+ # => <h1><a href=\"#the-site\"></a>The site</h1>\n<p>GitHub</p>\n
113
+ ```
114
+
115
+ #### Example: Converting a document back into raw CommonMark
116
+
117
+ You can use `to_commonmark` on a node to render it as raw text:
118
+
119
+ ```ruby
120
+ require 'commonmarker'
121
+
122
+ # parse some string
123
+ doc = Commonmarker.parse("# The site\n\n [GitHub](https://www.github.com)")
124
+
125
+ # Transform links to regular text
126
+ doc.walk do |node|
127
+ if node.type == :link
128
+ node.insert_before(node.first_child)
129
+ node.delete
130
+ end
131
+ end
132
+
133
+ doc.to_commonmark
134
+ # => # The site\n\nGitHub\n
135
+ ```
41
136
 
42
137
  ## Options and plugins
43
138
 
@@ -56,21 +151,23 @@ Note that there is a distinction in comrak for "parse" options and "render" opti
56
151
 
57
152
  ### Parse options
58
153
 
59
- | Name | Description | Default |
60
- | --------------------- | ------------------------------------------------------------------------------------ | ------- |
61
- | `smart` | Punctuation (quotes, full-stops and hyphens) are converted into 'smart' punctuation. | `false` |
62
- | `default_info_string` | The default info string for fenced code blocks. | `""` |
154
+ | Name | Description | Default |
155
+ | --------------------- | ------------------------------------------------------------------------------------------------------------------------------------------ | ------- |
156
+ | `smart` | Punctuation (quotes, full-stops and hyphens) are converted into 'smart' punctuation. | `false` |
157
+ | `default_info_string` | The default info string for fenced code blocks. | `""` |
158
+ | `relaxed_autolinks` | Enable relaxing of the autolink extension parsing, allowing links to be recognized when in brackets, as well as permitting any url scheme. | `false` |
63
159
 
64
160
  ### Render options
65
161
 
66
- | Name | Description | Default |
67
- | ----------------- | ------------------------------------------------------------------------------------------------------ | ------- |
68
- | `hardbreaks` | [Soft line breaks](http://spec.commonmark.org/0.27/#soft-line-breaks) translate into hard line breaks. | `true` |
69
- | `github_pre_lang` | GitHub-style `<pre lang="xyz">` is used for fenced code blocks with info tags. | `true` |
70
- | `width` | The wrap column when outputting CommonMark. | `80` |
71
- | `unsafe` | Allow rendering of raw HTML and potentially dangerous links. | `false` |
72
- | `escape` | Escape raw HTML instead of clobbering it. | `false` |
73
- | `sourcepos` | Include source position attribute in HTML and XML output. | `false` |
162
+ | Name | Description | Default |
163
+ | -------------------- | ------------------------------------------------------------------------------------------------------ | ------- |
164
+ | `hardbreaks` | [Soft line breaks](http://spec.commonmark.org/0.27/#soft-line-breaks) translate into hard line breaks. | `true` |
165
+ | `github_pre_lang` | GitHub-style `<pre lang="xyz">` is used for fenced code blocks with info tags. | `true` |
166
+ | `width` | The wrap column when outputting CommonMark. | `80` |
167
+ | `unsafe` | Allow rendering of raw HTML and potentially dangerous links. | `false` |
168
+ | `escape` | Escape raw HTML instead of clobbering it. | `false` |
169
+ | `sourcepos` | Include source position attribute in HTML and XML output. | `false` |
170
+ | `escaped_char_spans` | Wrap escaped characters in span tags | `true` |
74
171
 
75
172
  As well, there are several extensions which you can toggle in the same manner:
76
173
 
@@ -83,19 +180,21 @@ Commonmarker.to_html('"Hi *there*"', options: {
83
180
 
84
181
  ### Extension options
85
182
 
86
- | Name | Description | Default |
87
- | ------------------------ | ------------------------------------------------------------------------------------------------------------------- | ------- |
88
- | `strikethrough` | Enables the [strikethrough extension](https://github.github.com/gfm/#strikethrough-extension-) from the GFM spec. | `true` |
89
- | `tagfilter` | Enables the [tagfilter extension](https://github.github.com/gfm/#disallowed-raw-html-extension-) from the GFM spec. | `true` |
90
- | `table` | Enables the [table extension](https://github.github.com/gfm/#tables-extension-) from the GFM spec. | `true` |
91
- | `autolink` | Enables the [autolink extension](https://github.github.com/gfm/#autolinks-extension-) from the GFM spec. | `true` |
92
- | `tasklist` | Enables the [task list extension](https://github.github.com/gfm/#task-list-items-extension-) from the GFM spec. | `true` |
93
- | `superscript` | Enables the superscript Comrak extension. | `false` |
94
- | `header_ids` | Enables the header IDs Comrak extension. from the GFM spec. | `""` |
95
- | `footnotes` | Enables the footnotes extension per `cmark-gfm`. | `false` |
96
- | `description_lists` | Enables the description lists extension. | `false` |
97
- | `front_matter_delimiter` | Enables the front matter extension. | `""` |
98
- | `shortcodes` | Enables the shortcodes extension. | `true` |
183
+ | Name | Description | Default |
184
+ | --------------------------- | ------------------------------------------------------------------------------------------------------------------- | ------- |
185
+ | `strikethrough` | Enables the [strikethrough extension](https://github.github.com/gfm/#strikethrough-extension-) from the GFM spec. | `true` |
186
+ | `tagfilter` | Enables the [tagfilter extension](https://github.github.com/gfm/#disallowed-raw-html-extension-) from the GFM spec. | `true` |
187
+ | `table` | Enables the [table extension](https://github.github.com/gfm/#tables-extension-) from the GFM spec. | `true` |
188
+ | `autolink` | Enables the [autolink extension](https://github.github.com/gfm/#autolinks-extension-) from the GFM spec. | `true` |
189
+ | `tasklist` | Enables the [task list extension](https://github.github.com/gfm/#task-list-items-extension-) from the GFM spec. | `true` |
190
+ | `superscript` | Enables the superscript Comrak extension. | `false` |
191
+ | `header_ids` | Enables the header IDs Comrak extension. from the GFM spec. | `""` |
192
+ | `footnotes` | Enables the footnotes extension per `cmark-gfm`. | `false` |
193
+ | `description_lists` | Enables the description lists extension. | `false` |
194
+ | `front_matter_delimiter` | Enables the front matter extension. | `""` |
195
+ | `shortcodes` | Enables the shortcodes extension. | `true` |
196
+ | `multiline_block_quotes` | Enables the multiline block quotes extension. | `false` |
197
+ | `math_dollars`, `math_code` | Enables the math extension. | `false` |
99
198
 
100
199
  For more information on these options, see [the comrak documentation](https://github.com/kivikakk/comrak#usage).
101
200
 
@@ -205,26 +304,32 @@ If there were no errors, you're done! Otherwise, make sure to follow the comrak
205
304
 
206
305
  ## Benchmarks
207
306
 
208
- Some rough benchmarks:
209
-
210
307
  ```
211
- $ bundle exec rake benchmark
212
-
308
+ bundle exec rake benchmark
213
309
  input size = 11064832 bytes
214
310
 
311
+ ruby 3.3.0 (2023-12-25 revision 5124f9ac75) [arm64-darwin23]
215
312
  Warming up --------------------------------------
216
- redcarpet 2.000 i/100ms
217
- commonmarker with to_html
218
- 1.000 i/100ms
219
- kramdown 1.000 i/100ms
313
+ Markly.render_html 1.000 i/100ms
314
+ Markly::Node#to_html 1.000 i/100ms
315
+ Commonmarker.to_html 1.000 i/100ms
316
+ Commonmarker::Node.to_html
317
+ 1.000 i/100ms
318
+ Kramdown::Document#to_html
319
+ 1.000 i/100ms
220
320
  Calculating -------------------------------------
221
- redcarpet 22.317 4.5%) i/s - 112.000 in 5.036374s
222
- commonmarker with to_html
223
- 5.815 (± 0.0%) i/s - 30.000 in 5.168869s
224
- kramdown 0.327 (± 0.0%) i/s - 2.000 in 6.121486s
321
+ Markly.render_html 15.606 25.6%) i/s - 71.000 in 5.047132s
322
+ Markly::Node#to_html 15.692 (±25.5%) i/s - 72.000 in 5.095810s
323
+ Commonmarker.to_html 4.482 (± 0.0%) i/s - 23.000 in 5.137680s
324
+ Commonmarker::Node.to_html
325
+ 5.092 (±19.6%) i/s - 25.000 in 5.072220s
326
+ Kramdown::Document#to_html
327
+ 0.379 (± 0.0%) i/s - 2.000 in 5.277770s
225
328
 
226
329
  Comparison:
227
- redcarpet: 22.3 i/s
228
- commonmarker with to_html: 5.8 i/s - 3.84x (± 0.00) slower
229
- kramdown: 0.3 i/s - 68.30x (± 0.00) slower
330
+ Markly::Node#to_html: 15.7 i/s
331
+ Markly.render_html: 15.6 i/s - same-ish: difference falls within error
332
+ Commonmarker::Node.to_html: 5.1 i/s - 3.08x slower
333
+ Commonmarker.to_html: 4.5 i/s - 3.50x slower
334
+ Kramdown::Document#to_html: 0.4 i/s - 41.40x slower
230
335
  ```
@@ -8,6 +8,7 @@ module Commonmarker
8
8
  parse: {
9
9
  smart: false,
10
10
  default_info_string: "",
11
+ relaxed_autolinks: false,
11
12
  }.freeze,
12
13
  render: {
13
14
  hardbreaks: true,
@@ -16,6 +17,7 @@ module Commonmarker
16
17
  unsafe: false,
17
18
  escape: false,
18
19
  sourcepos: false,
20
+ escaped_char_spans: true,
19
21
  }.freeze,
20
22
  extension: {
21
23
  strikethrough: true,
@@ -29,6 +31,9 @@ module Commonmarker
29
31
  description_lists: false,
30
32
  front_matter_delimiter: "",
31
33
  shortcodes: true,
34
+ multiline_block_quotes: false,
35
+ math_dollars: false,
36
+ math_code: false,
32
37
  },
33
38
  format: [:html].freeze,
34
39
  }.freeze
@@ -0,0 +1,8 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Commonmarker
4
+ class Node
5
+ class Ast
6
+ end
7
+ end
8
+ end
@@ -0,0 +1,57 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "pp"
4
+
5
+ module Commonmarker
6
+ class Node
7
+ module Inspect
8
+ PP_INDENT_SIZE = 2
9
+
10
+ def inspect
11
+ PP.pp(self, +"", Float::INFINITY)
12
+ end
13
+
14
+ # @param printer [PrettyPrint] pp
15
+ def pretty_print(printer)
16
+ printer.group(PP_INDENT_SIZE, "#<#{self.class}(#{type}):", ">") do
17
+ printer.breakable
18
+
19
+ attrs = [
20
+ :source_position,
21
+ :string_content,
22
+ :url,
23
+ :title,
24
+ :header_level,
25
+ :list_type,
26
+ :list_start,
27
+ :list_tight,
28
+ :fence_info,
29
+ ].filter_map do |name|
30
+ [name, __send__(name)]
31
+ rescue StandardError
32
+ nil
33
+ end.compact
34
+
35
+ printer.seplist(attrs) do |name, value|
36
+ printer.text("#{name}=")
37
+ printer.pp(value)
38
+ end
39
+
40
+ if first_child
41
+ printer.breakable
42
+ printer.group(PP_INDENT_SIZE) do
43
+ children = []
44
+ node = first_child
45
+ while node
46
+ children << node
47
+ node = node.next_sibling
48
+ end
49
+ printer.text("children=")
50
+ printer.pp(children)
51
+ end
52
+ end
53
+ end
54
+ end
55
+ end
56
+ end
57
+ end
@@ -0,0 +1,65 @@
1
+ # frozen_string_literal: true
2
+
3
+ require "commonmarker/node/ast"
4
+ require "commonmarker/node/inspect"
5
+
6
+ module Commonmarker
7
+ class Node
8
+ include Enumerable
9
+ include Inspect
10
+
11
+ # Public: An iterator that "walks the tree," descending into children recursively.
12
+ #
13
+ # blk - A {Proc} representing the action to take for each child
14
+ def walk(&block)
15
+ return enum_for(:walk) unless block
16
+
17
+ yield self
18
+ each do |child|
19
+ child.walk(&block)
20
+ end
21
+ end
22
+
23
+ # Public: Iterate over the children (if any) of the current pointer.
24
+ def each
25
+ return enum_for(:each) unless block_given?
26
+
27
+ child = first_child
28
+ while child
29
+ next_child = child.next_sibling
30
+ yield child
31
+ child = next_child
32
+ end
33
+ end
34
+
35
+ # Public: Converts a node to an HTML string.
36
+ #
37
+ # options - A {Hash} of render, parse, and extension options to transform the text.
38
+ # plugins - A {Hash} of additional plugins.
39
+ #
40
+ # Returns a {String} of HTML.
41
+ def to_html(options: Commonmarker::Config::OPTIONS, plugins: Commonmarker::Config::PLUGINS)
42
+ raise TypeError, "options must be a Hash; got a #{options.class}!" unless options.is_a?(Hash)
43
+
44
+ opts = Config.process_options(options)
45
+ plugins = Config.process_plugins(plugins)
46
+
47
+ node_to_html(options: opts, plugins: plugins).force_encoding("utf-8")
48
+ end
49
+
50
+ # Public: Convert the node to a CommonMark string.
51
+ #
52
+ # options - A {Symbol} or {Array of Symbol}s indicating the render options
53
+ # plugins - A {Hash} of additional plugins.
54
+ #
55
+ # Returns a {String}.
56
+ def to_commonmark(options: Commonmarker::Config::OPTIONS, plugins: Commonmarker::Config::PLUGINS)
57
+ raise TypeError, "options must be a Hash; got a #{options.class}!" unless options.is_a?(Hash)
58
+
59
+ opts = Config.process_options(options)
60
+ plugins = Config.process_plugins(plugins)
61
+
62
+ node_to_commonmark(options: opts, plugins: plugins).force_encoding("utf-8")
63
+ end
64
+ end
65
+ end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Commonmarker
4
- VERSION = "1.0.4"
4
+ VERSION = "1.1.1"
5
5
  end
data/lib/commonmarker.rb CHANGED
@@ -3,12 +3,29 @@
3
3
  require_relative "commonmarker/extension"
4
4
 
5
5
  require "commonmarker/utils"
6
+ require "commonmarker/node"
6
7
  require "commonmarker/config"
7
8
  require "commonmarker/renderer"
8
9
  require "commonmarker/version"
9
10
 
10
11
  module Commonmarker
11
12
  class << self
13
+ # Public: Parses a CommonMark string into an HTML string.
14
+ #
15
+ # text - A {String} of text
16
+ # options - A {Hash} of render, parse, and extension options to transform the text.
17
+ #
18
+ # Returns the `parser` node.
19
+ def parse(text, options: Commonmarker::Config::OPTIONS)
20
+ raise TypeError, "text must be a String; got a #{text.class}!" unless text.is_a?(String)
21
+ raise TypeError, "text must be UTF-8 encoded; got #{text.encoding}!" unless text.encoding.name == "UTF-8"
22
+ raise TypeError, "options must be a Hash; got a #{options.class}!" unless options.is_a?(Hash)
23
+
24
+ opts = Config.process_options(options)
25
+
26
+ commonmark_parse(text, options: opts)
27
+ end
28
+
12
29
  # Public: Parses a CommonMark string into an HTML string.
13
30
  #
14
31
  # text - A {String} of text
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: commonmarker
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.4
4
+ version: 1.1.1
5
5
  platform: x86_64-darwin
6
6
  authors:
7
7
  - Garen Torikian
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: exe
11
11
  cert_chain: []
12
- date: 2024-01-03 00:00:00.000000000 Z
12
+ date: 2024-05-01 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: rake
@@ -55,6 +55,9 @@ files:
55
55
  - lib/commonmarker/config.rb
56
56
  - lib/commonmarker/constants.rb
57
57
  - lib/commonmarker/extension.rb
58
+ - lib/commonmarker/node.rb
59
+ - lib/commonmarker/node/ast.rb
60
+ - lib/commonmarker/node/inspect.rb
58
61
  - lib/commonmarker/renderer.rb
59
62
  - lib/commonmarker/utils.rb
60
63
  - lib/commonmarker/version.rb