treetop 1.4.15 → 1.5.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +15 -0
- data/README.md +1 -1
- data/Rakefile +0 -1
- data/lib/treetop/compiler/metagrammar.rb +223 -111
- data/lib/treetop/compiler/metagrammar.treetop +4 -4
- data/lib/treetop/compiler/node_classes/anything_symbol.rb +7 -3
- data/lib/treetop/compiler/node_classes/character_class.rb +2 -2
- data/lib/treetop/compiler/node_classes/choice.rb +3 -1
- data/lib/treetop/compiler/node_classes/parsing_rule.rb +4 -2
- data/lib/treetop/compiler/node_classes/terminal.rb +12 -6
- data/lib/treetop/runtime/compiled_parser.rb +9 -4
- data/lib/treetop/version.rb +2 -2
- data/spec/compiler/character_class_spec.rb +17 -17
- data/spec/compiler/choice_spec.rb +4 -4
- data/spec/compiler/not_predicate_spec.rb +2 -2
- data/spec/compiler/repeated_subrule_spec.rb +2 -2
- data/spec/compiler/terminal_spec.rb +44 -0
- data/spec/compiler/zero_or_more_spec.rb +1 -1
- data/spec/composition/b.treetop +2 -2
- data/spec/composition/grammar_composition_spec.rb +2 -2
- data/spec/runtime/compiled_parser_spec.rb +3 -3
- data/treetop.gemspec +24 -26
- metadata +27 -62
@@ -389,19 +389,19 @@ module Treetop
|
|
389
389
|
end
|
390
390
|
|
391
391
|
rule quoted_string
|
392
|
-
(single_quoted_string / double_quoted_string) {
|
392
|
+
qs:(single_quoted_string / double_quoted_string) insens:'i'? <Terminal> {
|
393
393
|
def string
|
394
|
-
|
394
|
+
qs.text_value
|
395
395
|
end
|
396
396
|
}
|
397
397
|
end
|
398
398
|
|
399
399
|
rule double_quoted_string
|
400
|
-
'"' string:(!'"' ("\\\\" / '\"' / .))* '"'
|
400
|
+
'"' string:(!'"' ("\\\\" / '\"' / .))* '"'
|
401
401
|
end
|
402
402
|
|
403
403
|
rule single_quoted_string
|
404
|
-
"'" string:(!"'" ("\\\\" / "\\'" / .))* "'"
|
404
|
+
"'" string:(!"'" ("\\\\" / "\\'" / .))* "'"
|
405
405
|
end
|
406
406
|
|
407
407
|
rule character_class
|
@@ -4,8 +4,12 @@ module Treetop
|
|
4
4
|
def compile(address, builder, parent_expression = nil)
|
5
5
|
super
|
6
6
|
builder.if__ "index < input_length" do
|
7
|
-
|
8
|
-
|
7
|
+
if address == 0 || decorated?
|
8
|
+
assign_result "instantiate_node(#{node_class_name},input, index...(index + 1))"
|
9
|
+
extend_result_with_inline_module
|
10
|
+
else
|
11
|
+
assign_lazily_instantiated_node
|
12
|
+
end
|
9
13
|
builder << "@index += 1"
|
10
14
|
end
|
11
15
|
builder.else_ do
|
@@ -15,4 +19,4 @@ module Treetop
|
|
15
19
|
end
|
16
20
|
end
|
17
21
|
end
|
18
|
-
end
|
22
|
+
end
|
@@ -3,8 +3,8 @@ module Treetop
|
|
3
3
|
class CharacterClass < AtomicExpression
|
4
4
|
def compile(address, builder, parent_expression = nil)
|
5
5
|
super
|
6
|
-
|
7
|
-
builder.if__ "has_terminal?(#{grounded_regexp(text_value)},
|
6
|
+
|
7
|
+
builder.if__ "has_terminal?(@regexps[gr = #{grounded_regexp(text_value)}] ||= Regexp.new(gr), :regexp, index)" do
|
8
8
|
if address == 0 || decorated?
|
9
9
|
assign_result "instantiate_node(#{node_class_name},input, index...(index + 1))"
|
10
10
|
extend_result_with_inline_module
|
@@ -13,6 +13,8 @@ module Treetop
|
|
13
13
|
obtain_new_subexpression_address
|
14
14
|
alternatives.first.compile(subexpression_address, builder)
|
15
15
|
builder.if__ subexpression_success? do
|
16
|
+
# Undo lazy instantiation:
|
17
|
+
builder << "#{subexpression_result_var} = SyntaxNode.new(input, (index-1)...index) if #{subexpression_result_var} == true"
|
16
18
|
assign_result subexpression_result_var
|
17
19
|
extend_result_with_declared_module
|
18
20
|
extend_result_with_inline_module
|
@@ -28,4 +30,4 @@ module Treetop
|
|
28
30
|
end
|
29
31
|
end
|
30
32
|
end
|
31
|
-
end
|
33
|
+
end
|
@@ -33,9 +33,11 @@ module Treetop
|
|
33
33
|
|
34
34
|
def generate_cache_lookup(builder)
|
35
35
|
builder.if_ "node_cache[:#{name}].has_key?(index)" do
|
36
|
-
|
36
|
+
cache_address = "node_cache[:#{name}][index]"
|
37
|
+
builder.assign 'cached', cache_address
|
37
38
|
builder.if_ "cached" do
|
38
|
-
|
39
|
+
# Handle lazily instantiated nodes:
|
40
|
+
builder << "#{cache_address} = cached = SyntaxNode.new(input, index...(index + 1)) if cached == true"
|
39
41
|
builder << '@index = cached.interval.end'
|
40
42
|
end
|
41
43
|
builder << 'return cached'
|
@@ -3,15 +3,21 @@ module Treetop
|
|
3
3
|
class Terminal < AtomicExpression
|
4
4
|
def compile(address, builder, parent_expression = nil)
|
5
5
|
super
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
6
|
+
insensitive = insens.text_value.length > 0
|
7
|
+
str = insensitive ? string.downcase : string
|
8
|
+
string_length = eval(str).length
|
9
|
+
|
10
|
+
builder.if__ "has_terminal?(#{str}, #{insensitive ? ':insens' : false}, index)" do
|
11
|
+
if address == 0 || decorated? || string_length > 1
|
12
|
+
assign_result "instantiate_node(#{node_class_name},input, index...(index + #{string_length}))"
|
13
|
+
extend_result_with_inline_module
|
14
|
+
else
|
15
|
+
assign_lazily_instantiated_node
|
16
|
+
end
|
11
17
|
builder << "@index += #{string_length}"
|
12
18
|
end
|
13
19
|
builder.else_ do
|
14
|
-
builder << "terminal_parse_failure(#{
|
20
|
+
builder << "terminal_parse_failure(#{str})"
|
15
21
|
assign_result 'nil'
|
16
22
|
end
|
17
23
|
end
|
@@ -92,12 +92,17 @@ module Treetop
|
|
92
92
|
end
|
93
93
|
end
|
94
94
|
|
95
|
-
def has_terminal?(terminal,
|
96
|
-
|
95
|
+
def has_terminal?(terminal, mode, index)
|
96
|
+
case mode
|
97
|
+
when :regexp # A Regexp has been passed in, probably a character class
|
98
|
+
input.index(terminal, index) == index
|
99
|
+
when false # The terminal is a string which must match exactly
|
100
|
+
input[index, terminal.size] == terminal
|
101
|
+
when :insens # The terminal is a downcased string which must match input downcased
|
102
|
+
input[index, terminal.size].downcase == terminal
|
103
|
+
when true # Only occurs with old compiled grammars, for character classes
|
97
104
|
rx = @regexps[terminal] ||= Regexp.new(terminal)
|
98
105
|
input.index(rx, index) == index
|
99
|
-
else
|
100
|
-
input[index, terminal.size] == terminal
|
101
106
|
end
|
102
107
|
end
|
103
108
|
|
data/lib/treetop/version.rb
CHANGED
@@ -228,19 +228,19 @@ module CharacterClassSpec
|
|
228
228
|
end
|
229
229
|
|
230
230
|
describe "a character class mixed with other expressions" do
|
231
|
-
testing_expression '[A-Z] "a"'
|
231
|
+
testing_expression '[A-Z] "a" "bc"'
|
232
232
|
it "lazily instantiates a node for the character" do
|
233
|
-
result = parse('
|
233
|
+
result = parse('Aabc')
|
234
234
|
result.instance_variable_get("@elements").should include(true)
|
235
235
|
result.elements.should_not include(true)
|
236
|
-
result.elements.size.should ==
|
236
|
+
result.elements.size.should == 3
|
237
237
|
end
|
238
238
|
end
|
239
239
|
|
240
240
|
describe "a character class with a node class declaration mixed with other expressions" do
|
241
|
-
testing_expression '([A-Z] <CharacterClassSpec::Foo>) "
|
241
|
+
testing_expression '([A-Z] <CharacterClassSpec::Foo>) "ab"'
|
242
242
|
it "actively generates a node for the character because it has a node class declared" do
|
243
|
-
result = parse('
|
243
|
+
result = parse('Aab')
|
244
244
|
result.instance_variable_get("@elements").should_not include(true)
|
245
245
|
result.elements.should_not include(true)
|
246
246
|
result.elements.size.should == 2
|
@@ -248,9 +248,9 @@ module CharacterClassSpec
|
|
248
248
|
end
|
249
249
|
|
250
250
|
describe "a character class with a node module declaration mixed with other expressions" do
|
251
|
-
testing_expression '([A-Z] <CharacterClassSpec::ModFoo>) "
|
251
|
+
testing_expression '([A-Z] <CharacterClassSpec::ModFoo>) "ab"'
|
252
252
|
it "actively generates a node for the character because it has a node module declared" do
|
253
|
-
result = parse('
|
253
|
+
result = parse('Aab')
|
254
254
|
result.instance_variable_get("@elements").should_not include(true)
|
255
255
|
result.elements.should_not include(true)
|
256
256
|
result.elements.size.should == 2
|
@@ -258,9 +258,9 @@ module CharacterClassSpec
|
|
258
258
|
end
|
259
259
|
|
260
260
|
describe "a character class with an inline block mixed with other expressions" do
|
261
|
-
testing_expression '([A-Z] { def a_method; end }) "
|
261
|
+
testing_expression '([A-Z] { def a_method; end }) "ab"'
|
262
262
|
it "actively generates a node for the character because it has an inline block" do
|
263
|
-
result = parse('
|
263
|
+
result = parse('Aab')
|
264
264
|
result.instance_variable_get("@elements").should_not include(true)
|
265
265
|
result.elements.should_not include(true)
|
266
266
|
result.elements.size.should == 2
|
@@ -268,28 +268,28 @@ module CharacterClassSpec
|
|
268
268
|
end
|
269
269
|
|
270
270
|
describe "a character class with a label mixed with other expressions" do
|
271
|
-
testing_expression 'upper:([A-Z]) "b"'
|
271
|
+
testing_expression 'upper:([A-Z]) "b" "cd"'
|
272
272
|
it "returns the correct element for the labeled expression" do
|
273
|
-
result = parse('
|
273
|
+
result = parse('Abcd')
|
274
274
|
result.upper.text_value.should == "A"
|
275
|
-
result.elements.size.should ==
|
275
|
+
result.elements.size.should == 3
|
276
276
|
end
|
277
277
|
end
|
278
278
|
|
279
279
|
describe "a character class repetition mixed with other expressions" do
|
280
|
-
testing_expression '[A-Z]+ "a"'
|
280
|
+
testing_expression '[A-Z]+ "a" "bc"'
|
281
281
|
it "lazily instantiates a node for the character" do
|
282
|
-
result = parse('
|
282
|
+
result = parse('ABCabc')
|
283
283
|
result.elements[0].instance_variable_get("@elements").should include(true)
|
284
284
|
result.elements[0].elements.should_not include(true)
|
285
285
|
result.elements[0].elements.size.should == 3
|
286
|
-
result.elements.size.should ==
|
287
|
-
result.elements.inspect.should == %Q{[SyntaxNode offset=0, "ABC":\n SyntaxNode offset=0, "A"\n SyntaxNode offset=1, "B"\n SyntaxNode offset=2, "C", SyntaxNode offset=3, "a"]}
|
286
|
+
result.elements.size.should == 3
|
287
|
+
result.elements.inspect.should == %Q{[SyntaxNode offset=0, "ABC":\n SyntaxNode offset=0, "A"\n SyntaxNode offset=1, "B"\n SyntaxNode offset=2, "C", SyntaxNode offset=3, "a", SyntaxNode offset=4, "bc"]}
|
288
288
|
end
|
289
289
|
end
|
290
290
|
|
291
291
|
describe "a character class that gets cached because of a choice" do
|
292
|
-
testing_expression "[A-Z] 'a' / [A-Z]"
|
292
|
+
testing_expression "[A-Z] 'a' 'bc' / [A-Z]"
|
293
293
|
|
294
294
|
it "generates a node for the lazily-instantiated character when it is the primary node" do
|
295
295
|
result = parse('A')
|
@@ -54,10 +54,10 @@ module ChoiceSpec
|
|
54
54
|
end
|
55
55
|
|
56
56
|
describe "A choice between terminals followed by a block" do
|
57
|
-
testing_expression "('a'/ '
|
57
|
+
testing_expression "('a'/ 'bb' / [c]) { def a_method; end }"
|
58
58
|
|
59
59
|
it "extends a match of any of its subexpressions with a module created from the block" do
|
60
|
-
['a', '
|
60
|
+
['a', 'bb', 'c'].each do |letter|
|
61
61
|
parse(letter).should respond_to(:a_method)
|
62
62
|
end
|
63
63
|
end
|
@@ -69,10 +69,10 @@ module ChoiceSpec
|
|
69
69
|
end
|
70
70
|
|
71
71
|
describe "a choice followed by a declared module" do
|
72
|
-
testing_expression "('a'/ '
|
72
|
+
testing_expression "('a'/ 'bb' / [c]) <ChoiceSpec::TestModule>"
|
73
73
|
|
74
74
|
it "extends a match of any of its subexpressions with a module created from the block" do
|
75
|
-
['a', '
|
75
|
+
['a', 'bb', 'c'].each do |letter|
|
76
76
|
parse(letter).should respond_to(:a_method)
|
77
77
|
end
|
78
78
|
end
|
@@ -29,10 +29,10 @@ module NotPredicateSpec
|
|
29
29
|
end
|
30
30
|
|
31
31
|
describe "A !-predicated sequence" do
|
32
|
-
testing_expression '!("a" "b" "
|
32
|
+
testing_expression '!("a" "b" "cc")'
|
33
33
|
|
34
34
|
it "fails to parse matching input" do
|
35
|
-
parse('
|
35
|
+
parse('abcc').should be_nil
|
36
36
|
end
|
37
37
|
end
|
38
38
|
end
|
@@ -5,7 +5,7 @@ module RepeatedSubruleSpec
|
|
5
5
|
testing_grammar %{
|
6
6
|
grammar Foo
|
7
7
|
rule foo
|
8
|
-
a:'a' space b:'b' space '
|
8
|
+
a:'a' space b:'b' space 'cc'
|
9
9
|
end
|
10
10
|
|
11
11
|
rule space
|
@@ -15,7 +15,7 @@ module RepeatedSubruleSpec
|
|
15
15
|
}
|
16
16
|
|
17
17
|
it "should produce a parser having sequence-numbered node accessor methods" do
|
18
|
-
parse("a b
|
18
|
+
parse("a b cc") do |result|
|
19
19
|
result.should_not be_nil
|
20
20
|
result.should respond_to(:space1)
|
21
21
|
result.should respond_to(:space2)
|
@@ -4,6 +4,50 @@ module TerminalSymbolSpec
|
|
4
4
|
class Foo < Treetop::Runtime::SyntaxNode
|
5
5
|
end
|
6
6
|
|
7
|
+
describe "a terminal symbol" do
|
8
|
+
testing_expression "'Foo'"
|
9
|
+
|
10
|
+
it "matches the input string" do
|
11
|
+
parse "Foo", :index => 0 do |result|
|
12
|
+
result.should_not be_nil
|
13
|
+
result.interval.should == (0...3)
|
14
|
+
result.text_value.should == 'Foo'
|
15
|
+
end
|
16
|
+
end
|
17
|
+
|
18
|
+
it "fails to match the input string other than at the start" do
|
19
|
+
parse " Foo", :index => 0 do |result|
|
20
|
+
result.should be_nil
|
21
|
+
end
|
22
|
+
end
|
23
|
+
|
24
|
+
it "fails to match the input string in the wrong case" do
|
25
|
+
parse "foo", :index => 0 do |result|
|
26
|
+
result.should be_nil
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
describe "a terminal symbol with case-insensitive matching" do
|
32
|
+
testing_expression "'Foo'i"
|
33
|
+
|
34
|
+
it "matches the input string in the same case" do
|
35
|
+
parse "Foo", :index => 0 do |result|
|
36
|
+
result.should_not be_nil
|
37
|
+
result.interval.should == (0...3)
|
38
|
+
result.text_value.should == 'Foo'
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
it "matches the input string in varied case" do
|
43
|
+
parse "foO", :index => 0 do |result|
|
44
|
+
result.should_not be_nil
|
45
|
+
result.interval.should == (0...3)
|
46
|
+
result.text_value.should == 'foO'
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
50
|
+
|
7
51
|
describe "a terminal symbol followed by a node class declaration and a block" do
|
8
52
|
testing_expression "'foo' <TerminalSymbolSpec::Foo> { def a_method; end }"
|
9
53
|
|
data/spec/composition/b.treetop
CHANGED
@@ -16,7 +16,7 @@ module GrammarCompositionSpec
|
|
16
16
|
end
|
17
17
|
|
18
18
|
specify "rules in C have access to rules defined in A and B" do
|
19
|
-
@c.parse('
|
19
|
+
@c.parse('abbc').should_not be_nil
|
20
20
|
end
|
21
21
|
|
22
22
|
specify "rules in C can override rules in A and B with super semantics" do
|
@@ -33,7 +33,7 @@ module GrammarCompositionSpec
|
|
33
33
|
end
|
34
34
|
|
35
35
|
specify "rules in F have access to rule defined in E" do
|
36
|
-
@f.parse('
|
36
|
+
@f.parse('abbcef').should_not be_nil
|
37
37
|
end
|
38
38
|
|
39
39
|
end
|
@@ -11,7 +11,7 @@ module CompiledParserSpec
|
|
11
11
|
end
|
12
12
|
|
13
13
|
rule b
|
14
|
-
'
|
14
|
+
'bb'
|
15
15
|
end
|
16
16
|
end
|
17
17
|
}
|
@@ -25,7 +25,7 @@ module CompiledParserSpec
|
|
25
25
|
parser.parse('b').should be_nil
|
26
26
|
|
27
27
|
# Check that the temporary-override works:
|
28
|
-
parser.parse('
|
28
|
+
parser.parse('bb', :root => :b).should_not be_nil
|
29
29
|
parser.parse('a', :root => :b).should be_nil
|
30
30
|
|
31
31
|
# Check that the temporary-override isn't sticky:
|
@@ -33,7 +33,7 @@ module CompiledParserSpec
|
|
33
33
|
|
34
34
|
# Try a permanent override:
|
35
35
|
parser.root = :b
|
36
|
-
parser.parse('
|
36
|
+
parser.parse('bb').should_not be_nil
|
37
37
|
parser.parse('a').should be_nil
|
38
38
|
end
|
39
39
|
|
data/treetop.gemspec
CHANGED
@@ -2,15 +2,17 @@
|
|
2
2
|
# DO NOT EDIT THIS FILE DIRECTLY
|
3
3
|
# Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
|
4
4
|
# -*- encoding: utf-8 -*-
|
5
|
+
# stub: treetop 1.5.1 ruby lib
|
5
6
|
|
6
7
|
Gem::Specification.new do |s|
|
7
8
|
s.name = "treetop"
|
8
|
-
s.version = "1.
|
9
|
+
s.version = "1.5.1"
|
9
10
|
|
10
11
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
12
|
+
s.require_paths = ["lib"]
|
11
13
|
s.authors = ["Nathan Sobo", "Clifford Heath"]
|
12
14
|
s.autorequire = "treetop"
|
13
|
-
s.date = "
|
15
|
+
s.date = "2014-03-12"
|
14
16
|
s.email = "cliffordheath@gmail.com"
|
15
17
|
s.executables = ["tt"]
|
16
18
|
s.extra_rdoc_files = [
|
@@ -136,41 +138,37 @@ Gem::Specification.new do |s|
|
|
136
138
|
]
|
137
139
|
s.homepage = "https://github.com/cjheath/treetop"
|
138
140
|
s.licenses = ["MIT"]
|
139
|
-
s.
|
140
|
-
s.rubygems_version = "1.8.24"
|
141
|
+
s.rubygems_version = "2.2.2"
|
141
142
|
s.summary = "A Ruby-based text parsing and interpretation DSL"
|
142
143
|
|
143
144
|
if s.respond_to? :specification_version then
|
144
|
-
s.specification_version =
|
145
|
+
s.specification_version = 4
|
145
146
|
|
146
147
|
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
147
|
-
s.add_runtime_dependency(%q<polyglot>, ["
|
148
|
-
s.add_development_dependency(%q<jeweler>, ["
|
149
|
-
s.add_development_dependency(%q<activesupport>, ["
|
150
|
-
s.add_development_dependency(%q<i18n>, ["~> 0.
|
148
|
+
s.add_runtime_dependency(%q<polyglot>, ["~> 0.3"])
|
149
|
+
s.add_development_dependency(%q<jeweler>, ["~> 2.0"])
|
150
|
+
s.add_development_dependency(%q<activesupport>, ["~> 4.0"])
|
151
|
+
s.add_development_dependency(%q<i18n>, ["~> 0.6"])
|
151
152
|
s.add_development_dependency(%q<rr>, ["~> 1.0"])
|
152
|
-
s.add_development_dependency(%q<rspec>, ["
|
153
|
-
s.add_development_dependency(%q<rake>, ["
|
154
|
-
s.add_runtime_dependency(%q<polyglot>, [">= 0.3.1"])
|
153
|
+
s.add_development_dependency(%q<rspec>, ["~> 2"])
|
154
|
+
s.add_development_dependency(%q<rake>, ["~> 10"])
|
155
155
|
else
|
156
|
-
s.add_dependency(%q<polyglot>, ["
|
157
|
-
s.add_dependency(%q<jeweler>, ["
|
158
|
-
s.add_dependency(%q<activesupport>, ["
|
159
|
-
s.add_dependency(%q<i18n>, ["~> 0.
|
156
|
+
s.add_dependency(%q<polyglot>, ["~> 0.3"])
|
157
|
+
s.add_dependency(%q<jeweler>, ["~> 2.0"])
|
158
|
+
s.add_dependency(%q<activesupport>, ["~> 4.0"])
|
159
|
+
s.add_dependency(%q<i18n>, ["~> 0.6"])
|
160
160
|
s.add_dependency(%q<rr>, ["~> 1.0"])
|
161
|
-
s.add_dependency(%q<rspec>, ["
|
162
|
-
s.add_dependency(%q<rake>, ["
|
163
|
-
s.add_dependency(%q<polyglot>, [">= 0.3.1"])
|
161
|
+
s.add_dependency(%q<rspec>, ["~> 2"])
|
162
|
+
s.add_dependency(%q<rake>, ["~> 10"])
|
164
163
|
end
|
165
164
|
else
|
166
|
-
s.add_dependency(%q<polyglot>, ["
|
167
|
-
s.add_dependency(%q<jeweler>, ["
|
168
|
-
s.add_dependency(%q<activesupport>, ["
|
169
|
-
s.add_dependency(%q<i18n>, ["~> 0.
|
165
|
+
s.add_dependency(%q<polyglot>, ["~> 0.3"])
|
166
|
+
s.add_dependency(%q<jeweler>, ["~> 2.0"])
|
167
|
+
s.add_dependency(%q<activesupport>, ["~> 4.0"])
|
168
|
+
s.add_dependency(%q<i18n>, ["~> 0.6"])
|
170
169
|
s.add_dependency(%q<rr>, ["~> 1.0"])
|
171
|
-
s.add_dependency(%q<rspec>, ["
|
172
|
-
s.add_dependency(%q<rake>, ["
|
173
|
-
s.add_dependency(%q<polyglot>, [">= 0.3.1"])
|
170
|
+
s.add_dependency(%q<rspec>, ["~> 2"])
|
171
|
+
s.add_dependency(%q<rake>, ["~> 10"])
|
174
172
|
end
|
175
173
|
end
|
176
174
|
|