diff --git a/CHANGELOG.md b/CHANGELOG.md index 9830ba8..1dacc40 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,13 +1,11 @@ Version 4.0.1-dev ----------------- -### Changed - -* Added checks to node traverser to prevent replacing a statement with an expression or vice versa. - This should prevent common mistakes in the implementation of node visitors. - ### Added +* [PHP 7.3] Added support for trailing commas in function calls. +* Added checks to node traverser to prevent replacing a statement with an expression or vice versa. + This should prevent common mistakes in the implementation of node visitors. * Added the following method to `BuilderFactory`, to simplify creation of expressions: * `funcCall()` * `methodCall()` diff --git a/grammar/php7.y b/grammar/php7.y index 07f978f..97b9175 100644 --- a/grammar/php7.y +++ b/grammar/php7.y @@ -277,7 +277,7 @@ optional_finally: ; variables_list: - non_empty_variables_list no_comma { $$ = $1; } + non_empty_variables_list optional_comma { $$ = $1; } ; non_empty_variables_list: @@ -472,7 +472,7 @@ optional_return_type: argument_list: '(' ')' { $$ = array(); } - | '(' non_empty_argument_list no_comma ')' { $$ = $2; } + | '(' non_empty_argument_list optional_comma ')' { $$ = $2; } ; non_empty_argument_list: diff --git a/lib/PhpParser/Parser/Php7.php b/lib/PhpParser/Parser/Php7.php index 251939c..3ef327a 100644 --- a/lib/PhpParser/Parser/Php7.php +++ b/lib/PhpParser/Parser/Php7.php @@ -517,7 +517,7 @@ class Php7 extends \PhpParser\ParserAbstract protected $actionDefault = array( 3,32767,32767,32767,32767,32767,32767,32767,32767, 91, 32767,32767,32767,32767,32767,32767,32767,32767,32767,32767, - 32767,32767,32767, 91, 494, 494,32767, 494,32767,32767, + 32767,32767,32767, 93, 494, 494,32767, 494,32767,32767, 32767, 306, 306, 306,32767, 486, 443, 443, 443, 443, 443, 443, 443, 486,32767,32767,32767,32767,32767, 385, 32767,32767,32767,32767,32767,32767,32767,32767,32767,32767, @@ -537,7 +537,7 @@ class Php7 extends \PhpParser\ParserAbstract 323, 324, 325, 326, 309, 310, 387, 365, 364, 363, 331, 332, 308, 336, 338, 308, 337, 354, 355, 352, 353, 356, 357, 358, 359, 360,32767,32767,32767,32767, - 32767,32767,32767,32767,32767,32767,32767,32767, 91,32767, + 32767,32767,32767,32767,32767,32767,32767,32767, 93,32767, 287, 287, 287, 287,32767, 345, 346, 245, 245, 245, 245,32767, 245, 288,32767,32767,32767,32767,32767,32767, 32767, 437, 362, 340, 341, 339,32767, 415,32767,32767, @@ -552,7 +552,7 @@ class Php7 extends \PhpParser\ParserAbstract 32767,32767,32767, 93, 418, 418, 91, 91, 91, 91, 413,32767, 177,32767,32767,32767,32767,32767, 177, 90, 90, 90, 90, 177, 90, 190,32767, 188, 188, 90, - 32767, 90,32767, 90, 192,32767, 459, 192, 90, 177, + 32767, 92,32767, 92, 192,32767, 459, 192, 90, 177, 90, 212, 212, 394, 179, 92, 247,32767, 247, 92, 394, 90, 177, 247, 90,32767, 90, 247,32767,32767, 32767, 84,32767,32767,32767,32767,32767,32767,32767,32767, @@ -592,26 +592,26 @@ class Php7 extends \PhpParser\ParserAbstract 675, 447, 447, 447, 476, 447, 798, 779, 777, 779, 571, 711, 440, 807, 802, 1076, 462, 460, 663, 447, 574, 496, 498, 523, 526, 531, 532, 809, 539, 541, - 548, 805, 550, 491, 491, 1005, 1005, 1005, 1005, 1005, - 1005, 1005, 1005, 1005, 1005, 1005, 1005, 428, 428, 428, - 428, 428, 428, 428, 428, 428, 428, 428, 428, 428, - 428, 980, 447, 447, 231, 738, 232, 233, 461, 482, + 548, 805, 550, 428, 428, 428, 428, 428, 428, 428, + 428, 428, 428, 428, 428, 428, 428, 427, 427, 427, + 427, 427, 427, 427, 427, 427, 427, 427, 427, 427, + 427, 980, 447, 447, 231, 738, 232, 233, 461, 482, 447, 447, 447, 302, 306, 454, 477, 478, 480, 467, 492, 494, 542, 781, 448, 489, 509, 467, 773, 313, - 545, 1050, 1051, 473, 485, 472, 427, 427, 427, 427, - 427, 427, 427, 427, 427, 427, 427, 427, 427, 427, - 702, 706, 694, 836, 832, 840, 3, 4, 468, 981, - 784, 1068, 754, 300, 486, 1060, 475, 862, 549, 814, - 678, 774, 528, 860, 510, 465, 941, 982, 1036, 817, - 828, 702, 877, 1049, 702, 710, 287, 976, 821, 683, - 502, 733, 728, 729, 742, 439, 684, 730, 681, 731, - 732, 682, 439, 736, 279, 328, 511, 332, 320, 320, + 545, 1050, 1051, 473, 485, 472, 491, 491, 1005, 1005, + 1005, 1005, 1005, 1005, 1005, 1005, 1005, 1005, 1005, 1005, + 702, 706, 694, 836, 832, 840, 475, 862, 549, 981, + 784, 468, 528, 860, 3, 4, 1068, 486, 300, 814, + 678, 774, 1060, 1075, 1075, 510, 465, 982, 1036, 697, + 941, 702, 877, 691, 702, 710, 817, 976, 821, 683, + 1075, 733, 728, 729, 742, 439, 684, 730, 681, 731, + 732, 682, 439, 736, 1078, 328, 511, 332, 320, 320, 268, 269, 285, 471, 271, 327, 286, 330, 497, 775, - 775, 775, 775, 282, 283, 769, 776, 693, 693, 1075, - 1075, 310, 698, 703, 703, 703, 705, 692, 695, 837, - 578, 517, 977, 972, 841, 1091, 1075, 707, 786, 377, - 488, 984, 879, 691, 822, 822, 822, 822, 984, 822, - 1078, 822, 870, 304, 1055, 1055, 393, 822, 444, 453, + 775, 775, 775, 282, 283, 769, 776, 693, 693, 828, + 1049, 287, 502, 703, 703, 703, 705, 692, 698, 279, + 310, 695, 837, 578, 977, 1091, 517, 972, 841, 707, + 488, 984, 786, 377, 822, 822, 822, 822, 984, 822, + 393, 822, 870, 304, 1055, 1055, 879, 822, 444, 453, 0, 0, 0, 1046, 463, 984, 984, 984, 984, 0, 1046, 984, 984, 0, 0, 0, 0, 1057, 1057, 0, 384, 0, 749, 0, 533, 750, 0, 0, 0, 0, @@ -643,26 +643,26 @@ class Php7 extends \PhpParser\ParserAbstract 17, 10, 10, 10, 96, 10, 16, 16, 16, 16, 16, 36, 16, 16, 16, 145, 10, 39, 5, 10, 39, 39, 39, 39, 39, 39, 39, 39, 39, 39, - 39, 39, 39, 85, 85, 85, 85, 85, 85, 85, - 85, 85, 85, 85, 85, 85, 85, 135, 135, 135, - 135, 135, 135, 135, 135, 135, 135, 135, 135, 135, - 135, 91, 10, 10, 72, 55, 72, 72, 10, 10, + 39, 39, 39, 135, 135, 135, 135, 135, 135, 135, + 135, 135, 135, 135, 135, 135, 135, 133, 133, 133, + 133, 133, 133, 133, 133, 133, 133, 133, 133, 133, + 133, 91, 10, 10, 72, 55, 72, 72, 10, 10, 10, 10, 10, 49, 49, 49, 49, 49, 49, 84, 67, 67, 67, 40, 10, 46, 46, 84, 75, 75, - 75, 139, 139, 2, 2, 10, 133, 133, 133, 133, - 133, 133, 133, 133, 133, 133, 133, 133, 133, 133, - 26, 14, 14, 14, 93, 14, 37, 37, 134, 91, - 14, 143, 14, 52, 14, 141, 7, 7, 7, 14, - 13, 14, 7, 7, 54, 53, 116, 91, 91, 87, - 89, 26, 14, 137, 26, 14, 20, 14, 90, 13, - 24, 13, 13, 13, 13, 74, 13, 13, 13, 13, - 13, 13, 74, 13, 11, 56, 56, 56, 56, 56, + 75, 139, 139, 2, 2, 10, 85, 85, 85, 85, + 85, 85, 85, 85, 85, 85, 85, 85, 85, 85, + 26, 14, 14, 14, 93, 14, 7, 7, 7, 91, + 14, 134, 7, 7, 37, 37, 143, 15, 52, 14, + 13, 14, 141, 144, 144, 54, 53, 91, 91, 15, + 116, 26, 14, 15, 26, 14, 87, 14, 90, 13, + 144, 13, 13, 13, 13, 74, 13, 13, 13, 13, + 13, 13, 74, 13, 144, 56, 56, 56, 56, 56, 56, 56, 56, 56, 56, 56, 56, 56, 56, 74, - 74, 74, 74, 79, 79, 74, 74, 26, 26, 144, - 144, 19, 30, 26, 26, 26, 26, 26, 28, 95, - 81, 23, 125, 122, 98, 12, 144, 32, 78, 70, - 71, 63, 112, 15, 63, 63, 63, 63, 63, 63, - 144, 63, 109, 65, 8, 8, 120, 63, 12, 65, + 74, 74, 74, 79, 79, 74, 74, 26, 26, 89, + 137, 20, 24, 26, 26, 26, 26, 26, 30, 11, + 19, 28, 95, 81, 125, 12, 23, 122, 98, 32, + 71, 63, 78, 70, 63, 63, 63, 63, 63, 63, + 120, 63, 109, 65, 8, 8, 112, 63, 12, 65, -1, -1, -1, 96, 65, 63, 63, 63, 63, -1, 96, 63, 63, -1, -1, -1, -1, 96, 96, -1, 65, -1, 63, -1, 12, 63, -1, -1, -1, -1, @@ -678,26 +678,26 @@ class Php7 extends \PhpParser\ParserAbstract ); protected $gotoBase = array( - 0, 0, -330, 0, 0, 138, 0, 251, 106, 0, - -141, 18, 69, -19, -119, -46, 123, 128, 122, 34, - 20, 0, 0, -3, 7, 0, -16, 0, 38, 0, - 48, 0, -9, -22, 0, 0, 132, -332, 0, -405, + 0, 0, -330, 0, 0, 138, 0, 241, 106, 0, + -141, 53, 69, -19, -119, -116, 123, 128, 122, 43, + 65, 0, 0, 2, 49, 0, -16, 0, 41, 0, + 54, 0, -7, -22, 0, 0, 132, -324, 0, -405, 195, 0, 0, 0, 0, 0, 183, 0, 0, 166, - 0, 0, 219, 45, 47, 179, 79, 0, 0, 0, + 0, 0, 224, 46, 48, 179, 79, 0, 0, 0, 0, 0, 0, 107, 0, 1, 0, -28, -270, 0, - -29, -37, -376, 0, 51, -41, 0, 0, -10, -262, - 0, 16, 0, 0, 174, -53, 0, 27, 0, 26, - 28, -108, 0, 221, 0, 36, 129, 0, -13, 0, + -25, -37, -376, 0, 51, -41, 0, 0, -6, -262, + 0, 19, 0, 0, 174, 10, 0, 34, 0, 75, + 28, -108, 0, 221, 0, 39, 129, 0, -9, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 109, - 0, 0, -7, 0, 0, 0, 25, 0, 0, 0, - -34, 0, -12, 0, 0, -6, 0, 0, 0, 0, - 0, 0, -136, 10, 223, -39, 0, 24, 0, -70, - 0, 212, 0, 224, 73, -118, 0, 0 + 0, 0, 7, 0, 0, 0, 29, 0, 0, 0, + -40, 0, -8, 0, 0, -4, 0, 0, 0, 0, + 0, 0, -136, -39, 226, -53, 0, 71, 0, -70, + 0, 219, 0, 229, 17, -118, 0, 0 ); protected $gotoDefault = array( -32768, 398, 581, 2, 582, 653, 661, 518, 415, 547, - 416, 443, 318, 735, 883, 697, 717, 718, 719, 307, + 416, 443, 318, 735, 883, 754, 717, 718, 719, 307, 342, 298, 305, 503, 493, 389, 704, 361, 696, 385, 699, 360, 708, 135, 519, 394, 712, 1, 714, 449, 745, 295, 722, 296, 522, 724, 456, 726, 727, 301, diff --git a/test/code/parser/errorHandling/recovery.test b/test/code/parser/errorHandling/recovery.test index 5fd3d54..02c176b 100644 --- a/test/code/parser/errorHandling/recovery.test +++ b/test/code/parser/errorHandling/recovery.test @@ -613,11 +613,8 @@ A trailing comma is not allowed here from 11:25 to 11:25 A trailing comma is not allowed here from 13:17 to 13:17 A trailing comma is not allowed here from 14:14 to 14:14 A trailing comma is not allowed here from 16:22 to 16:22 -A trailing comma is not allowed here from 18:9 to 18:9 -A trailing comma is not allowed here from 19:9 to 19:9 A trailing comma is not allowed here from 21:13 to 21:13 A trailing comma is not allowed here from 23:16 to 23:16 -A trailing comma is not allowed here from 24:7 to 24:7 A trailing comma is not allowed here from 25:10 to 25:10 A trailing comma is not allowed here from 26:10 to 26:10 A trailing comma is not allowed here from 27:8 to 27:8 diff --git a/test/code/parser/expr/trailingCommas.test b/test/code/parser/expr/trailingCommas.test new file mode 100644 index 0000000..11092d9 --- /dev/null +++ b/test/code/parser/expr/trailingCommas.test @@ -0,0 +1,140 @@ +PHP 7.3 trailing comma additions +----- +bar($a, $b, ); +Foo::bar($a, $b, ); +new Foo($a, $b, ); +unset($a, $b, ); +isset($a, $b, ); +----- +!!php7 +array( + 0: Stmt_Expression( + expr: Expr_FuncCall( + name: Name( + parts: array( + 0: foo + ) + ) + args: array( + 0: Arg( + value: Expr_Variable( + name: a + ) + byRef: false + unpack: false + ) + 1: Arg( + value: Expr_Variable( + name: b + ) + byRef: false + unpack: false + ) + ) + ) + ) + 1: Stmt_Expression( + expr: Expr_MethodCall( + var: Expr_Variable( + name: foo + ) + name: Identifier( + name: bar + ) + args: array( + 0: Arg( + value: Expr_Variable( + name: a + ) + byRef: false + unpack: false + ) + 1: Arg( + value: Expr_Variable( + name: b + ) + byRef: false + unpack: false + ) + ) + ) + ) + 2: Stmt_Expression( + expr: Expr_StaticCall( + class: Name( + parts: array( + 0: Foo + ) + ) + name: Identifier( + name: bar + ) + args: array( + 0: Arg( + value: Expr_Variable( + name: a + ) + byRef: false + unpack: false + ) + 1: Arg( + value: Expr_Variable( + name: b + ) + byRef: false + unpack: false + ) + ) + ) + ) + 3: Stmt_Expression( + expr: Expr_New( + class: Name( + parts: array( + 0: Foo + ) + ) + args: array( + 0: Arg( + value: Expr_Variable( + name: a + ) + byRef: false + unpack: false + ) + 1: Arg( + value: Expr_Variable( + name: b + ) + byRef: false + unpack: false + ) + ) + ) + ) + 4: Stmt_Unset( + vars: array( + 0: Expr_Variable( + name: a + ) + 1: Expr_Variable( + name: b + ) + ) + ) + 5: Stmt_Expression( + expr: Expr_Isset( + vars: array( + 0: Expr_Variable( + name: a + ) + 1: Expr_Variable( + name: b + ) + ) + ) + ) +) \ No newline at end of file