New in Symfony 5.1: ExpressionLanguage validator
May 6, 2020 • Published by Javier Eguiluz
Warning: This post is about an unsupported Symfony version. Some of this information may be out of date. Read the most recent Symfony Docs.
The ExpressionLanguage component provides an engine to compile and evaluate
expressions. It's used by many companies to allow non-developers write business
rules (e.g. evaluate the following expression to decide if your store offers a
discount: 'user["isActive"] == true and product["price"] > 20'
).
In Symfony 5.1 we've improved the ExpressionLanguage component to allow
validating the expressions without parsing or evaluating them. The
ExpressionLanguage
and Parser
classes now include a lint()
method to
validate expressions:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20
use Symfony\Component\ExpressionLanguage\Lexer;
use Symfony\Component\ExpressionLanguage\Parser;
$lexer = new Lexer();
$parser = new Parser([]);
$parser->lint($lexer->tokenize($expression), $allowedVariableNames);
$expression = 'foo["some_key"].callFunction(a ? b)';
$allowedVariableNames = ['foo', 'a', 'b'];
// Result: no error; expression is valid.
$expression = 'foo["some_key")';
$allowedVariableNames = ['foo'];
// Result: Unclosed "[" around position 3 for expression `foo["some_key")`.
$expression = '{key: foo key2: bar}';
$allowedVariableNames = ['foo', 'bar'];
// Result: A hash value must be followed by a comma
// Unexpected token "name" of value "key2" ("punctuation" expected with value ",")
// around position 11 for expression `{key: foo key2: bar}`.
In addition to using these lint()
methods, you can also use the new
ExpressionLanguageSyntax
constraint to validate that the value stored in
some property defines valid ExpressionLanguage syntax (you can optionally
validate the expression variable names too):
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19
namespace App\Entity;
use Symfony\Component\Validator\Constraints as Assert;
class Order
{
/**
* @Assert\ExpressionLanguageSyntax()
*/
protected $promotion;
/**
* @Assert\ExpressionLanguageSyntax(
* names = ['user', 'shipping_centers'],
* validateNames = true
* )
*/
protected $shippingOptions;
}
Help the Symfony project!
As with any Open-Source project, contributing code or documentation is the most common way to help, but we also have a wide range of sponsoring opportunities.
Comments are closed.
To ensure that comments stay relevant, they are closed for old posts.