20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
|
# File 'lib/ext/mustache.rb', line 20
def scan_tags
start_of_line = @scanner.beginning_of_line?
pre_match_position = @scanner.pos
last_index = @result.length
return unless x = @scanner.scan(/([ \t]*)?#{Regexp.escape(otag)}/)
padding = @scanner[1] || ''
unless start_of_line
@result << [:static, padding] unless padding.empty?
pre_match_position += padding.length
padding = ''
end
current_ctag = self.ctag
type = @scanner.scan(/#|\^|\/|=|!|<|>|&|\{/)
@scanner.skip(/\s*/)
if ANY_CONTENT.include?(type)
r = /\s*#{regexp(type)}?#{regexp(current_ctag)}/
content = scan_until_exclusive(r)
else
content = @scanner.scan(ALLOWED_CONTENT)
end
error "Illegal content in tag" if content.empty?
fetch = [:mustache, :fetch, content.split('.')]
prev = @result
case type
when '#'
block = [:multi]
@result << [:mustache, :section, fetch, block]
@sections << [content, position, @result]
@result = block
when '^'
block = [:multi]
@result << [:mustache, :inverted_section, fetch, block]
@sections << [content, position, @result]
@result = block
when '/'
section, pos, result = @sections.pop
raw = @scanner.pre_match[pos[3]...pre_match_position] + padding
(@result = result).last << raw << [self.otag, self.ctag]
if section.nil?
error "Closing unopened #{content.inspect}"
elsif section != content
error "Unclosed section #{section.inspect}", pos
end
when '!'
when '='
self.otag, self.ctag = content.split(' ', 2)
when '>'
@result << [:mustache, :partial, content, padding]
when '<'
@result << [:mustache, :routes, content, padding]
when '{', '&'
type = "}" if type == "{"
@result << [:mustache, :utag, fetch]
else
@result << [:mustache, :etag, fetch]
end
@scanner.skip(/\s+/)
@scanner.skip(regexp(type)) if type
unless close = @scanner.scan(regexp(current_ctag))
error "Unclosed tag"
end
if start_of_line && !@scanner.eos?
if @scanner.peek(2) =~ /\r?\n/ && SKIP_WHITESPACE.include?(type)
@scanner.skip(/\r?\n/)
else
prev.insert(last_index, [:static, padding]) unless padding.empty?
end
end
@sections.last[1] << @scanner.pos unless @sections.empty?
return unless @result == [:multi]
end
|