mirror of
https://github.com/phabelio/PHP-Parser.git
synced 2024-11-30 04:29:15 +01:00
Add emulation for enum keyword
This commit is contained in:
parent
8165cf69fa
commit
a8223f228a
@ -110,4 +110,5 @@
|
||||
%token T_NAME_FULLY_QUALIFIED
|
||||
%token T_NAME_QUALIFIED
|
||||
%token T_NAME_RELATIVE
|
||||
%token T_ATTRIBUTE
|
||||
%token T_ATTRIBUTE
|
||||
%token T_ENUM
|
@ -421,6 +421,8 @@ class Lexer
|
||||
'T_MATCH',
|
||||
'T_NULLSAFE_OBJECT_OPERATOR',
|
||||
'T_ATTRIBUTE',
|
||||
// PHP 8.1
|
||||
'T_ENUM',
|
||||
];
|
||||
|
||||
// PHP-Parser might be used together with another library that also emulates some or all
|
||||
@ -511,6 +513,7 @@ class Lexer
|
||||
$tokenMap[\T_MATCH] = Tokens::T_MATCH;
|
||||
$tokenMap[\T_NULLSAFE_OBJECT_OPERATOR] = Tokens::T_NULLSAFE_OBJECT_OPERATOR;
|
||||
$tokenMap[\T_ATTRIBUTE] = Tokens::T_ATTRIBUTE;
|
||||
$tokenMap[\T_ENUM] = Tokens::T_ENUM;
|
||||
|
||||
return $tokenMap;
|
||||
}
|
||||
|
@ -6,6 +6,7 @@ use PhpParser\Error;
|
||||
use PhpParser\ErrorHandler;
|
||||
use PhpParser\Lexer;
|
||||
use PhpParser\Lexer\TokenEmulator\AttributeEmulator;
|
||||
use PhpParser\Lexer\TokenEmulator\EnumTokenEmulator;
|
||||
use PhpParser\Lexer\TokenEmulator\CoaleseEqualTokenEmulator;
|
||||
use PhpParser\Lexer\TokenEmulator\FlexibleDocStringEmulator;
|
||||
use PhpParser\Lexer\TokenEmulator\FnTokenEmulator;
|
||||
@ -14,13 +15,13 @@ use PhpParser\Lexer\TokenEmulator\NullsafeTokenEmulator;
|
||||
use PhpParser\Lexer\TokenEmulator\NumericLiteralSeparatorEmulator;
|
||||
use PhpParser\Lexer\TokenEmulator\ReverseEmulator;
|
||||
use PhpParser\Lexer\TokenEmulator\TokenEmulator;
|
||||
use PhpParser\Parser\Tokens;
|
||||
|
||||
class Emulative extends Lexer
|
||||
{
|
||||
const PHP_7_3 = '7.3dev';
|
||||
const PHP_7_4 = '7.4dev';
|
||||
const PHP_8_0 = '8.0dev';
|
||||
const PHP_8_1 = '8.1dev';
|
||||
|
||||
/** @var mixed[] Patches used to reverse changes introduced in the code */
|
||||
private $patches = [];
|
||||
@ -38,7 +39,7 @@ class Emulative extends Lexer
|
||||
*/
|
||||
public function __construct(array $options = [])
|
||||
{
|
||||
$this->targetPhpVersion = $options['phpVersion'] ?? Emulative::PHP_8_0;
|
||||
$this->targetPhpVersion = $options['phpVersion'] ?? Emulative::PHP_8_1;
|
||||
unset($options['phpVersion']);
|
||||
|
||||
parent::__construct($options);
|
||||
@ -51,6 +52,7 @@ class Emulative extends Lexer
|
||||
new NumericLiteralSeparatorEmulator(),
|
||||
new NullsafeTokenEmulator(),
|
||||
new AttributeEmulator(),
|
||||
new EnumTokenEmulator(),
|
||||
];
|
||||
|
||||
// Collect emulators that are relevant for the PHP version we're running
|
||||
|
31
lib/PhpParser/Lexer/TokenEmulator/EnumTokenEmulator.php
Normal file
31
lib/PhpParser/Lexer/TokenEmulator/EnumTokenEmulator.php
Normal file
@ -0,0 +1,31 @@
|
||||
<?php declare(strict_types=1);
|
||||
|
||||
namespace PhpParser\Lexer\TokenEmulator;
|
||||
|
||||
use PhpParser\Lexer\Emulative;
|
||||
|
||||
final class EnumTokenEmulator extends KeywordEmulator
|
||||
{
|
||||
public function getPhpVersion(): string
|
||||
{
|
||||
return Emulative::PHP_8_1;
|
||||
}
|
||||
|
||||
public function getKeywordString(): string
|
||||
{
|
||||
return 'enum';
|
||||
}
|
||||
|
||||
public function getKeywordToken(): int
|
||||
{
|
||||
return \T_ENUM;
|
||||
}
|
||||
|
||||
protected function isKeywordContext(array $tokens, int $pos): bool
|
||||
{
|
||||
return parent::isKeywordContext($tokens, $pos)
|
||||
&& isset($tokens[$pos + 2])
|
||||
&& $tokens[$pos + 1][0] === \T_WHITESPACE
|
||||
&& $tokens[$pos + 2][0] === \T_STRING;
|
||||
}
|
||||
}
|
@ -12,16 +12,18 @@ abstract class KeywordEmulator extends TokenEmulator
|
||||
return strpos(strtolower($code), $this->getKeywordString()) !== false;
|
||||
}
|
||||
|
||||
protected function isKeywordContext(array $tokens, int $pos): bool
|
||||
{
|
||||
$previousNonSpaceToken = $this->getPreviousNonSpaceToken($tokens, $pos);
|
||||
return $previousNonSpaceToken === null || $previousNonSpaceToken[0] !== \T_OBJECT_OPERATOR;
|
||||
}
|
||||
|
||||
public function emulate(string $code, array $tokens): array
|
||||
{
|
||||
$keywordString = $this->getKeywordString();
|
||||
foreach ($tokens as $i => $token) {
|
||||
if ($token[0] === T_STRING && strtolower($token[1]) === $keywordString) {
|
||||
$previousNonSpaceToken = $this->getPreviousNonSpaceToken($tokens, $i);
|
||||
if ($previousNonSpaceToken !== null && $previousNonSpaceToken[0] === \T_OBJECT_OPERATOR) {
|
||||
continue;
|
||||
}
|
||||
|
||||
if ($token[0] === T_STRING && strtolower($token[1]) === $keywordString
|
||||
&& $this->isKeywordContext($tokens, $i)) {
|
||||
$tokens[$i][0] = $this->getKeywordToken();
|
||||
}
|
||||
}
|
||||
|
@ -17,11 +17,11 @@ use PhpParser\Node\Stmt;
|
||||
*/
|
||||
class Php5 extends \PhpParser\ParserAbstract
|
||||
{
|
||||
protected $tokenToSymbolMapSize = 392;
|
||||
protected $tokenToSymbolMapSize = 393;
|
||||
protected $actionTableSize = 1069;
|
||||
protected $gotoTableSize = 580;
|
||||
|
||||
protected $invalidSymbol = 165;
|
||||
protected $invalidSymbol = 166;
|
||||
protected $errorSymbol = 1;
|
||||
protected $defaultAction = -32766;
|
||||
protected $unexpectedTokenRule = 32767;
|
||||
@ -194,36 +194,37 @@ class Php5 extends \PhpParser\ParserAbstract
|
||||
"']'",
|
||||
"'\"'",
|
||||
"T_NULLSAFE_OBJECT_OPERATOR",
|
||||
"T_ATTRIBUTE"
|
||||
"T_ATTRIBUTE",
|
||||
"T_ENUM"
|
||||
);
|
||||
|
||||
protected $tokenToSymbol = array(
|
||||
0, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 55, 162, 165, 159, 54, 37, 165,
|
||||
157, 158, 52, 49, 8, 50, 51, 53, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 31, 154,
|
||||
43, 16, 45, 30, 67, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 69, 165, 161, 36, 165, 160, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 155, 35, 156, 57, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 1, 2, 3, 4,
|
||||
0, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 55, 162, 166, 159, 54, 37, 166,
|
||||
157, 158, 52, 49, 8, 50, 51, 53, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 31, 154,
|
||||
43, 16, 45, 30, 67, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 69, 166, 161, 36, 166, 160, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 155, 35, 156, 57, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 1, 2, 3, 4,
|
||||
5, 6, 7, 9, 10, 11, 12, 13, 14, 15,
|
||||
17, 18, 19, 20, 21, 22, 23, 24, 25, 26,
|
||||
27, 28, 29, 32, 33, 34, 38, 39, 40, 41,
|
||||
@ -237,7 +238,7 @@ class Php5 extends \PhpParser\ParserAbstract
|
||||
124, 125, 126, 127, 128, 129, 130, 131, 163, 132,
|
||||
133, 134, 135, 136, 137, 138, 139, 140, 141, 142,
|
||||
143, 144, 145, 146, 147, 148, 149, 150, 151, 152,
|
||||
153, 164
|
||||
153, 164, 165
|
||||
);
|
||||
|
||||
protected $action = array(
|
||||
|
@ -17,11 +17,11 @@ use PhpParser\Node\Stmt;
|
||||
*/
|
||||
class Php7 extends \PhpParser\ParserAbstract
|
||||
{
|
||||
protected $tokenToSymbolMapSize = 392;
|
||||
protected $tokenToSymbolMapSize = 393;
|
||||
protected $actionTableSize = 1162;
|
||||
protected $gotoTableSize = 588;
|
||||
|
||||
protected $invalidSymbol = 165;
|
||||
protected $invalidSymbol = 166;
|
||||
protected $errorSymbol = 1;
|
||||
protected $defaultAction = -32766;
|
||||
protected $unexpectedTokenRule = 32767;
|
||||
@ -194,36 +194,37 @@ class Php7 extends \PhpParser\ParserAbstract
|
||||
"')'",
|
||||
"'`'",
|
||||
"'\"'",
|
||||
"'$'"
|
||||
"'$'",
|
||||
"T_ENUM"
|
||||
);
|
||||
|
||||
protected $tokenToSymbol = array(
|
||||
0, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 55, 163, 165, 164, 54, 37, 165,
|
||||
160, 161, 52, 49, 8, 50, 51, 53, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 31, 156,
|
||||
43, 16, 45, 30, 67, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 69, 165, 157, 36, 165, 162, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 158, 35, 159, 57, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 165, 165, 165, 165,
|
||||
165, 165, 165, 165, 165, 165, 1, 2, 3, 4,
|
||||
0, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 55, 163, 166, 164, 54, 37, 166,
|
||||
160, 161, 52, 49, 8, 50, 51, 53, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 31, 156,
|
||||
43, 16, 45, 30, 67, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 69, 166, 157, 36, 166, 162, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 158, 35, 159, 57, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 166, 166, 166, 166,
|
||||
166, 166, 166, 166, 166, 166, 1, 2, 3, 4,
|
||||
5, 6, 7, 9, 10, 11, 12, 13, 14, 15,
|
||||
17, 18, 19, 20, 21, 22, 23, 24, 25, 26,
|
||||
27, 28, 29, 32, 33, 34, 38, 39, 40, 41,
|
||||
@ -237,7 +238,7 @@ class Php7 extends \PhpParser\ParserAbstract
|
||||
124, 125, 126, 127, 128, 129, 130, 131, 132, 133,
|
||||
134, 135, 136, 137, 138, 139, 140, 141, 142, 143,
|
||||
144, 145, 146, 147, 148, 149, 150, 151, 152, 153,
|
||||
154, 155
|
||||
154, 155, 165
|
||||
);
|
||||
|
||||
protected $action = array(
|
||||
|
@ -141,4 +141,5 @@ final class Tokens
|
||||
const T_NAME_QUALIFIED = 389;
|
||||
const T_NAME_RELATIVE = 390;
|
||||
const T_ATTRIBUTE = 391;
|
||||
const T_ENUM = 392;
|
||||
}
|
||||
|
@ -313,6 +313,35 @@ class EmulativeTest extends LexerTest
|
||||
[Tokens::T_END_HEREDOC, " LABEL"],
|
||||
[ord(','), ','],
|
||||
]],
|
||||
// Enums use a contextual keyword
|
||||
['enum Foo {}', [
|
||||
[Tokens::T_ENUM, 'enum'],
|
||||
[Tokens::T_STRING, 'Foo'],
|
||||
[ord('{'), '{'],
|
||||
[ord('}'), '}'],
|
||||
]],
|
||||
['class Enum {}', [
|
||||
[Tokens::T_CLASS, 'class'],
|
||||
[Tokens::T_STRING, 'Enum'],
|
||||
[ord('{'), '{'],
|
||||
[ord('}'), '}'],
|
||||
]],
|
||||
['class Enum extends X {}', [
|
||||
[Tokens::T_CLASS, 'class'],
|
||||
[Tokens::T_STRING, 'Enum'],
|
||||
[Tokens::T_EXTENDS, 'extends'],
|
||||
[Tokens::T_STRING, 'X'],
|
||||
[ord('{'), '{'],
|
||||
[ord('}'), '}'],
|
||||
]],
|
||||
['class Enum implements X {}', [
|
||||
[Tokens::T_CLASS, 'class'],
|
||||
[Tokens::T_STRING, 'Enum'],
|
||||
[Tokens::T_IMPLEMENTS, 'implements'],
|
||||
[Tokens::T_STRING, 'X'],
|
||||
[ord('{'), '{'],
|
||||
[ord('}'), '}'],
|
||||
]],
|
||||
];
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user