uuf6429 / expression-language-tplstring
Template String support for Symfony Expression Language
Package info
github.com/uuf6429/expression-language-tplstring
pkg:composer/uuf6429/expression-language-tplstring
Requires
- php: ^7.4 || ^8
- symfony/expression-language: ^5.4 || ^6 || ^7 || ^8
Requires (Dev)
- ergebnis/composer-normalize: ^2.7
- phpstan/phpstan: ^2.1
- phpstan/phpstan-phpunit: ^2.0
- phpstan/phpstan-strict-rules: ^2.0
- phpunit/phpunit: ^9.5
This package is auto-updated.
Last update: 2026-07-05 17:18:47 UTC
README
for Symfony Expression Language (5-8)
What looks like a dot, a cross and a wave, and does the same thing?
It's the string concatenation operator, of course!
PHP uses a dot/period (
.), many languages including JavaScript use+, whereas Symfony Expression Language uses the tilde (~).
This library provides a translation layer on top of Expression Language that converts template strings in ES6 format* to a valid expression. While an updated Expression Language subclass wrapper is provided for convenience, you don't have to use it – you can use the provided trait instead.
* only ES6 string interpolation (with any expressions and nesting) is supported; f.e. tagged templates are not.
🔌 Installation
As always, the recommended and easiest way to install this library is through Composer:
composer require "uuf6429/expression-language-tplstring"
🚀 Usage
If you do not plan on extending Symfony Expression Language class, you can use the provided drop-in:
$el = new \uuf6429\ExpressionLanguage\ExpressionLanguageWithTplStr(); $result = $el->evaluate('`hello ${name}!`', ['name' => 'mars']); assert($result === 'hello mars!');
Otherwise, you can also use the provided trait:
use uuf6429\ExpressionLanguage\TemplateStringTranslatorTrait; use Symfony\Component\ExpressionLanguage\ExpressionLanguage as SymfonyExpressionLanguage; use Symfony\Component\ExpressionLanguage\ParsedExpression as SymfonyParsedExpression; class MyCustomExpressionLanguage { use TemplateStringTranslatorTrait; private SymfonyExpressionLanguage $base; public function __construct() { $this->base = new SymfonyExpressionLanguage(); } public function compile($expression, array $names = []): string { return $this->base->compile($this->processTemplateStrings($expression), $names); } public function evaluate($expression, array $values = []) { return $this->base->evaluate($this->processTemplateStrings($expression), $values); } } $el = new MyCustomExpressionLanguage(); $result = $el->evaluate('`hello ${name}!`', ['name' => 'world']); assert($result === 'hello world!');
🪆 Nested Template Strings
Since the translator uses a robust state machine, you can nest template strings infinitely:
$el = new \uuf6429\ExpressionLanguage\ExpressionLanguageWithTplStr(); $result = $el->evaluate( '`Hello ${user.isMember ? `VIP ${user.name}` : \'Guest\'}!`', [ 'user' => (object)[ 'isMember' => true, 'name' => 'John', ], ] ); assert($result === 'Hello VIP John!');
🚨 Robust Error Handling
Unmatched template boundaries (like unclosed backticks , or unclosed ${, or unclosed quotes '/") will
immediately trigger a Symfony\Component\ExpressionLanguage\SyntaxError with precise details and position:
$el = new \uuf6429\ExpressionLanguage\ExpressionLanguageWithTplStr(); try { $el->evaluate('`hello ${name'); } catch (\Symfony\Component\ExpressionLanguage\SyntaxError $e) { assert($e->getMessage() === 'Expected "}" around position 13 for expression ``hello ${name`.'); }