bkerley-radius 0.6.1

Sign up to get free protection for your applications and to get access to all the features.
data/Rakefile ADDED
@@ -0,0 +1,33 @@
1
+ %w[rubygems rake rake/clean fileutils newgem rubigen].each { |f| require f }
2
+ require File.dirname(__FILE__) + '/lib/radius'
3
+
4
+ # Generate all the Rake tasks
5
+ # Run 'rake -T' to see list of generated tasks (from gem root directory)
6
+ $hoe = Hoe.new('radius', Radius::VERSION) do |p|
7
+ p.developer('John W. Long', 'me@johnwlong.com')
8
+ p.author = [
9
+ "John W. Long (me@johnwlong.com)",
10
+ "David Chelimsky (dchelimsky@gmail.com)",
11
+ "Bryce Kerley (bkerley@brycekerley.net)"
12
+ ]
13
+ p.changes = p.paragraphs_of("CHANGELOG", 1..2).join("\n\n")
14
+ p.rubyforge_name = p.name # TODO this is default value
15
+ # p.extra_deps = [
16
+ # ['activesupport','>= 2.0.2'],
17
+ # ]
18
+ p.extra_dev_deps = [
19
+ ['newgem', ">= #{::Newgem::VERSION}"]
20
+ ]
21
+
22
+ p.clean_globs |= %w[**/.DS_Store tmp *.log]
23
+ path = (p.rubyforge_name == p.name) ? p.rubyforge_name : "\#{p.rubyforge_name}/\#{p.name}"
24
+ p.remote_rdoc_dir = File.join(path.gsub(/^#{p.rubyforge_name}\/?/,''), 'rdoc')
25
+ p.rsync_args = '-av --delete --ignore-errors'
26
+ p.test_globs = "test/**/*_test.rb"
27
+ end
28
+
29
+ require 'newgem/tasks' # load /tasks/*.rake
30
+ Dir['tasks/**/*.rake'].each { |t| load t }
31
+
32
+ # TODO - want other tests/tasks run by default? Add them to the list
33
+ # task :default => [:spec, :features]
data/lib/radius.rb ADDED
@@ -0,0 +1,7 @@
1
+ dir = File.join(File.dirname(__FILE__), 'radius')
2
+ require_files = %w{error tagdefs dostruct tagbinding context parsetag parser/scan parser util}
3
+ require_files.each {|f| require File.join(dir, f)}
4
+
5
+ module Radius
6
+ VERSION = '0.6.1'
7
+ end
@@ -0,0 +1,139 @@
1
+ module Radius
2
+ #
3
+ # A context contains the tag definitions which are available for use in a template.
4
+ # See the QUICKSTART[link:files/QUICKSTART.html] for a detailed explaination its
5
+ # usage.
6
+ #
7
+ class Context
8
+ # A hash of tag definition blocks that define tags accessible on a Context.
9
+ attr_accessor :definitions # :nodoc:
10
+ attr_accessor :globals # :nodoc:
11
+
12
+ # Creates a new Context object.
13
+ def initialize(&block)
14
+ @definitions = {}
15
+ @tag_binding_stack = []
16
+ @globals = DelegatingOpenStruct.new
17
+ with(&block) if block_given?
18
+ end
19
+
20
+ # Yeild an instance of self for tag definitions:
21
+ #
22
+ # context.with do |c|
23
+ # c.define_tag 'test' do
24
+ # 'test'
25
+ # end
26
+ # end
27
+ #
28
+ def with
29
+ yield self
30
+ self
31
+ end
32
+
33
+ # Creates a tag definition on a context. Several options are available to you
34
+ # when creating a tag:
35
+ #
36
+ # +for+:: Specifies an object that the tag is in reference to. This is
37
+ # applicable when a block is not passed to the tag, or when the
38
+ # +expose+ option is also used.
39
+ #
40
+ # +expose+:: Specifies that child tags should be set for each of the methods
41
+ # contained in this option. May be either a single symbol/string or
42
+ # an array of symbols/strings.
43
+ #
44
+ # +attributes+:: Specifies whether or not attributes should be exposed
45
+ # automatically. Useful for ActiveRecord objects. Boolean. Defaults
46
+ # to +true+.
47
+ #
48
+ def define_tag(name, options = {}, &block)
49
+ type = Util.impartial_hash_delete(options, :type).to_s
50
+ klass = Util.constantize('Radius::TagDefinitions::' + Util.camelize(type) + 'TagFactory') rescue raise(ArgumentError.new("Undefined type `#{type}' in options hash"))
51
+ klass.new(self).define_tag(name, options, &block)
52
+ end
53
+
54
+ # Returns the value of a rendered tag. Used internally by Parser#parse.
55
+ def render_tag(name, attributes = {}, &block)
56
+ if name =~ /^(.+?):(.+)$/
57
+ render_tag($1) { render_tag($2, attributes, &block) }
58
+ else
59
+ tag_definition_block = @definitions[qualified_tag_name(name.to_s)]
60
+ if tag_definition_block
61
+ stack(name, attributes, block) do |tag|
62
+ tag_definition_block.call(tag).to_s
63
+ end
64
+ else
65
+ tag_missing(name, attributes, &block)
66
+ end
67
+ end
68
+ end
69
+
70
+ # Like method_missing for objects, but fired when a tag is undefined.
71
+ # Override in your own Context to change what happens when a tag is
72
+ # undefined. By default this method raises an UndefinedTagError.
73
+ def tag_missing(name, attributes, &block)
74
+ raise UndefinedTagError.new(name)
75
+ end
76
+
77
+ # Returns the state of the current render stack. Useful from inside
78
+ # a tag definition. Normally just use TagBinding#nesting.
79
+ def current_nesting
80
+ @tag_binding_stack.collect { |tag| tag.name }.join(':')
81
+ end
82
+
83
+ private
84
+
85
+ # A convienence method for managing the various parts of the
86
+ # tag binding stack.
87
+ def stack(name, attributes, block)
88
+ previous = @tag_binding_stack.last
89
+ previous_locals = previous.nil? ? @globals : previous.locals
90
+ locals = DelegatingOpenStruct.new(previous_locals)
91
+ binding = TagBinding.new(self, locals, name, attributes, block)
92
+ @tag_binding_stack.push(binding)
93
+ result = yield(binding)
94
+ @tag_binding_stack.pop
95
+ result
96
+ end
97
+
98
+ # Returns a fully qualified tag name based on state of the
99
+ # tag binding stack.
100
+ def qualified_tag_name(name)
101
+ nesting_parts = @tag_binding_stack.collect { |tag| tag.name }
102
+ nesting_parts << name unless nesting_parts.last == name
103
+ specific_name = nesting_parts.join(':') # specific_name always has the highest specificity
104
+ unless @definitions.has_key? specific_name
105
+ possible_matches = @definitions.keys.grep(/(^|:)#{name}$/)
106
+ specificity = possible_matches.inject({}) { |hash, tag| hash[numeric_specificity(tag, nesting_parts)] = tag; hash }
107
+ max = specificity.keys.max
108
+ if max != 0
109
+ specificity[max]
110
+ else
111
+ name
112
+ end
113
+ else
114
+ specific_name
115
+ end
116
+ end
117
+
118
+ # Returns the specificity for +tag_name+ at nesting defined
119
+ # by +nesting_parts+ as a number.
120
+ def numeric_specificity(tag_name, nesting_parts)
121
+ nesting_parts = nesting_parts.dup
122
+ name_parts = tag_name.split(':')
123
+ specificity = 0
124
+ value = 1
125
+ if nesting_parts.last == name_parts.last
126
+ while nesting_parts.size > 0
127
+ if nesting_parts.last == name_parts.last
128
+ specificity += value
129
+ name_parts.pop
130
+ end
131
+ nesting_parts.pop
132
+ value *= 0.1
133
+ end
134
+ specificity = 0 if (name_parts.size > 0)
135
+ end
136
+ specificity
137
+ end
138
+ end
139
+ end
@@ -0,0 +1,31 @@
1
+ module Radius
2
+ class DelegatingOpenStruct # :nodoc:
3
+ attr_accessor :object
4
+
5
+ def initialize(object = nil)
6
+ @object = object
7
+ @hash = {}
8
+ end
9
+
10
+ def method_missing(method, *args, &block)
11
+ symbol = (method.to_s =~ /^(.*?)=$/) ? $1.intern : method
12
+ if (0..1).include?(args.size)
13
+ if args.size == 1
14
+ @hash[symbol] = args.first
15
+ else
16
+ if @hash.has_key?(symbol)
17
+ @hash[symbol]
18
+ else
19
+ unless object.nil?
20
+ @object.send(method, *args, &block)
21
+ else
22
+ nil
23
+ end
24
+ end
25
+ end
26
+ else
27
+ super
28
+ end
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,43 @@
1
+ module Radius
2
+ # Abstract base class for all parsing errors.
3
+ class ParseError < StandardError
4
+ end
5
+
6
+ # Occurs when the Parser expects an end tag for one tag and finds the end tag for another.
7
+ class WrongEndTagError < ParseError
8
+ def initialize(expected_tag, got_tag, stack)
9
+ stack_message = " with stack #{stack.inspect}" if stack
10
+ super("wrong end tag `#{got_tag}' found for start tag `#{expected_tag}'#{stack_message}")
11
+ end
12
+ end
13
+
14
+ # Occurs when Parser cannot find an end tag for a given tag in a template or when
15
+ # tags are miss-matched in a template.
16
+ class MissingEndTagError < ParseError
17
+ # Create a new MissingEndTagError object for +tag_name+.
18
+ def initialize(tag_name, stack)
19
+ stack_message = " with stack #{stack.inspect}" if stack
20
+ super("end tag not found for start tag `#{tag_name}'#{stack_message}")
21
+ end
22
+ end
23
+
24
+ # Occurs when Context#render_tag cannot find the specified tag on a Context.
25
+ class UndefinedTagError < ParseError
26
+ # Create a new UndefinedTagError object for +tag_name+.
27
+ def initialize(tag_name)
28
+ super("undefined tag `#{tag_name}'")
29
+ end
30
+ end
31
+
32
+ class TastelessTagError < ParseError #:nodoc:
33
+ def initialize(tag, stack)
34
+ super("internal error with tasteless tag #{tag.inspect} and stack #{stack.inspect}")
35
+ end
36
+ end
37
+
38
+ class UndefinedFlavorError < ParseError #:nodoc:
39
+ def initialize(tag, stack)
40
+ super("internal error with unknown flavored tag #{tag.inspect} and stack #{stack.inspect}")
41
+ end
42
+ end
43
+ end
@@ -0,0 +1,65 @@
1
+ module Radius
2
+ #
3
+ # The Radius parser. Initialize a parser with a Context object that
4
+ # defines how tags should be expanded. See the QUICKSTART[link:files/QUICKSTART.html]
5
+ # for a detailed explaination of its usage.
6
+ #
7
+ class Parser
8
+ # The Context object used to expand template tags.
9
+ attr_accessor :context
10
+
11
+ # The string that prefixes all tags that are expanded by a parser
12
+ # (the part in the tag name before the first colon).
13
+ attr_accessor :tag_prefix
14
+
15
+ # Creates a new parser object initialized with a Context.
16
+ def initialize(context = Context.new, options = {})
17
+ if context.kind_of?(Hash) and options.empty?
18
+ options = context
19
+ context = options[:context] || options['context'] || Context.new
20
+ end
21
+ options = Util.symbolize_keys(options)
22
+ @context = context
23
+ @tag_prefix = options[:tag_prefix]
24
+ end
25
+
26
+ # Parses string for tags, expands them, and returns the result.
27
+ def parse(string)
28
+ @stack = [ParseContainerTag.new { |t| t.contents.to_s }]
29
+ tokenize(string)
30
+ stack_up
31
+ @stack.last.to_s
32
+ end
33
+
34
+ protected
35
+ # Convert the string into a list of text blocks and scanners (tokens)
36
+ def tokenize(string)
37
+ @tokens = Scanner::operate(tag_prefix, string)
38
+ end
39
+
40
+ def stack_up
41
+ @tokens.each do |t|
42
+ if t.is_a? String
43
+ @stack.last.contents << t
44
+ next
45
+ end
46
+ case t[:flavor]
47
+ when :open
48
+ @stack.push(ParseContainerTag.new(t[:name], t[:attrs]))
49
+ when :self
50
+ @stack.last.contents << ParseTag.new {@context.render_tag(t[:name], t[:attrs])}
51
+ when :close
52
+ popped = @stack.pop
53
+ raise WrongEndTagError.new(popped.name, t[:name], @stack) if popped.name != t[:name]
54
+ popped.on_parse { |b| @context.render_tag(popped.name, popped.attributes) { b.contents.to_s } }
55
+ @stack.last.contents << popped
56
+ when :tasteless
57
+ raise TastelessTagError.new(t, @stack)
58
+ else
59
+ raise UndefinedFlavorError.new(t, @stack)
60
+ end
61
+ end
62
+ raise MissingEndTagError.new(@stack.last.name, @stack) if @stack.length != 1
63
+ end
64
+ end
65
+ end
@@ -0,0 +1,688 @@
1
+ # line 1 "scan.rl"
2
+ # line 82 "scan.rl"
3
+
4
+
5
+ module Radius
6
+ class Scanner
7
+ def self.operate(prefix, data)
8
+ buf = ""
9
+ csel = ""
10
+ @prematch = ''
11
+ @starttag = nil
12
+ @attrs = {}
13
+ @flavor = :tasteless
14
+ @cursor = 0
15
+ @tagstart = 0
16
+ @nodes = ['']
17
+ remainder = data.dup
18
+
19
+ until remainder.length == 0
20
+ p = perform_parse(prefix, remainder)
21
+ remainder = remainder[p..-1]
22
+ end
23
+
24
+ return @nodes
25
+ end
26
+
27
+ private
28
+ def self.perform_parse(prefix, data)
29
+ stack = []
30
+ p = 0
31
+ ts = 0
32
+ te = 0
33
+ act = 0
34
+ eof = data.length
35
+
36
+ @prefix = prefix
37
+
38
+ # line 39 "scan.rb"
39
+ class << self
40
+ attr_accessor :_parser_actions
41
+ private :_parser_actions, :_parser_actions=
42
+ end
43
+ self._parser_actions = [
44
+ 0, 1, 0, 1, 1, 1, 2, 1,
45
+ 3, 1, 4, 1, 5, 1, 6, 1,
46
+ 7, 1, 8, 1, 9, 1, 13, 1,
47
+ 14, 1, 18, 1, 20, 1, 21, 1,
48
+ 22, 2, 4, 5, 2, 5, 6, 2,
49
+ 8, 4, 2, 8, 9, 2, 9, 8,
50
+ 2, 10, 19, 2, 11, 19, 2, 12,
51
+ 19, 2, 15, 16, 2, 15, 17, 3,
52
+ 4, 5, 6, 3, 8, 4, 5, 3,
53
+ 15, 5, 16, 4, 8, 4, 5, 6,
54
+ 4, 15, 4, 5, 16, 5, 15, 8,
55
+ 4, 5, 16
56
+ ]
57
+
58
+ class << self
59
+ attr_accessor :_parser_key_offsets
60
+ private :_parser_key_offsets, :_parser_key_offsets=
61
+ end
62
+ self._parser_key_offsets = [
63
+ 0, 0, 11, 21, 34, 47, 61, 65,
64
+ 70, 72, 74, 87, 100, 101, 103, 118,
65
+ 133, 149, 155, 161, 176, 179, 182, 185,
66
+ 200, 202, 204, 219, 235, 241, 247, 250,
67
+ 253, 269, 285, 302, 309, 315, 331, 335,
68
+ 351, 366, 369, 371, 381, 392, 402, 416,
69
+ 420, 420, 421, 430, 430, 430, 432, 434,
70
+ 437, 440, 442, 444
71
+ ]
72
+
73
+ class << self
74
+ attr_accessor :_parser_trans_keys
75
+ private :_parser_trans_keys, :_parser_trans_keys=
76
+ end
77
+ self._parser_trans_keys = [
78
+ 58, 63, 95, 45, 46, 48, 57, 65,
79
+ 90, 97, 122, 63, 95, 45, 46, 48,
80
+ 58, 65, 90, 97, 122, 32, 47, 62,
81
+ 63, 95, 9, 13, 45, 58, 65, 90,
82
+ 97, 122, 32, 47, 62, 63, 95, 9,
83
+ 13, 45, 58, 65, 90, 97, 122, 32,
84
+ 61, 63, 95, 9, 13, 45, 46, 48,
85
+ 58, 65, 90, 97, 122, 32, 61, 9,
86
+ 13, 32, 34, 39, 9, 13, 34, 92,
87
+ 34, 92, 32, 47, 62, 63, 95, 9,
88
+ 13, 45, 58, 65, 90, 97, 122, 32,
89
+ 47, 62, 63, 95, 9, 13, 45, 58,
90
+ 65, 90, 97, 122, 62, 34, 92, 32,
91
+ 34, 47, 62, 63, 92, 95, 9, 13,
92
+ 45, 58, 65, 90, 97, 122, 32, 34,
93
+ 47, 62, 63, 92, 95, 9, 13, 45,
94
+ 58, 65, 90, 97, 122, 32, 34, 61,
95
+ 63, 92, 95, 9, 13, 45, 46, 48,
96
+ 58, 65, 90, 97, 122, 32, 34, 61,
97
+ 92, 9, 13, 32, 34, 39, 92, 9,
98
+ 13, 32, 34, 47, 62, 63, 92, 95,
99
+ 9, 13, 45, 58, 65, 90, 97, 122,
100
+ 34, 62, 92, 34, 39, 92, 34, 39,
101
+ 92, 32, 39, 47, 62, 63, 92, 95,
102
+ 9, 13, 45, 58, 65, 90, 97, 122,
103
+ 39, 92, 39, 92, 32, 39, 47, 62,
104
+ 63, 92, 95, 9, 13, 45, 58, 65,
105
+ 90, 97, 122, 32, 39, 61, 63, 92,
106
+ 95, 9, 13, 45, 46, 48, 58, 65,
107
+ 90, 97, 122, 32, 39, 61, 92, 9,
108
+ 13, 32, 34, 39, 92, 9, 13, 34,
109
+ 39, 92, 34, 39, 92, 32, 34, 39,
110
+ 47, 62, 63, 92, 95, 9, 13, 45,
111
+ 58, 65, 90, 97, 122, 32, 34, 39,
112
+ 47, 62, 63, 92, 95, 9, 13, 45,
113
+ 58, 65, 90, 97, 122, 32, 34, 39,
114
+ 61, 63, 92, 95, 9, 13, 45, 46,
115
+ 48, 58, 65, 90, 97, 122, 32, 34,
116
+ 39, 61, 92, 9, 13, 32, 34, 39,
117
+ 92, 9, 13, 32, 34, 39, 47, 62,
118
+ 63, 92, 95, 9, 13, 45, 58, 65,
119
+ 90, 97, 122, 34, 39, 62, 92, 32,
120
+ 34, 39, 47, 62, 63, 92, 95, 9,
121
+ 13, 45, 58, 65, 90, 97, 122, 32,
122
+ 39, 47, 62, 63, 92, 95, 9, 13,
123
+ 45, 58, 65, 90, 97, 122, 39, 62,
124
+ 92, 39, 92, 63, 95, 45, 46, 48,
125
+ 57, 65, 90, 97, 122, 58, 63, 95,
126
+ 45, 46, 48, 57, 65, 90, 97, 122,
127
+ 63, 95, 45, 46, 48, 58, 65, 90,
128
+ 97, 122, 32, 62, 63, 95, 9, 13,
129
+ 45, 46, 48, 58, 65, 90, 97, 122,
130
+ 32, 62, 9, 13, 60, 47, 63, 95,
131
+ 45, 57, 65, 90, 97, 122, 34, 92,
132
+ 34, 92, 34, 39, 92, 34, 39, 92,
133
+ 39, 92, 39, 92, 0
134
+ ]
135
+
136
+ class << self
137
+ attr_accessor :_parser_single_lengths
138
+ private :_parser_single_lengths, :_parser_single_lengths=
139
+ end
140
+ self._parser_single_lengths = [
141
+ 0, 3, 2, 5, 5, 4, 2, 3,
142
+ 2, 2, 5, 5, 1, 2, 7, 7,
143
+ 6, 4, 4, 7, 3, 3, 3, 7,
144
+ 2, 2, 7, 6, 4, 4, 3, 3,
145
+ 8, 8, 7, 5, 4, 8, 4, 8,
146
+ 7, 3, 2, 2, 3, 2, 4, 2,
147
+ 0, 1, 3, 0, 0, 2, 2, 3,
148
+ 3, 2, 2, 0
149
+ ]
150
+
151
+ class << self
152
+ attr_accessor :_parser_range_lengths
153
+ private :_parser_range_lengths, :_parser_range_lengths=
154
+ end
155
+ self._parser_range_lengths = [
156
+ 0, 4, 4, 4, 4, 5, 1, 1,
157
+ 0, 0, 4, 4, 0, 0, 4, 4,
158
+ 5, 1, 1, 4, 0, 0, 0, 4,
159
+ 0, 0, 4, 5, 1, 1, 0, 0,
160
+ 4, 4, 5, 1, 1, 4, 0, 4,
161
+ 4, 0, 0, 4, 4, 4, 5, 1,
162
+ 0, 0, 3, 0, 0, 0, 0, 0,
163
+ 0, 0, 0, 0
164
+ ]
165
+
166
+ class << self
167
+ attr_accessor :_parser_index_offsets
168
+ private :_parser_index_offsets, :_parser_index_offsets=
169
+ end
170
+ self._parser_index_offsets = [
171
+ 0, 0, 8, 15, 25, 35, 45, 49,
172
+ 54, 57, 60, 70, 80, 82, 85, 97,
173
+ 109, 121, 127, 133, 145, 149, 153, 157,
174
+ 169, 172, 175, 187, 199, 205, 211, 215,
175
+ 219, 232, 245, 258, 265, 271, 284, 289,
176
+ 302, 314, 318, 321, 328, 336, 343, 353,
177
+ 357, 358, 360, 367, 368, 369, 372, 375,
178
+ 379, 383, 386, 389
179
+ ]
180
+
181
+ class << self
182
+ attr_accessor :_parser_indicies
183
+ private :_parser_indicies, :_parser_indicies=
184
+ end
185
+ self._parser_indicies = [
186
+ 2, 1, 1, 1, 1, 1, 1, 0,
187
+ 3, 3, 3, 3, 3, 3, 0, 4,
188
+ 6, 7, 5, 5, 4, 5, 5, 5,
189
+ 0, 8, 10, 11, 9, 9, 8, 9,
190
+ 9, 9, 0, 13, 15, 14, 14, 13,
191
+ 14, 14, 14, 14, 12, 16, 17, 16,
192
+ 12, 17, 18, 19, 17, 12, 21, 22,
193
+ 20, 24, 25, 23, 26, 28, 29, 27,
194
+ 27, 26, 27, 27, 27, 12, 30, 32,
195
+ 33, 31, 31, 30, 31, 31, 31, 12,
196
+ 34, 12, 35, 25, 23, 36, 24, 38,
197
+ 39, 37, 25, 37, 36, 37, 37, 37,
198
+ 23, 40, 24, 42, 43, 41, 25, 41,
199
+ 40, 41, 41, 41, 23, 44, 24, 46,
200
+ 45, 25, 45, 44, 45, 45, 45, 45,
201
+ 23, 47, 24, 48, 25, 47, 23, 48,
202
+ 49, 50, 25, 48, 23, 51, 21, 53,
203
+ 54, 52, 22, 52, 51, 52, 52, 52,
204
+ 20, 24, 55, 25, 23, 57, 58, 59,
205
+ 56, 61, 35, 62, 60, 64, 24, 66,
206
+ 67, 65, 68, 65, 64, 65, 65, 65,
207
+ 63, 24, 68, 63, 61, 68, 63, 69,
208
+ 24, 71, 72, 70, 68, 70, 69, 70,
209
+ 70, 70, 63, 73, 24, 75, 74, 68,
210
+ 74, 73, 74, 74, 74, 74, 63, 76,
211
+ 24, 77, 68, 76, 63, 77, 78, 79,
212
+ 68, 77, 63, 80, 58, 59, 56, 81,
213
+ 81, 62, 60, 82, 61, 35, 84, 85,
214
+ 83, 62, 83, 82, 83, 83, 83, 60,
215
+ 86, 61, 35, 88, 89, 87, 62, 87,
216
+ 86, 87, 87, 87, 60, 90, 61, 35,
217
+ 92, 91, 62, 91, 90, 91, 91, 91,
218
+ 91, 60, 93, 61, 35, 94, 62, 93,
219
+ 60, 94, 95, 96, 62, 94, 60, 97,
220
+ 80, 58, 99, 100, 98, 59, 98, 97,
221
+ 98, 98, 98, 56, 61, 35, 101, 62,
222
+ 60, 97, 57, 58, 99, 100, 98, 59,
223
+ 98, 97, 98, 98, 98, 56, 103, 21,
224
+ 105, 106, 104, 107, 104, 103, 104, 104,
225
+ 104, 102, 24, 108, 68, 63, 21, 107,
226
+ 102, 109, 109, 109, 109, 109, 109, 0,
227
+ 111, 110, 110, 110, 110, 110, 110, 0,
228
+ 112, 112, 112, 112, 112, 112, 0, 113,
229
+ 115, 114, 114, 113, 114, 114, 114, 114,
230
+ 0, 116, 117, 116, 0, 118, 120, 119,
231
+ 123, 122, 122, 122, 122, 122, 121, 124,
232
+ 125, 24, 25, 23, 24, 25, 23, 61,
233
+ 35, 62, 60, 61, 35, 62, 60, 24,
234
+ 68, 63, 24, 68, 63, 126, 0
235
+ ]
236
+
237
+ class << self
238
+ attr_accessor :_parser_trans_targs
239
+ private :_parser_trans_targs, :_parser_trans_targs=
240
+ end
241
+ self._parser_trans_targs = [
242
+ 49, 1, 2, 3, 4, 3, 12, 52,
243
+ 4, 5, 12, 52, 49, 6, 5, 7,
244
+ 6, 7, 8, 42, 9, 10, 13, 9,
245
+ 10, 13, 11, 5, 12, 52, 11, 5,
246
+ 12, 52, 51, 14, 15, 16, 20, 54,
247
+ 15, 16, 20, 54, 17, 16, 18, 17,
248
+ 18, 19, 21, 15, 16, 20, 54, 53,
249
+ 22, 23, 14, 31, 22, 23, 31, 24,
250
+ 26, 27, 41, 58, 25, 26, 27, 41,
251
+ 58, 28, 27, 29, 28, 29, 30, 40,
252
+ 23, 32, 33, 34, 38, 56, 33, 34,
253
+ 38, 56, 35, 34, 36, 35, 36, 37,
254
+ 39, 33, 34, 38, 56, 55, 24, 26,
255
+ 27, 41, 58, 25, 57, 44, 44, 45,
256
+ 46, 47, 46, 59, 47, 59, 0, 49,
257
+ 50, 49, 1, 43, 49, 49, 49
258
+ ]
259
+
260
+ class << self
261
+ attr_accessor :_parser_trans_actions
262
+ private :_parser_trans_actions, :_parser_trans_actions=
263
+ end
264
+ self._parser_trans_actions = [
265
+ 29, 0, 3, 5, 7, 0, 7, 7,
266
+ 0, 13, 0, 0, 31, 15, 0, 15,
267
+ 0, 0, 0, 0, 17, 42, 17, 0,
268
+ 19, 0, 9, 63, 33, 33, 0, 36,
269
+ 11, 11, 0, 19, 9, 63, 33, 80,
270
+ 0, 36, 11, 71, 15, 0, 15, 0,
271
+ 0, 19, 0, 39, 75, 67, 85, 57,
272
+ 17, 45, 42, 17, 0, 19, 0, 0,
273
+ 9, 63, 33, 80, 0, 0, 36, 11,
274
+ 71, 15, 0, 15, 0, 0, 0, 19,
275
+ 42, 19, 9, 63, 33, 80, 0, 36,
276
+ 11, 71, 15, 0, 15, 0, 0, 19,
277
+ 19, 39, 75, 67, 85, 57, 17, 39,
278
+ 75, 67, 85, 17, 57, 1, 0, 3,
279
+ 5, 7, 0, 7, 0, 0, 0, 25,
280
+ 60, 27, 1, 0, 51, 48, 54
281
+ ]
282
+
283
+ class << self
284
+ attr_accessor :_parser_to_state_actions
285
+ private :_parser_to_state_actions, :_parser_to_state_actions=
286
+ end
287
+ self._parser_to_state_actions = [
288
+ 0, 0, 0, 0, 0, 0, 0, 0,
289
+ 0, 0, 0, 0, 0, 0, 0, 0,
290
+ 0, 0, 0, 0, 0, 0, 0, 0,
291
+ 0, 0, 0, 0, 0, 0, 0, 0,
292
+ 0, 0, 0, 0, 0, 0, 0, 0,
293
+ 0, 0, 0, 0, 0, 0, 0, 0,
294
+ 21, 21, 0, 0, 0, 0, 0, 0,
295
+ 0, 0, 0, 0
296
+ ]
297
+
298
+ class << self
299
+ attr_accessor :_parser_from_state_actions
300
+ private :_parser_from_state_actions, :_parser_from_state_actions=
301
+ end
302
+ self._parser_from_state_actions = [
303
+ 0, 0, 0, 0, 0, 0, 0, 0,
304
+ 0, 0, 0, 0, 0, 0, 0, 0,
305
+ 0, 0, 0, 0, 0, 0, 0, 0,
306
+ 0, 0, 0, 0, 0, 0, 0, 0,
307
+ 0, 0, 0, 0, 0, 0, 0, 0,
308
+ 0, 0, 0, 0, 0, 0, 0, 0,
309
+ 0, 23, 0, 0, 0, 0, 0, 0,
310
+ 0, 0, 0, 0
311
+ ]
312
+
313
+ class << self
314
+ attr_accessor :_parser_eof_trans
315
+ private :_parser_eof_trans, :_parser_eof_trans=
316
+ end
317
+ self._parser_eof_trans = [
318
+ 0, 1, 1, 1, 1, 13, 13, 13,
319
+ 13, 13, 13, 13, 13, 13, 13, 13,
320
+ 13, 13, 13, 13, 13, 13, 13, 13,
321
+ 13, 13, 13, 13, 13, 13, 13, 13,
322
+ 13, 13, 13, 13, 13, 13, 13, 13,
323
+ 13, 13, 13, 1, 1, 1, 1, 1,
324
+ 0, 0, 122, 125, 126, 125, 126, 125,
325
+ 126, 125, 126, 127
326
+ ]
327
+
328
+ class << self
329
+ attr_accessor :parser_start
330
+ end
331
+ self.parser_start = 49;
332
+ class << self
333
+ attr_accessor :parser_first_final
334
+ end
335
+ self.parser_first_final = 49;
336
+ class << self
337
+ attr_accessor :parser_error
338
+ end
339
+ self.parser_error = 0;
340
+
341
+ class << self
342
+ attr_accessor :parser_en_Closeout
343
+ end
344
+ self.parser_en_Closeout = 48;
345
+ class << self
346
+ attr_accessor :parser_en_main
347
+ end
348
+ self.parser_en_main = 49;
349
+
350
+ # line 117 "scan.rl"
351
+
352
+ # line 353 "scan.rb"
353
+ begin
354
+ p ||= 0
355
+ pe ||= data.length
356
+ cs = parser_start
357
+ ts = nil
358
+ te = nil
359
+ act = 0
360
+ end
361
+ # line 118 "scan.rl"
362
+
363
+ # line 364 "scan.rb"
364
+ begin
365
+ _klen, _trans, _keys, _acts, _nacts = nil
366
+ _goto_level = 0
367
+ _resume = 10
368
+ _eof_trans = 15
369
+ _again = 20
370
+ _test_eof = 30
371
+ _out = 40
372
+ while true
373
+ _trigger_goto = false
374
+ if _goto_level <= 0
375
+ if p == pe
376
+ _goto_level = _test_eof
377
+ next
378
+ end
379
+ if cs == 0
380
+ _goto_level = _out
381
+ next
382
+ end
383
+ end
384
+ if _goto_level <= _resume
385
+ _acts = _parser_from_state_actions[cs]
386
+ _nacts = _parser_actions[_acts]
387
+ _acts += 1
388
+ while _nacts > 0
389
+ _nacts -= 1
390
+ _acts += 1
391
+ case _parser_actions[_acts - 1]
392
+ when 14 then
393
+ # line 1 "scan.rl"
394
+ begin
395
+ ts = p
396
+ end
397
+ # line 1 "scan.rl"
398
+ # line 399 "scan.rb"
399
+ end # from state action switch
400
+ end
401
+ if _trigger_goto
402
+ next
403
+ end
404
+ _keys = _parser_key_offsets[cs]
405
+ _trans = _parser_index_offsets[cs]
406
+ _klen = _parser_single_lengths[cs]
407
+ _break_match = false
408
+
409
+ begin
410
+ if _klen > 0
411
+ _lower = _keys
412
+ _upper = _keys + _klen - 1
413
+
414
+ loop do
415
+ break if _upper < _lower
416
+ _mid = _lower + ( (_upper - _lower) >> 1 )
417
+
418
+ if data[p] < _parser_trans_keys[_mid]
419
+ _upper = _mid - 1
420
+ elsif data[p] > _parser_trans_keys[_mid]
421
+ _lower = _mid + 1
422
+ else
423
+ _trans += (_mid - _keys)
424
+ _break_match = true
425
+ break
426
+ end
427
+ end # loop
428
+ break if _break_match
429
+ _keys += _klen
430
+ _trans += _klen
431
+ end
432
+ _klen = _parser_range_lengths[cs]
433
+ if _klen > 0
434
+ _lower = _keys
435
+ _upper = _keys + (_klen << 1) - 2
436
+ loop do
437
+ break if _upper < _lower
438
+ _mid = _lower + (((_upper-_lower) >> 1) & ~1)
439
+ if data[p] < _parser_trans_keys[_mid]
440
+ _upper = _mid - 2
441
+ elsif data[p] > _parser_trans_keys[_mid+1]
442
+ _lower = _mid + 2
443
+ else
444
+ _trans += ((_mid - _keys) >> 1)
445
+ _break_match = true
446
+ break
447
+ end
448
+ end # loop
449
+ break if _break_match
450
+ _trans += _klen
451
+ end
452
+ end while false
453
+ _trans = _parser_indicies[_trans]
454
+ end
455
+ if _goto_level <= _eof_trans
456
+ cs = _parser_trans_targs[_trans]
457
+ if _parser_trans_actions[_trans] != 0
458
+ _acts = _parser_trans_actions[_trans]
459
+ _nacts = _parser_actions[_acts]
460
+ _acts += 1
461
+ while _nacts > 0
462
+ _nacts -= 1
463
+ _acts += 1
464
+ case _parser_actions[_acts - 1]
465
+ when 0 then
466
+ # line 5 "scan.rl"
467
+ begin
468
+ mark_pfx = p end
469
+ # line 5 "scan.rl"
470
+ when 1 then
471
+ # line 6 "scan.rl"
472
+ begin
473
+
474
+ if data[mark_pfx..p-1] != @prefix
475
+ cs = 48;
476
+ end
477
+ end
478
+ # line 6 "scan.rl"
479
+ when 2 then
480
+ # line 11 "scan.rl"
481
+ begin
482
+ mark_stg = p end
483
+ # line 11 "scan.rl"
484
+ when 3 then
485
+ # line 12 "scan.rl"
486
+ begin
487
+ @starttag = data[mark_stg..p-1] end
488
+ # line 12 "scan.rl"
489
+ when 4 then
490
+ # line 13 "scan.rl"
491
+ begin
492
+ mark_attr = p end
493
+ # line 13 "scan.rl"
494
+ when 5 then
495
+ # line 14 "scan.rl"
496
+ begin
497
+
498
+ @attrs[@nat] = @vat
499
+ end
500
+ # line 14 "scan.rl"
501
+ when 6 then
502
+ # line 23 "scan.rl"
503
+ begin
504
+ mark_nat = p end
505
+ # line 23 "scan.rl"
506
+ when 7 then
507
+ # line 24 "scan.rl"
508
+ begin
509
+ @nat = data[mark_nat..p-1] end
510
+ # line 24 "scan.rl"
511
+ when 8 then
512
+ # line 25 "scan.rl"
513
+ begin
514
+ mark_vat = p end
515
+ # line 25 "scan.rl"
516
+ when 9 then
517
+ # line 26 "scan.rl"
518
+ begin
519
+ @vat = data[mark_vat..p-1] end
520
+ # line 26 "scan.rl"
521
+ when 10 then
522
+ # line 28 "scan.rl"
523
+ begin
524
+ @flavor = :open end
525
+ # line 28 "scan.rl"
526
+ when 11 then
527
+ # line 29 "scan.rl"
528
+ begin
529
+ @flavor = :self end
530
+ # line 29 "scan.rl"
531
+ when 12 then
532
+ # line 30 "scan.rl"
533
+ begin
534
+ @flavor = :close end
535
+ # line 30 "scan.rl"
536
+ when 15 then
537
+ # line 1 "scan.rl"
538
+ begin
539
+ te = p+1
540
+ end
541
+ # line 1 "scan.rl"
542
+ when 16 then
543
+ # line 68 "scan.rl"
544
+ begin
545
+ act = 1; end
546
+ # line 68 "scan.rl"
547
+ when 17 then
548
+ # line 77 "scan.rl"
549
+ begin
550
+ act = 2; end
551
+ # line 77 "scan.rl"
552
+ when 18 then
553
+ # line 77 "scan.rl"
554
+ begin
555
+ te = p+1
556
+ begin
557
+ @nodes.last << data[p]
558
+ @tagstart = p
559
+ end
560
+ end
561
+ # line 77 "scan.rl"
562
+ when 19 then
563
+ # line 68 "scan.rl"
564
+ begin
565
+ te = p
566
+ p = p - 1; begin
567
+ tag = {:prefix=>@prefix, :name=>@starttag, :flavor => @flavor, :attrs => @attrs}
568
+ @prefix = nil
569
+ @name = nil
570
+ @flavor = :tasteless
571
+ @attrs = {}
572
+ @nodes << tag << ''
573
+ begin
574
+ p += 1
575
+ _trigger_goto = true
576
+ _goto_level = _out
577
+ break
578
+ end
579
+
580
+ end
581
+ end
582
+ # line 68 "scan.rl"
583
+ when 20 then
584
+ # line 77 "scan.rl"
585
+ begin
586
+ te = p
587
+ p = p - 1; begin
588
+ @nodes.last << data[p]
589
+ @tagstart = p
590
+ end
591
+ end
592
+ # line 77 "scan.rl"
593
+ when 21 then
594
+ # line 77 "scan.rl"
595
+ begin
596
+ begin p = ((te))-1; end
597
+ begin
598
+ @nodes.last << data[p]
599
+ @tagstart = p
600
+ end
601
+ end
602
+ # line 77 "scan.rl"
603
+ when 22 then
604
+ # line 1 "scan.rl"
605
+ begin
606
+ case act
607
+ when 1 then
608
+ begin begin p = ((te))-1; end
609
+
610
+ tag = {:prefix=>@prefix, :name=>@starttag, :flavor => @flavor, :attrs => @attrs}
611
+ @prefix = nil
612
+ @name = nil
613
+ @flavor = :tasteless
614
+ @attrs = {}
615
+ @nodes << tag << ''
616
+ begin
617
+ p += 1
618
+ _trigger_goto = true
619
+ _goto_level = _out
620
+ break
621
+ end
622
+
623
+ end
624
+ when 2 then
625
+ begin begin p = ((te))-1; end
626
+
627
+ @nodes.last << data[p]
628
+ @tagstart = p
629
+ end
630
+ end
631
+ end
632
+ # line 1 "scan.rl"
633
+ # line 634 "scan.rb"
634
+ end # action switch
635
+ end
636
+ end
637
+ if _trigger_goto
638
+ next
639
+ end
640
+ end
641
+ if _goto_level <= _again
642
+ _acts = _parser_to_state_actions[cs]
643
+ _nacts = _parser_actions[_acts]
644
+ _acts += 1
645
+ while _nacts > 0
646
+ _nacts -= 1
647
+ _acts += 1
648
+ case _parser_actions[_acts - 1]
649
+ when 13 then
650
+ # line 1 "scan.rl"
651
+ begin
652
+ ts = nil; end
653
+ # line 1 "scan.rl"
654
+ # line 655 "scan.rb"
655
+ end # to state action switch
656
+ end
657
+ if _trigger_goto
658
+ next
659
+ end
660
+ if cs == 0
661
+ _goto_level = _out
662
+ next
663
+ end
664
+ p += 1
665
+ if p != pe
666
+ _goto_level = _resume
667
+ next
668
+ end
669
+ end
670
+ if _goto_level <= _test_eof
671
+ if p == eof
672
+ if _parser_eof_trans[cs] > 0
673
+ _trans = _parser_eof_trans[cs] - 1;
674
+ _goto_level = _eof_trans
675
+ next;
676
+ end
677
+ end
678
+ end
679
+ if _goto_level <= _out
680
+ break
681
+ end
682
+ end
683
+ end
684
+ # line 119 "scan.rl"
685
+ return p
686
+ end
687
+ end
688
+ end