Sha256: aa055d805d72ddfd64482250da74bf5e9d29345d6af85fbf28d00fe70d8a63f8
Contents?: true
Size: 1.72 KB
Versions: 1
Compression:
Stored size: 1.72 KB
Contents
require 'strscan' class Sapluuna class Parser CODE_OPEN = '<%\s*' CODE_CLOSE = '\s*%>' TEMPLATE_OPEN = '^\s*{{{[\t ]*' TEMPLATE_CLOSE = '\s*}}}\s*$' NEW_LINE = "\n" class ParserError < Error; end class UnterminatedBlock < ParserError; end def initialize @sc = StringScanner.new '' end def parse input level = 0 cfg = [] @sc.string = input loop do if @sc.scan_until Regexp.new(TEMPLATE_OPEN) cfg << [:template, get_labels, get_template(level)] else break end end @sc.string = '' # no need to keep it in memory cfg end private def get_labels labels = @sc.scan_until Regexp.new(NEW_LINE) labels.strip.split(/\s+/) end def re_combine *args re = args.map do |arg| '(?:%s)' % arg end.join('|') Regexp.new re end def clean_scan scan endstr = -(@sc.matched.size+1) scan[0..endstr] end def get_template level cfg = [] loop do scan = @sc.scan_until re_combine(CODE_OPEN, TEMPLATE_OPEN, TEMPLATE_CLOSE) raise UnterminatedBlock, "template at #{level}, #{@sc.pos} runs forever" unless scan cfg << [:cfg, clean_scan(scan)] case @sc.matched when Regexp.new(CODE_OPEN) scan = @sc.scan_until Regexp.new(CODE_CLOSE) raise UnterminatedBlock, "code at #{level}, #{@sc.pos} runs forever" unless scan cfg << [:code, clean_scan(scan)] when Regexp.new(TEMPLATE_OPEN) cfg << [:template, get_labels, get_template(level+1)] when Regexp.new(TEMPLATE_CLOSE) return cfg end end end end end
Version data entries
1 entries across 1 versions & 1 rubygems
Version | Path |
---|---|
sapluuna-0.1.4 | lib/sapluuna/parser.rb |