lib/asciidoctor/lexer.rb in asciidoctor-0.0.3 vs lib/asciidoctor/lexer.rb in asciidoctor-0.0.4

- old
+ new

@@ -6,10 +6,18 @@ # Public: Make sure the Lexer object doesn't get initialized. def initialize raise 'Au contraire, mon frere. No lexer instances will be running around.' end + def self.document_from_parent(parent) + if parent.is_a? Document + parent + else + parent.document + end + end + # Return the next block from the Reader. # # * Skip over blank lines to find the start of the next content block. # * Use defined regular expressions to determine the type of content block. # * Based on the type of content block, grab lines to the end of the block. @@ -29,11 +37,11 @@ # NOTE: This expression conditionally strips off the brackets from # [foo], though REGEXP[:anchor] won't actually match without # match[1] being bracketed, so the condition isn't necessary. anchor = match[1].match(/^\[(.*)\]/) ? $1 : match[1] # NOTE: Set @references['foo'] = '[foo]' - parent.document.references[anchor] = match[1] + document_from_parent(parent).references[anchor] = match[1] reader.get_line else anchor = nil end @@ -91,11 +99,12 @@ # buffer.pop # end block = Block.new(parent, :oblock, []) while buffer.has_lines? - block.blocks << next_block(buffer, block) + new_block = next_block(buffer, block) + block.blocks << new_block unless new_block.nil? end elsif list_type = [:olist, :colist].detect{|l| this_line.match( REGEXP[l] )} items = [] Asciidoctor.debug "Creating block of type: #{list_type}" @@ -104,11 +113,12 @@ item = ListItem.new reader.unshift match[2].lstrip.sub(/^\./, '\.') item_segment = Reader.new(list_item_segment(reader, :alt_ending => REGEXP[list_type])) while item_segment.has_lines? - item.blocks << next_block(item_segment, block) + new_block = next_block(item_segment, block) + item.blocks << new_block unless new_block.nil? end if item.blocks.any? && item.blocks.first.is_a?(Block) && (item.blocks.first.context == :paragraph || item.blocks.first.context == :literal) @@ -147,11 +157,12 @@ # workaround eg. git-config OPTIONS --get-colorbool reader.get_line if reader.has_lines? && reader.peek_line.strip.empty? dd_segment = Reader.new(list_item_segment(reader, :alt_ending => this_dlist)) while dd_segment.has_lines? - dd.blocks << next_block(dd_segment, block) + new_block = next_block(dd_segment, block) + dd.blocks << new_block unless new_block.nil? end if dd.blocks.any? && dd.blocks.first.is_a?(Block) && (dd.blocks.first.context == :paragraph || dd.blocks.first.context == :literal) @@ -183,12 +194,13 @@ elsif this_line.match( REGEXP[:quote] ) block = Block.new(parent, :quote) buffer = Reader.new(reader.grab_lines_until {|line| line.match( REGEXP[:quote] ) }) - while buffer.any? - block.blocks << next_block(reader, block) + while buffer.has_lines? + new_block = next_block(buffer, block) + block.blocks << new_block unless new_block.nil? end elsif this_line.match(REGEXP[:lit_blk]) # example is surrounded by '....' (4 or more '.' chars) lines buffer = reader.grab_lines_until {|line| line.match( REGEXP[:lit_blk] ) } @@ -376,11 +388,12 @@ reader.unshift match[2].lstrip.sub(/^\./, '\.') item_segment = Reader.new(list_item_segment(reader, :alt_ending => REGEXP[list_type])) # item_segment = list_item_segment(reader) while item_segment.has_lines? - list_item.blocks << next_block(item_segment, block) + new_block = next_block(item_segment, block) + list_item.blocks << new_block unless new_block.nil? end Asciidoctor.debug "\n\nlist_item has #{list_item.blocks.count} blocks, and first is a #{list_item.blocks.first.class} with context #{list_item.blocks.first.context rescue 'n/a'}\n\n" first_block = list_item.blocks.first @@ -439,11 +452,12 @@ Asciidoctor.debug "Created ListItem #{list_item} with match[2]: #{match[2]} and level: #{list_item.level}" lines.unshift match[2].lstrip.sub(/^\./, '\.') item_segment = list_item_segment(lines, :alt_ending => REGEXP[list_type], :list_level => level) while item_segment.any? - list_item.blocks << next_block(item_segment, block) + new_block = next_block(item_segment, block) + list_item.blocks << new_block unless new_block.nil? end first_block = list_item.blocks.first if first_block.is_a?(Block) && (first_block.context == :paragraph || first_block.context == :literal) @@ -561,18 +575,18 @@ end Asciidoctor.debug "#{__method__} -> Returning #{sect_name}, #{sect_level} (anchor: '#{sect_anchor || '<none>'}')" return [sect_name, sect_level, sect_anchor] end - # Private: Return the next section from the document. + # Private: Return the next section from the Reader. # # Examples # # source # => "GREETINGS\n---------\nThis is my doc.\n\nSALUTATIONS\n-----------\nIt is awesome." # - # doc = Asciidoctor::Document.new(source) + # TODO: doc = Asciidoctor::Document.new(source) # # doc.next_section # ["GREETINGS", [:paragraph, "This is my doc."]] # # doc.next_section @@ -600,11 +614,11 @@ end end if !section.anchor.nil? anchor_id = section.anchor.match(/^\[(.*)\]/) ? $1 : section.anchor - parent.document.references[anchor_id] = section.anchor + document_from_parent(parent).references[anchor_id] = section.anchor section.anchor = anchor_id end # Grab all the lines that belong to this section section_lines = [] @@ -643,10 +657,11 @@ section_reader = Reader.new(section_lines) # Now parse section_lines into Blocks belonging to the current Section while section_reader.has_lines? section_reader.skip_blank - section << next_block(section_reader, section) if section_reader.has_lines? + new_block = next_block(section_reader, section) if section_reader.has_lines? + section << new_block unless new_block.nil? end section end