ruby_parser 3.14.2 → 3.15.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- checksums.yaml.gz.sig +0 -0
- data.tar.gz.sig +0 -0
- data/History.rdoc +35 -0
- data/Manifest.txt +2 -0
- data/Rakefile +28 -9
- data/bin/ruby_parse_extract_error +8 -3
- data/compare/normalize.rb +43 -3
- data/debugging.md +39 -0
- data/lib/ruby20_parser.rb +2722 -2702
- data/lib/ruby20_parser.y +91 -58
- data/lib/ruby21_parser.rb +2603 -2576
- data/lib/ruby21_parser.y +91 -58
- data/lib/ruby22_parser.rb +2729 -2715
- data/lib/ruby22_parser.y +91 -58
- data/lib/ruby23_parser.rb +2698 -2686
- data/lib/ruby23_parser.y +91 -58
- data/lib/ruby24_parser.rb +2699 -2670
- data/lib/ruby24_parser.y +91 -58
- data/lib/ruby25_parser.rb +2699 -2670
- data/lib/ruby25_parser.y +91 -58
- data/lib/ruby26_parser.rb +2699 -2670
- data/lib/ruby26_parser.y +91 -58
- data/lib/ruby27_parser.rb +7224 -0
- data/lib/ruby27_parser.y +2657 -0
- data/lib/ruby_lexer.rb +72 -40
- data/lib/ruby_lexer.rex +5 -6
- data/lib/ruby_lexer.rex.rb +6 -8
- data/lib/ruby_parser.rb +2 -0
- data/lib/ruby_parser.yy +93 -58
- data/lib/ruby_parser_extras.rb +49 -16
- data/test/test_ruby_lexer.rb +32 -16
- data/test/test_ruby_parser.rb +204 -3
- data/tools/munge.rb +9 -4
- metadata +12 -7
- metadata.gz.sig +0 -0
data/lib/ruby_parser_extras.rb
CHANGED
@@ -1,4 +1,5 @@
|
|
1
1
|
# encoding: ASCII-8BIT
|
2
|
+
# TODO: remove
|
2
3
|
|
3
4
|
require "sexp"
|
4
5
|
require "ruby_lexer"
|
@@ -28,7 +29,7 @@ class Sexp
|
|
28
29
|
end
|
29
30
|
|
30
31
|
module RubyParserStuff
|
31
|
-
VERSION = "3.
|
32
|
+
VERSION = "3.15.0"
|
32
33
|
|
33
34
|
attr_accessor :lexer, :in_def, :in_single, :file
|
34
35
|
attr_accessor :in_kwarg
|
@@ -45,6 +46,11 @@ module RubyParserStuff
|
|
45
46
|
|
46
47
|
attr_accessor :canonicalize_conditions
|
47
48
|
|
49
|
+
##
|
50
|
+
# The last token type returned from #next_token
|
51
|
+
|
52
|
+
attr_accessor :last_token_type
|
53
|
+
|
48
54
|
$good20 = []
|
49
55
|
|
50
56
|
%w[
|
@@ -493,6 +499,8 @@ module RubyParserStuff
|
|
493
499
|
str.encode! Encoding::UTF_8
|
494
500
|
break
|
495
501
|
end
|
502
|
+
rescue ArgumentError # unknown encoding name
|
503
|
+
# do nothing
|
496
504
|
rescue Encoding::InvalidByteSequenceError
|
497
505
|
# do nothing
|
498
506
|
rescue Encoding::UndefinedConversionError
|
@@ -532,7 +540,7 @@ module RubyParserStuff
|
|
532
540
|
header.map! { |s| s.force_encoding "ASCII-8BIT" } if has_enc
|
533
541
|
|
534
542
|
first = header.first || ""
|
535
|
-
encoding, str = "utf-8", str[3..-1] if first =~ /\A\xEF\xBB\xBF/
|
543
|
+
encoding, str = "utf-8", str.b[3..-1] if first =~ /\A\xEF\xBB\xBF/
|
536
544
|
|
537
545
|
encoding = $1.strip if header.find { |s|
|
538
546
|
s[/^#.*?-\*-.*?coding:\s*([^ ;]+).*?-\*-/, 1] ||
|
@@ -592,7 +600,9 @@ module RubyParserStuff
|
|
592
600
|
case ttype
|
593
601
|
when :str then
|
594
602
|
if htype == :str
|
595
|
-
head.last
|
603
|
+
a, b = head.last, tail.last
|
604
|
+
b = b.dup.force_encoding a.encoding unless Encoding.compatible?(a, b)
|
605
|
+
a << b
|
596
606
|
elsif htype == :dstr and head.size == 2 then
|
597
607
|
head.last << tail.last
|
598
608
|
else
|
@@ -696,6 +706,15 @@ module RubyParserStuff
|
|
696
706
|
result
|
697
707
|
end
|
698
708
|
|
709
|
+
def new_begin val
|
710
|
+
_, lineno, body, _ = val
|
711
|
+
|
712
|
+
result = body ? s(:begin, body) : s(:nil)
|
713
|
+
result.line lineno
|
714
|
+
|
715
|
+
result
|
716
|
+
end
|
717
|
+
|
699
718
|
def new_body val
|
700
719
|
body, resbody, elsebody, ensurebody = val
|
701
720
|
|
@@ -723,7 +742,10 @@ module RubyParserStuff
|
|
723
742
|
result = block_append(result, elsebody)
|
724
743
|
end
|
725
744
|
|
726
|
-
|
745
|
+
if ensurebody
|
746
|
+
lineno = (result || ensurebody).line
|
747
|
+
result = s(:ensure, result, ensurebody).compact.line lineno
|
748
|
+
end
|
727
749
|
|
728
750
|
result
|
729
751
|
end
|
@@ -843,14 +865,17 @@ module RubyParserStuff
|
|
843
865
|
end
|
844
866
|
|
845
867
|
def new_defs val
|
846
|
-
recv,
|
847
|
-
|
868
|
+
_, recv, _, _, name, (_in_def, line), args, body, _ = val
|
869
|
+
|
848
870
|
body ||= s(:nil).line line
|
849
871
|
|
850
872
|
args.line line
|
851
873
|
|
852
874
|
result = s(:defs, recv, name.to_sym, args)
|
853
875
|
|
876
|
+
# TODO: remove_begin
|
877
|
+
# TODO: reduce_nodes
|
878
|
+
|
854
879
|
if body then
|
855
880
|
if body.sexp_type == :block then
|
856
881
|
result.push(*body.sexp_body)
|
@@ -875,7 +900,9 @@ module RubyParserStuff
|
|
875
900
|
end
|
876
901
|
|
877
902
|
def new_hash val
|
878
|
-
|
903
|
+
_, line, assocs = val
|
904
|
+
|
905
|
+
s(:hash).line(line).concat assocs.values
|
879
906
|
end
|
880
907
|
|
881
908
|
def new_if c, t, f
|
@@ -1134,6 +1161,7 @@ module RubyParserStuff
|
|
1134
1161
|
def new_string val
|
1135
1162
|
str, = val
|
1136
1163
|
str.force_encoding("UTF-8")
|
1164
|
+
# TODO: remove:
|
1137
1165
|
str.force_encoding("ASCII-8BIT") unless str.valid_encoding?
|
1138
1166
|
result = s(:str, str).line lexer.lineno
|
1139
1167
|
self.lexer.fixup_lineno str.count("\n")
|
@@ -1228,20 +1256,23 @@ module RubyParserStuff
|
|
1228
1256
|
result
|
1229
1257
|
end
|
1230
1258
|
|
1231
|
-
def new_xstring
|
1232
|
-
|
1233
|
-
|
1259
|
+
def new_xstring val
|
1260
|
+
_, node = val
|
1261
|
+
|
1262
|
+
node ||= s(:str, "").line lexer.lineno
|
1263
|
+
|
1264
|
+
if node then
|
1265
|
+
case node.sexp_type
|
1234
1266
|
when :str
|
1235
|
-
|
1267
|
+
node.sexp_type = :xstr
|
1236
1268
|
when :dstr
|
1237
|
-
|
1269
|
+
node.sexp_type = :dxstr
|
1238
1270
|
else
|
1239
|
-
|
1271
|
+
node = s(:dxstr, "", node).line node.line
|
1240
1272
|
end
|
1241
|
-
str
|
1242
|
-
else
|
1243
|
-
s(:xstr, "")
|
1244
1273
|
end
|
1274
|
+
|
1275
|
+
node
|
1245
1276
|
end
|
1246
1277
|
|
1247
1278
|
def new_yield args = nil
|
@@ -1262,6 +1293,7 @@ module RubyParserStuff
|
|
1262
1293
|
token = self.lexer.next_token
|
1263
1294
|
|
1264
1295
|
if token and token.first != RubyLexer::EOF then
|
1296
|
+
self.last_token_type = token
|
1265
1297
|
return token
|
1266
1298
|
else
|
1267
1299
|
return [false, false]
|
@@ -1320,6 +1352,7 @@ module RubyParserStuff
|
|
1320
1352
|
self.in_single = 0
|
1321
1353
|
self.env.reset
|
1322
1354
|
self.comments.clear
|
1355
|
+
self.last_token_type = nil
|
1323
1356
|
end
|
1324
1357
|
|
1325
1358
|
def ret_args node
|
data/test/test_ruby_lexer.rb
CHANGED
@@ -1,7 +1,3 @@
|
|
1
|
-
# encoding: US-ASCII
|
2
|
-
|
3
|
-
# TODO: work this out
|
4
|
-
|
5
1
|
require "minitest/autorun"
|
6
2
|
require "ruby_lexer"
|
7
3
|
require "ruby_parser"
|
@@ -84,10 +80,12 @@ class TestRubyLexer < Minitest::Test
|
|
84
80
|
assert_in_epsilon value, act_value, 0.001, msg
|
85
81
|
when NilClass then
|
86
82
|
assert_nil act_value, msg
|
83
|
+
when String then
|
84
|
+
assert_equal value, act_value.b.force_encoding(value.encoding), msg
|
87
85
|
else
|
88
86
|
assert_equal value, act_value, msg
|
89
87
|
end
|
90
|
-
|
88
|
+
assert_match state, @lex.lex_state, msg if state
|
91
89
|
assert_equal paren, @lex.paren_nest, msg if paren
|
92
90
|
assert_equal brace, @lex.brace_nest, msg if brace
|
93
91
|
end
|
@@ -98,7 +96,8 @@ class TestRubyLexer < Minitest::Test
|
|
98
96
|
|
99
97
|
def assert_read_escape expected, input
|
100
98
|
@lex.ss.string = input.dup
|
101
|
-
|
99
|
+
enc = expected.encoding
|
100
|
+
assert_equal expected, @lex.read_escape.b.force_encoding(enc), input
|
102
101
|
end
|
103
102
|
|
104
103
|
def assert_read_escape_bad input # TODO: rename refute_read_escape
|
@@ -146,7 +145,7 @@ class TestRubyLexer < Minitest::Test
|
|
146
145
|
yield
|
147
146
|
|
148
147
|
lexer.lex_state = EXPR_ENDARG
|
149
|
-
assert_next_lexeme :tSTRING_DEND, "}", EXPR_END, 0
|
148
|
+
assert_next_lexeme :tSTRING_DEND, "}", EXPR_END|EXPR_ENDARG, 0
|
150
149
|
|
151
150
|
lexer.lex_strterm = lex_strterm
|
152
151
|
lexer.lex_state = EXPR_BEG
|
@@ -720,7 +719,7 @@ class TestRubyLexer < Minitest::Test
|
|
720
719
|
|
721
720
|
assert_lex3("do 42 end",
|
722
721
|
nil,
|
723
|
-
:
|
722
|
+
:kDO, "do", EXPR_BEG,
|
724
723
|
:tINTEGER, 42, EXPR_NUM,
|
725
724
|
:kEND, "end", EXPR_END)
|
726
725
|
end
|
@@ -926,6 +925,14 @@ class TestRubyLexer < Minitest::Test
|
|
926
925
|
assert_lex3("$1234", nil, :tGVAR, "$1234", EXPR_END)
|
927
926
|
end
|
928
927
|
|
928
|
+
def test_yylex_global_I_have_no_words
|
929
|
+
assert_lex3("$x\xE2\x80\x8B = 42", # zero width space?!?!?
|
930
|
+
nil,
|
931
|
+
:tGVAR, "$x\xE2\x80\x8B", EXPR_END,
|
932
|
+
:tEQL, "=", EXPR_BEG,
|
933
|
+
:tINTEGER, 42, EXPR_NUM)
|
934
|
+
end
|
935
|
+
|
929
936
|
def test_yylex_global_other
|
930
937
|
assert_lex3("[$~, $*, $$, $?, $!, $@, $/, $\\, $;, $,, $., $=, $:, $<, $>, $\"]",
|
931
938
|
nil,
|
@@ -1109,11 +1116,11 @@ class TestRubyLexer < Minitest::Test
|
|
1109
1116
|
:tEQL, "=", EXPR_BEG,
|
1110
1117
|
:tSTRING_BEG, "\"", EXPR_BEG,
|
1111
1118
|
:tSTRING_CONTENT, "#x a ", EXPR_BEG,
|
1112
|
-
:tSTRING_DVAR, "
|
1119
|
+
:tSTRING_DVAR, "#", EXPR_BEG,
|
1113
1120
|
:tSTRING_CONTENT, "@a b ", EXPR_BEG, # HUH?
|
1114
|
-
:tSTRING_DVAR, "
|
1121
|
+
:tSTRING_DVAR, "#", EXPR_BEG,
|
1115
1122
|
:tSTRING_CONTENT, "$b c ", EXPR_BEG, # HUH?
|
1116
|
-
:tSTRING_DVAR, "
|
1123
|
+
:tSTRING_DVAR, "#", EXPR_BEG,
|
1117
1124
|
:tSTRING_CONTENT, "@@d ", EXPR_BEG, # HUH?
|
1118
1125
|
:tSTRING_DBEG, "\#{", EXPR_BEG,
|
1119
1126
|
:tSTRING_CONTENT, "3} \n", EXPR_BEG,
|
@@ -2099,6 +2106,10 @@ class TestRubyLexer < Minitest::Test
|
|
2099
2106
|
assert_lex3("?\\M-\\C-a", nil, :tSTRING, "\M-\C-a", EXPR_END)
|
2100
2107
|
end
|
2101
2108
|
|
2109
|
+
def test_yylex_question_control_escape
|
2110
|
+
assert_lex3('?\C-\]', nil, :tSTRING, ?\C-\], EXPR_END)
|
2111
|
+
end
|
2112
|
+
|
2102
2113
|
def test_yylex_question_ws
|
2103
2114
|
assert_lex3("? ", nil, :tEH, "?", EXPR_BEG)
|
2104
2115
|
assert_lex3("?\n", nil, :tEH, "?", EXPR_BEG)
|
@@ -2549,11 +2560,7 @@ class TestRubyLexer < Minitest::Test
|
|
2549
2560
|
end
|
2550
2561
|
|
2551
2562
|
def test_yylex_string_double_escape_c_backslash
|
2552
|
-
|
2553
|
-
nil,
|
2554
|
-
:tSTRING_BEG, "\"", EXPR_BEG,
|
2555
|
-
:tSTRING_CONTENT, "\034", EXPR_BEG,
|
2556
|
-
:tSTRING_END, "\"", EXPR_LIT)
|
2563
|
+
refute_lex("\"\\c\\\"", :tSTRING_BEG, '"')
|
2557
2564
|
end
|
2558
2565
|
|
2559
2566
|
def test_yylex_string_double_escape_c_escape
|
@@ -2847,6 +2854,15 @@ class TestRubyLexer < Minitest::Test
|
|
2847
2854
|
:tSTRING_END, '"')
|
2848
2855
|
end
|
2849
2856
|
|
2857
|
+
def test_yylex_string_utf8_bad_encoding_with_escapes
|
2858
|
+
str = "\"\\xBADπ\""
|
2859
|
+
exp = "\xBADπ".b
|
2860
|
+
|
2861
|
+
assert_lex(str,
|
2862
|
+
s(:str, exp),
|
2863
|
+
:tSTRING, exp, EXPR_END)
|
2864
|
+
end
|
2865
|
+
|
2850
2866
|
def test_yylex_string_utf8_complex_trailing_hex
|
2851
2867
|
chr = [0x3024].pack("U")
|
2852
2868
|
str = "#{chr}abz"
|
data/test/test_ruby_parser.rb
CHANGED
@@ -185,6 +185,57 @@ module TestRubyParserShared
|
|
185
185
|
assert_syntax_error rb, "else without rescue is useless"
|
186
186
|
end
|
187
187
|
|
188
|
+
def test_begin_ensure_no_bodies
|
189
|
+
rb = "begin\nensure\nend"
|
190
|
+
pt = s(:ensure, s(:nil).line(2)).line(2)
|
191
|
+
|
192
|
+
assert_parse rb, pt
|
193
|
+
end
|
194
|
+
|
195
|
+
def test_begin_rescue_ensure_no_bodies
|
196
|
+
rb = "begin\nrescue\nensure\nend"
|
197
|
+
pt = s(:ensure,
|
198
|
+
s(:rescue,
|
199
|
+
s(:resbody, s(:array).line(2),
|
200
|
+
nil).line(2)
|
201
|
+
).line(2),
|
202
|
+
s(:nil).line(3)
|
203
|
+
).line(2)
|
204
|
+
|
205
|
+
assert_parse rb, pt
|
206
|
+
end
|
207
|
+
|
208
|
+
def test_begin_rescue_else_ensure_bodies
|
209
|
+
rb = "begin\n 1\nrescue\n 2\nelse\n 3\nensure\n 4\nend"
|
210
|
+
pt = s(:ensure,
|
211
|
+
s(:rescue,
|
212
|
+
s(:lit, 1).line(2),
|
213
|
+
s(:resbody, s(:array).line(3),
|
214
|
+
s(:lit, 2).line(4)).line(3),
|
215
|
+
s(:lit, 3).line(6)).line(2),
|
216
|
+
s(:lit, 4).line(8)).line(2)
|
217
|
+
|
218
|
+
s(:ensure, s(:rescue, s(:resbody, s(:array), nil)), s(:nil))
|
219
|
+
|
220
|
+
assert_parse rb, pt
|
221
|
+
end
|
222
|
+
|
223
|
+
def test_begin_rescue_else_ensure_no_bodies
|
224
|
+
rb = "begin\n\nrescue\n\nelse\n\nensure\n\nend"
|
225
|
+
pt = s(:ensure,
|
226
|
+
s(:rescue,
|
227
|
+
s(:resbody, s(:array).line(3),
|
228
|
+
# TODO: s(:nil)
|
229
|
+
nil
|
230
|
+
).line(3),
|
231
|
+
).line(3),
|
232
|
+
s(:nil).line(7)).line(3)
|
233
|
+
|
234
|
+
s(:ensure, s(:rescue, s(:resbody, s(:array), nil)), s(:nil))
|
235
|
+
|
236
|
+
assert_parse rb, pt
|
237
|
+
end
|
238
|
+
|
188
239
|
def test_block_append
|
189
240
|
head = s(:args).line 1
|
190
241
|
tail = s(:zsuper).line 2
|
@@ -290,7 +341,7 @@ module TestRubyParserShared
|
|
290
341
|
def test_bug190
|
291
342
|
skip "not ready for this yet"
|
292
343
|
|
293
|
-
rb = %{%r'
|
344
|
+
rb = %{%r'\\\''} # stupid emacs
|
294
345
|
|
295
346
|
assert_parse rb, :FUCK
|
296
347
|
assert_syntax_error rb, "FUCK"
|
@@ -872,6 +923,13 @@ module TestRubyParserShared
|
|
872
923
|
assert_parse rb, pt
|
873
924
|
end
|
874
925
|
|
926
|
+
def test_heredoc_with_extra_carriage_horrible_mix?
|
927
|
+
rb = "<<'eot'\r\nbody\r\neot\n"
|
928
|
+
pt = s(:str, "body\r\n")
|
929
|
+
|
930
|
+
assert_parse rb, pt
|
931
|
+
end
|
932
|
+
|
875
933
|
def test_heredoc_with_interpolation_and_carriage_return_escapes
|
876
934
|
rb = "<<EOS\nfoo\\r\#@bar\nEOS\n"
|
877
935
|
pt = s(:dstr, "foo\r", s(:evstr, s(:ivar, :@bar)), s(:str, "\n"))
|
@@ -900,6 +958,13 @@ module TestRubyParserShared
|
|
900
958
|
assert_parse rb, pt
|
901
959
|
end
|
902
960
|
|
961
|
+
def test_heredoc_with_not_global_interpolation
|
962
|
+
rb = "<<-HEREDOC\n#${\nHEREDOC"
|
963
|
+
pt = s(:str, "\#${\n")
|
964
|
+
|
965
|
+
assert_parse rb, pt
|
966
|
+
end
|
967
|
+
|
903
968
|
def test_i_fucking_hate_line_numbers
|
904
969
|
rb = <<-END.gsub(/^ {6}/, "")
|
905
970
|
if true
|
@@ -1252,6 +1317,20 @@ module TestRubyParserShared
|
|
1252
1317
|
end
|
1253
1318
|
end
|
1254
1319
|
|
1320
|
+
def test_magic_encoding_comment__bad
|
1321
|
+
rb = "#encoding: bunk\n0"
|
1322
|
+
pt = s(:lit, 0)
|
1323
|
+
|
1324
|
+
assert_parse rb, pt
|
1325
|
+
end
|
1326
|
+
|
1327
|
+
def test_utf8_bom
|
1328
|
+
rb = "\xEF\xBB\xBF#!/usr/bin/env ruby -w\np 0\n"
|
1329
|
+
pt = s(:call, nil, :p, s(:lit, 0))
|
1330
|
+
|
1331
|
+
assert_parse rb, pt
|
1332
|
+
end
|
1333
|
+
|
1255
1334
|
def test_masgn_arg_colon_arg
|
1256
1335
|
rb = "a, b::c = d"
|
1257
1336
|
pt = s(:masgn,
|
@@ -1383,13 +1462,43 @@ module TestRubyParserShared
|
|
1383
1462
|
assert_parse rb, pt
|
1384
1463
|
end
|
1385
1464
|
|
1386
|
-
def
|
1465
|
+
def test_op_asgn_primary_colon_identifier1
|
1387
1466
|
rb = "A::b += 1"
|
1388
1467
|
pt = s(:op_asgn, s(:const, :A), s(:lit, 1), :b, :+) # TODO: check? looks wack
|
1389
1468
|
|
1390
1469
|
assert_parse rb, pt
|
1391
1470
|
end
|
1392
1471
|
|
1472
|
+
def test_lasgn_middle_splat
|
1473
|
+
rb = "a = b, *c, d"
|
1474
|
+
pt = s(:lasgn, :a,
|
1475
|
+
s(:svalue,
|
1476
|
+
s(:array,
|
1477
|
+
s(:call, nil, :b),
|
1478
|
+
s(:splat, s(:call, nil, :c)),
|
1479
|
+
s(:call, nil, :d))))
|
1480
|
+
|
1481
|
+
assert_parse rb, pt
|
1482
|
+
end
|
1483
|
+
|
1484
|
+
def test_op_asgn_primary_colon_const_command_call
|
1485
|
+
rb = "A::B *= c d"
|
1486
|
+
pt = s(:op_asgn, s(:const, :A),
|
1487
|
+
s(:call, nil, :c, s(:call, nil, :d)),
|
1488
|
+
:B, :*)
|
1489
|
+
|
1490
|
+
assert_parse rb, pt
|
1491
|
+
end
|
1492
|
+
|
1493
|
+
def test_op_asgn_primary_colon_identifier_command_call
|
1494
|
+
rb = "A::b *= c d"
|
1495
|
+
pt = s(:op_asgn, s(:const, :A),
|
1496
|
+
s(:call, nil, :c, s(:call, nil, :d)),
|
1497
|
+
:b, :*)
|
1498
|
+
|
1499
|
+
assert_parse rb, pt
|
1500
|
+
end
|
1501
|
+
|
1393
1502
|
def test_op_asgn_val_dot_ident_command_call
|
1394
1503
|
rb = "a.b ||= c 1"
|
1395
1504
|
pt = s(:op_asgn, s(:call, nil, :a), s(:call, nil, :c, s(:lit, 1)), :b, :"||")
|
@@ -3288,6 +3397,76 @@ module TestRubyParserShared20Plus
|
|
3288
3397
|
assert_parse rb, pt
|
3289
3398
|
end
|
3290
3399
|
|
3400
|
+
def test_call_array_block_call
|
3401
|
+
rb = "a [ nil, b do end ]"
|
3402
|
+
pt = s(:call, nil, :a,
|
3403
|
+
s(:array,
|
3404
|
+
s(:nil),
|
3405
|
+
s(:iter, s(:call, nil, :b), 0)))
|
3406
|
+
|
3407
|
+
assert_parse rb, pt
|
3408
|
+
end
|
3409
|
+
|
3410
|
+
def test_block_call_paren_call_block_call
|
3411
|
+
rb = "a (b)\nc.d do end"
|
3412
|
+
pt = s(:block,
|
3413
|
+
s(:call, nil, :a, s(:call, nil, :b)),
|
3414
|
+
s(:iter, s(:call, s(:call, nil, :c), :d), 0))
|
3415
|
+
|
3416
|
+
|
3417
|
+
assert_parse rb, pt
|
3418
|
+
end
|
3419
|
+
|
3420
|
+
def test_block_call_defn_call_block_call
|
3421
|
+
rb = "a def b(c)\n d\n end\n e.f do end"
|
3422
|
+
pt = s(:block,
|
3423
|
+
s(:call, nil, :a,
|
3424
|
+
s(:defn, :b, s(:args, :c), s(:call, nil, :d))),
|
3425
|
+
s(:iter, s(:call, s(:call, nil, :e), :f), 0))
|
3426
|
+
|
3427
|
+
assert_parse rb, pt
|
3428
|
+
end
|
3429
|
+
|
3430
|
+
def test_call_array_lambda_block_call
|
3431
|
+
rb = "a [->() {}] do\nend"
|
3432
|
+
pt = s(:iter,
|
3433
|
+
s(:call, nil, :a,
|
3434
|
+
s(:array, s(:iter, s(:lambda), s(:args)))),
|
3435
|
+
0)
|
3436
|
+
|
3437
|
+
assert_parse rb, pt
|
3438
|
+
end
|
3439
|
+
|
3440
|
+
def test_call_begin_call_block_call
|
3441
|
+
rb = "a begin\nb.c do end\nend"
|
3442
|
+
pt = s(:call, nil, :a,
|
3443
|
+
s(:iter, s(:call, s(:call, nil, :b), :c), 0))
|
3444
|
+
|
3445
|
+
assert_parse rb, pt
|
3446
|
+
end
|
3447
|
+
|
3448
|
+
def test_messy_op_asgn_lineno
|
3449
|
+
rb = "a (B::C *= d e)"
|
3450
|
+
pt = s(:call, nil, :a,
|
3451
|
+
s(:op_asgn, s(:const, :B),
|
3452
|
+
s(:call, nil, :d, s(:call, nil, :e)),
|
3453
|
+
:C,
|
3454
|
+
:*)).line(1)
|
3455
|
+
|
3456
|
+
assert_parse rb, pt
|
3457
|
+
end
|
3458
|
+
|
3459
|
+
def test_str_lit_concat_bad_encodings
|
3460
|
+
rb = '"\xE3\xD3\x8B\xE3\x83\xBC\x83\xE3\x83\xE3\x82\xB3\xA3\x82\x99" \
|
3461
|
+
"\xE3\x83\xB3\xE3\x83\x8F\xE3\x82\x9A\xC3\xBD;foo@bar.com"'.b
|
3462
|
+
pt = s(:str, "\xE3\xD3\x8B\xE3\x83\xBC\x83\xE3\x83\xE3\x82\xB3\xA3\x82\x99\xE3\x83\xB3\xE3\x83\x8F\xE3\x82\x9A\xC3\xBD;foo@bar.com".b)
|
3463
|
+
|
3464
|
+
assert_parse rb, pt
|
3465
|
+
|
3466
|
+
sexp = processor.parse rb
|
3467
|
+
assert_equal Encoding::ASCII_8BIT, sexp.last.encoding
|
3468
|
+
end
|
3469
|
+
|
3291
3470
|
def test_block_call_dot_op2_cmd_args_do_block
|
3292
3471
|
rb = "a.b c() do d end.e f do |g| h end"
|
3293
3472
|
pt = s(:iter,
|
@@ -3588,7 +3767,7 @@ module TestRubyParserShared21Plus
|
|
3588
3767
|
|
3589
3768
|
def test_bug162__21plus
|
3590
3769
|
rb = %q(<<E\nfoo\nE\rO)
|
3591
|
-
emsg = "can't match /E(
|
3770
|
+
emsg = "can't match /E(\\r*\\n|\\z)/ anywhere in . near line 1: \"\""
|
3592
3771
|
|
3593
3772
|
assert_syntax_error rb, emsg
|
3594
3773
|
end
|
@@ -3738,6 +3917,13 @@ module TestRubyParserShared23Plus
|
|
3738
3917
|
assert_parse rb, pt
|
3739
3918
|
end
|
3740
3919
|
|
3920
|
+
def test_heredoc__backslash_dos_format
|
3921
|
+
rb = "str = <<-XXX\r\nbefore\\\r\nafter\r\nXXX\r\n"
|
3922
|
+
pt = s(:lasgn, :str, s(:str, "before\nafter\n"))
|
3923
|
+
|
3924
|
+
assert_parse rb, pt
|
3925
|
+
end
|
3926
|
+
|
3741
3927
|
def test_heredoc_squiggly
|
3742
3928
|
rb = "a = <<~\"EOF\"\n x\n y\n z\n EOF\n\n"
|
3743
3929
|
pt = s(:lasgn, :a, s(:str, "x\ny\nz\n"))
|
@@ -3946,6 +4132,10 @@ module TestRubyParserShared26Plus
|
|
3946
4132
|
end
|
3947
4133
|
end
|
3948
4134
|
|
4135
|
+
module TestRubyParserShared27Plus
|
4136
|
+
include TestRubyParserShared26Plus
|
4137
|
+
end
|
4138
|
+
|
3949
4139
|
class TestRubyParser < Minitest::Test
|
3950
4140
|
def test_cls_version
|
3951
4141
|
assert_equal 23, RubyParser::V23.version
|
@@ -4242,6 +4432,17 @@ class TestRubyParserV26 < RubyParserTestCase
|
|
4242
4432
|
|
4243
4433
|
end
|
4244
4434
|
|
4435
|
+
class TestRubyParserV27 < RubyParserTestCase
|
4436
|
+
include TestRubyParserShared27Plus
|
4437
|
+
|
4438
|
+
def setup
|
4439
|
+
super
|
4440
|
+
|
4441
|
+
self.processor = RubyParser::V27.new
|
4442
|
+
end
|
4443
|
+
end
|
4444
|
+
|
4445
|
+
|
4245
4446
|
RubyParser::VERSIONS.each do |klass|
|
4246
4447
|
v = klass.version
|
4247
4448
|
describe "block args arity #{v}" do
|