phpstan/phpdoc-parser now requires PHP 7.4 or newer to run.
Instead of different arrays and boolean values passed into class constructors during setup, parser classes now share a common ParserConfig object.
Before:
use PHPStan\PhpDocParser\Lexer\Lexer;
use PHPStan\PhpDocParser\Parser\ConstExprParser;
use PHPStan\PhpDocParser\Parser\TypeParser;
use PHPStan\PhpDocParser\Parser\PhpDocParser;
$usedAttributes = ['lines' => true, 'indexes' => true];
$lexer = new Lexer();
$constExprParser = new ConstExprParser(true, true, $usedAttributes);
$typeParser = new TypeParser($constExprParser, true, $usedAttributes);
$phpDocParser = new PhpDocParser($typeParser, $constExprParser, true, true, $usedAttributes);
After:
use PHPStan\PhpDocParser\Lexer\Lexer;
use PHPStan\PhpDocParser\ParserConfig;
use PHPStan\PhpDocParser\Parser\ConstExprParser;
use PHPStan\PhpDocParser\Parser\TypeParser;
use PHPStan\PhpDocParser\Parser\PhpDocParser;
$config = new ParserConfig(usedAttributes: ['lines' => true, 'indexes' => true]);
$lexer = new Lexer($config);
$constExprParser = new ConstExprParser($config);
$typeParser = new TypeParser($config, $constExprParser);
$phpDocParser = new PhpDocParser($config, $typeParser, $constExprParser);
The point of ParserConfig is that over the course of phpstan/phpdoc-parser 2.x development series it's most likely going to gain new optional parameters akin to PHPStan's bleeding edge. These parameters will allow opting in to new behaviour which will become the default in 3.0.
With ParserConfig object, it's now going to be impossible to configure parser classes inconsistently. Which happened to users when they were separate boolean values.
This parser now supports parsing Doctrine Annotations. The AST nodes representing Doctrine Annotations live in the PHPStan\PhpDocParser\Ast\PhpDoc\Doctrine namespace.
phpdoc-parser 1.x sometimes silently consumed invalid part of a PHPDoc type as description:
/** @return \Closure(...int, string): string */
This became IdentifierTypeNode
of \Closure
and with (...int, string): string
as description. (Valid callable syntax is: \Closure(int ...$u, string): string
.)
Another example:
/** @return array{foo: int}} */
The extra }
also became description.
Both of these examples are now InvalidTagValueNode.
If these parts are supposed to be PHPDoc descriptions, you need to put whitespace between the type and the description text:
/** @return \Closure (...int, string): string */
/** @return array{foo: int} } */
In phpdoc-parser 1.x, invalid type alias syntax was represented as InvalidTagValueNode
, losing information about a type alias being present.
/**
* @phpstan-type TypeAlias
*/
This @phpstan-type
is missing the actual type to alias. In phpdoc-parser 2.0 this is now represented as TypeAliasTagValueNode
(instead of InvalidTagValueNode
) with InvalidTypeNode
in place of the type.
The class QuoteAwareConstExprStringNode has been removed.
Instead, ConstExprStringNode gained information about the kind of quotes being used.
ConstExprStringNode::$value
now contains unescaped values without surrounding ''
or ""
quotes.
Use ConstExprStringNode::__toString()
or Printer
to get the escaped value along with surrounding quotes.
Multi-line descriptions between tags were previously represented as separate PhpDocTextNode:
/**
* @param Foo $foo 1st multi world description
* some text in the middle
* @param Bar $bar 2nd multi world description
*/
The line with some text in the middle
in phpdoc-parser 2.0 is now part of the description of the first @param
tag.
ArrayShapeNode
constructor made private, added public static methods createSealed()
and createUnsealed()
.
- Constructor parameter
$isEquality
inAssertTag*ValueNode
made required - Constructor parameter
$templateTypes
inMethodTagValueNode
made required - Constructor parameter
$isReference
inParamTagValueNode
made required - Constructor parameter
$isReference
inTypelessParamTagValueNode
made required - Constructor parameter
$templateTypes
inCallableTypeNode
made required - Constructor parameters
$expectedTokenValue
and$currentTokenLine
inParserException
made required ArrayShapeItemNode
andObjectShapeItemNode
are not standalone TypeNode, just Node