module Margin::Parser
Notes:
-
The parser requires a trailing newline at the end of the last item.
-
Per the spec: leading and trailing dashes, colons, asterisks, chevrons, underscores and whitespaces, as well as blank lines, are ignored.
Constants
- ANNOTATION_ONLY
- EMPTY_LINE
- IGNORED_CHARACTERS
- LINE_DECORATION
- TASK_START
Public Instance Methods
parse(text)
click to toggle source
# File lib/margin/parser.rb, line 137 def parse(text) s = StringScanner.new(text) lines = [] until s.eos? raw = s.scan_until(/\n/)&.chomp break if raw.nil? # probably should handle this with a custom error lines << Line.new(raw) unless raw.match? (/^#{IGNORED_CHARACTERS}*$/) end parse_items Item.root, lines end
parse_items(parent, lines)
click to toggle source
# File lib/margin/parser.rb, line 148 def parse_items(parent, lines) return parent if !lines.any? while this_line = lines.shift do this_item = nil # handle this line case this_line.type when :item, :task this_item = Item.from_line(this_line) parent.children << this_item when :annotation parent.annotations += this_line.annotations else raise TypeError, "Unknown line type: `#{this_line.type}`" end break if this_item.nil? break if lines.empty? # now look ahead to decide what to do next next_line = lines.first parse_items(this_item, lines) if next_line.offset > this_line.offset break if next_line.offset < this_line.offset end parent end