diff options
| author | Dan Allen <dan.j.allen@gmail.com> | 2013-08-28 04:23:09 -0600 |
|---|---|---|
| committer | Dan Allen <dan.j.allen@gmail.com> | 2013-08-28 04:23:09 -0600 |
| commit | 975b94b5100f1e11601ca33f1071233a1a231330 (patch) | |
| tree | 0dc22a428f3b1369f970ef452c658fbcea5a99b5 | |
| parent | b2d027a50c4c893e640654f4cfdc89a0ac954e40 (diff) | |
fix regression for multiple callouts on a single line
| -rwxr-xr-x | lib/asciidoctor.rb | 10 | ||||
| -rw-r--r-- | lib/asciidoctor/lexer.rb | 4 | ||||
| -rw-r--r-- | lib/asciidoctor/substituters.rb | 18 | ||||
| -rw-r--r-- | test/blocks_test.rb | 12 | ||||
| -rw-r--r-- | test/lists_test.rb | 22 |
5 files changed, 51 insertions, 15 deletions
diff --git a/lib/asciidoctor.rb b/lib/asciidoctor.rb index a76ef155..78794a50 100755 --- a/lib/asciidoctor.rb +++ b/lib/asciidoctor.rb @@ -340,12 +340,14 @@ module Asciidoctor :biblio_macro => /\\?\[\[\[([\w:][\w:.-]*?)\]\]\]/, # callout reference inside literal text - # <1> (optionally prefixed by //, # or ;; line comment chars) or <!--1--> (for XML-based languages) + # <1> (optionally prefixed by //, # or ;; line comment chars) + # <1> <2> (multiple callouts on one line) + # <!--1--> (for XML-based languages) # special characters are already be replaced at this point during render - :callout_render => /(?:(?:\/\/|#|;;) ?)?(\\)?<!?(--|)(\d+)\2>$/, + :callout_render => /(?:(?:\/\/|#|;;) ?)?(\\)?<!?(--|)(\d+)\2>(?=$| ?\\?<!?\2\d+\2>$)/, # ...but not while scanning - :callout_quick_scan => /(\\)?<!?(--|)(\d+)\2>$/, - :callout_scan => /(?:(?:\/\/|#|;;) ?)?(\\)?<!?(--|)(\d+)\2>$/, + :callout_quick_scan => /\\?<!?(--|)(\d+)\1>(?=$| ?\\?<!?\1\d+\1>$)/, + :callout_scan => /(?:(?:\/\/|#|;;) ?)?(\\)?<!?(--|)(\d+)\2>(?=$| ?\\?<!?\2\d+\2>$)/, # <1> Foo :colist => /^<?(\d+)>[[:blank:]]+(.*)/, diff --git a/lib/asciidoctor/lexer.rb b/lib/asciidoctor/lexer.rb index f27d7182..fc2ea47d 100644 --- a/lib/asciidoctor/lexer.rb +++ b/lib/asciidoctor/lexer.rb @@ -1026,8 +1026,8 @@ class Lexer text.scan(REGEXP[:callout_quick_scan]) { # alias match for Ruby 1.8.7 compat m = $~ - next if m[1] == '\\' - document.callouts.register(m[3]) + next if m[0][0..0] == '\\' + document.callouts.register(m[2]) } end diff --git a/lib/asciidoctor/substituters.rb b/lib/asciidoctor/substituters.rb index 248cd0b9..3abf5e7c 100644 --- a/lib/asciidoctor/substituters.rb +++ b/lib/asciidoctor/substituters.rb @@ -795,7 +795,7 @@ module Substituters m = $~ # honor the escape if m[1] == '\\' - next "<#{m[3]}>" + next m[0].sub('\\', '') end Inline.new(self, :callout, m[3], :id => @document.callouts.read_next_id).render } @@ -957,15 +957,14 @@ module Substituters # extract callout marks, indexed by line number source = source.split(EOL).map {|line| lineno = lineno + 1 - line.sub(REGEXP[:callout_scan]) { + line.gsub(REGEXP[:callout_scan]) { # alias match for Ruby 1.8.7 compat m = $~ # honor the escape - # FIXME this does not put back the optional leading comment chars if m[1] == '\\' - "<#{m[3]}>" + m[0].sub('\\', '') else - callout_marks[lineno] = m[3] + (callout_marks[lineno] ||= []) << m[3] nil end } @@ -996,8 +995,13 @@ module Substituters lineno = 0 result.split(EOL).map {|line| lineno = lineno + 1 - if (conum = callout_marks.delete(lineno)) - %(#{line}#{Inline.new(self, :callout, conum, :id => @document.callouts.read_next_id).render}) + if (conums = callout_marks.delete(lineno)) + if conums.size == 1 + %(#{line}#{Inline.new(self, :callout, conums.first, :id => @document.callouts.read_next_id).render }) + else + conums_markup = conums.map {|conum| Inline.new(self, :callout, conum, :id => @document.callouts.read_next_id).render } * ' ' + %(#{line}#{conums_markup}) + end else line end diff --git a/test/blocks_test.rb b/test/blocks_test.rb index 69f2e8c3..1dbefaeb 100644 --- a/test/blocks_test.rb +++ b/test/blocks_test.rb @@ -1620,7 +1620,7 @@ html = CodeRay.scan("puts 'Hello, world!'", :ruby).div(:line_numbers => :table) assert_match(/\.CodeRay \{/, output) end - test 'wip should replace callout marks if source-highlighter attribute is coderay' do + test 'should replace callout marks but not highlight them if source-highlighter attribute is coderay' do input = <<-EOS :source-highlighter: coderay @@ -1629,13 +1629,21 @@ html = CodeRay.scan("puts 'Hello, world!'", :ruby).div(:line_numbers => :table) require 'coderay' # <1> html = CodeRay.scan("puts 'Hello, world!'", :ruby).div(:line_numbers => :table) # <2> +puts html # <3> <4> +exit 0 # <5><6> ---- <1> Load library <2> Highlight source +<3> Print to stdout +<4> Redirect to a file to capture output +<5> Exit program +<6> Reports success EOS output = render_embedded_string input, :safe => Asciidoctor::SafeMode::SAFE, :linkcss_default => true assert_match(/ <b>\(1\)<\/b>$/, output) - assert_match(/ <b>\(2\)<\/b><\/code>/, output) + assert_match(/ <b>\(2\)<\/b>$/, output) + assert_match(/ <b>\(3\)<\/b> <b>\(4\)<\/b>$/, output) + assert_match(/ <b>\(5\)<\/b> <b>\(6\)<\/b><\/code>/, output) end test 'should link to CodeRay stylesheet if source-highlighter is coderay and linkcss is set' do diff --git a/test/lists_test.rb b/test/lists_test.rb index 16436437..5f9fb8ee 100644 --- a/test/lists_test.rb +++ b/test/lists_test.rb @@ -3757,6 +3757,28 @@ puts "The syntax <1> at the end of the line makes a code callout" assert_xpath '//b', output, 0 end + test 'should allow multiple callouts on the same line' do + input = <<-EOS +[source, ruby] +---- +require 'asciidoctor' <1> +doc = Asciidoctor.load('Hello, World!') # <2> <3> +puts doc.render <4><5> +exit 0 +---- +<1> Require library +<2> Load document from String +<3> Uses default backend and doctype +<4> Renders document to String +<5> Prints output to stdout + EOS + output = render_embedded_string input + assert_xpath '//code/b', output, 5 + assert_match(/ <b>\(1\)<\/b>$/, output) + assert_match(/ <b>\(2\)<\/b> <b>\(3\)<\/b>$/, output) + assert_match(/ <b>\(4\)<\/b><b>\(5\)<\/b>$/, output) + end + test 'should allow XML comment-style callouts' do input = <<-EOS [source, xml] |
