Skip to content

Commit

Permalink
Fix two bugs in InvalidDotOperation inspection
Browse files Browse the repository at this point in the history
  • Loading branch information
drjayvee committed Oct 23, 2024
1 parent 1316748 commit a7ce2fa
Show file tree
Hide file tree
Showing 2 changed files with 35 additions and 3 deletions.
14 changes: 11 additions & 3 deletions src/Inspection/InvalidDotOperation.php
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,8 @@
use AlisQI\TwigQI\Helper\VariableTypeCollector;
use Twig\Environment;
use Twig\Node\Expression\GetAttrExpression;
use Twig\Node\Expression\NameExpression;
use Twig\Node\ModuleNode;
use Twig\Node\Node;
use Twig\Node\TypesNode;
use Twig\NodeVisitor\NodeVisitorInterface;
Expand All @@ -21,7 +23,7 @@ class InvalidDotOperation implements NodeVisitorInterface
'boolean',
];

private readonly VariableTypeCollector $variableTypeCollector;
private VariableTypeCollector $variableTypeCollector;

public function __construct()
{
Expand All @@ -30,16 +32,22 @@ public function __construct()

public function enterNode(Node $node, Environment $env): Node
{
// reset state between templates
if ($node instanceof ModuleNode) {
$this->variableTypeCollector = new VariableTypeCollector();
}

if ($node instanceof TypesNode) {
$this->variableTypeCollector->add($node);
}

if (
$node instanceof GetAttrExpression &&
$node->getAttribute('type') !== Template::ARRAY_CALL
$node->getAttribute('type') !== Template::ARRAY_CALL &&
($nameNode = $node->getNode('node')) instanceof NameExpression
) {
$location = new NodeLocation($node);
$name = $node->getNode('node')->getAttribute('name');
$name = $nameNode->getAttribute('name');
$attribute = $node->getNode('attribute')->getAttribute('value');
$this->checkOperation($name, $attribute, $location);
}
Expand Down
24 changes: 24 additions & 0 deletions tests/InvalidDotOperationTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,19 @@

class InvalidDotOperationTest extends AbstractTestCase
{
public function test_itIgnoresAttributesOnExpressions(): void
{
$this->env->createTemplate(<<<EOF
{{ ([]|first).bad }}
{{ (this ?: that).bad }}
EOF);

self::assertEmpty(
$this->errors,
implode(', ', $this->errors)
);
}

public function test_itIgnoresUndeclaredVariables(): void
{
$this->env->createTemplate(<<<EOF
Expand Down Expand Up @@ -42,4 +55,15 @@ public function test_itDetectsDotOperatorOnUnsupportedTypes(string $type): void
"Error should trigger when using dot operator for type '$type'"
);
}

public function test_itSupportsTemplateScope(): void
{
$this->env->createTemplate("{% types {foo: 'string'} %}");
$this->env->createTemplate("{{ foo.bad }}"); // this is a separate template: types must not carry over!

self::assertEmpty(
$this->errors,
implode(', ', $this->errors)
);
}
}

0 comments on commit a7ce2fa

Please sign in to comment.