Skip to content

Commit f19cf8a

Browse files
committed
[ExpressionLanguage] make a proposal in SyntaxError message
1 parent 22c0028 commit f19cf8a

File tree

3 files changed

+30
-3
lines changed

3 files changed

+30
-3
lines changed

src/Symfony/Component/ExpressionLanguage/Parser.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -195,13 +195,13 @@ public function parsePrimaryExpression()
195195
default:
196196
if ('(' === $this->stream->current->value) {
197197
if (false === isset($this->functions[$token->value])) {
198-
throw new SyntaxError(sprintf('The function "%s" does not exist', $token->value), $token->cursor, $this->stream->getExpression());
198+
throw new SyntaxError(sprintf('The function "%s" does not exist', $token->value), $token->cursor, $this->stream->getExpression(), $token->value, array_keys($this->functions));
199199
}
200200

201201
$node = new Node\FunctionNode($token->value, $this->parseArguments());
202202
} else {
203203
if (!in_array($token->value, $this->names, true)) {
204-
throw new SyntaxError(sprintf('Variable "%s" is not valid', $token->value), $token->cursor, $this->stream->getExpression());
204+
throw new SyntaxError(sprintf('Variable "%s" is not valid', $token->value), $token->cursor, $this->stream->getExpression(), $token->value, $this->names);
205205
}
206206

207207
// is the name used in the compiled code different

src/Symfony/Component/ExpressionLanguage/SyntaxError.php

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,14 +13,29 @@
1313

1414
class SyntaxError extends \LogicException
1515
{
16-
public function __construct($message, $cursor = 0, $expression = '')
16+
public function __construct($message, $cursor = 0, $expression = '', $subject = null, array $proposals = null)
1717
{
1818
$message = sprintf('%s around position %d', $message, $cursor);
1919
if ($expression) {
2020
$message = sprintf('%s for expression `%s`', $message, $expression);
2121
}
2222
$message .= '.';
2323

24+
if (null !== $subject && null !== $proposals) {
25+
$minScore = INF;
26+
foreach ($proposals as $proposal) {
27+
$distance = levenshtein($subject, $proposal);
28+
if ($distance < $minScore) {
29+
$guess = $proposal;
30+
$minScore = $distance;
31+
}
32+
}
33+
34+
if (isset($guess) && $minScore < 3) {
35+
$message .= sprintf(' Did you mean "%s"?', $guess);
36+
}
37+
}
38+
2439
parent::__construct($message);
2540
}
2641
}

src/Symfony/Component/ExpressionLanguage/Tests/ParserTest.php

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -195,4 +195,16 @@ public function getInvalidPostfixData()
195195
),
196196
);
197197
}
198+
199+
/**
200+
* @expectedException \Symfony\Component\ExpressionLanguage\SyntaxError
201+
* @expectedExceptionMessage Did you mean "baz"?
202+
*/
203+
public function testNameProposal()
204+
{
205+
$lexer = new Lexer();
206+
$parser = new Parser(array());
207+
208+
$parser->parse($lexer->tokenize('foo > bar'), array('foo', 'baz'));
209+
}
198210
}

0 commit comments

Comments
 (0)