mirror of
https://github.com/twigphp/Twig.git
synced 2026-09-15 20:06:31 +00:00
added the starts with, ends with, and matches operators
This commit is contained in:
@@ -1,5 +1,6 @@
|
||||
* 1.14.0 (2013-XX-XX)
|
||||
|
||||
* added new operators: ends with, starts with, and matches
|
||||
* fixed some compatibility issues with HHVM
|
||||
* added a way to add custom escaping strategies
|
||||
* fixed the C extension compilation on Windows
|
||||
|
||||
+27
-5
@@ -586,9 +586,9 @@ even if you're not working with PHP you should feel comfortable with it.
|
||||
|
||||
The operator precedence is as follows, with the lowest-precedence
|
||||
operators listed first: ``b-and``, ``b-xor``, ``b-or``, ``or``, ``and``,
|
||||
``==``, ``!=``, ``<``, ``>``, ``>=``, ``<=``, ``in``, ``..``, ``+``,
|
||||
``-``, ``~``, ``*``, ``/``, ``//``, ``%``, ``is``, ``**``, ``|``, ``[]``,
|
||||
and ``.``:
|
||||
``==``, ``!=``, ``<``, ``>``, ``>=``, ``<=``, ``in``, ``matches``,
|
||||
``starts with``, ``ends with``, ``..``, ``+``, ``-``, ``~``, ``*``, ``/``,
|
||||
``//``, ``%``, ``is``, ``**``, ``|``, ``[]``, and ``.``:
|
||||
|
||||
.. code-block:: jinja
|
||||
|
||||
@@ -707,6 +707,27 @@ Comparisons
|
||||
The following comparison operators are supported in any expression: ``==``,
|
||||
``!=``, ``<``, ``>``, ``>=``, and ``<=``.
|
||||
|
||||
You can also check if a string ``starts with`` or ``ends with`` another
|
||||
string:
|
||||
|
||||
.. code-block:: jinja
|
||||
|
||||
{% if 'Fabien' starts with 'F' %}
|
||||
{% endif %}
|
||||
|
||||
{% if 'Fabien' ends with 'n' %}
|
||||
{% endif %}
|
||||
|
||||
.. note::
|
||||
|
||||
For complex string comparisons, the ``matches`` operator allows you to use
|
||||
`regular expressions`_:
|
||||
|
||||
.. code-block:: jinja
|
||||
|
||||
{% if phone matches '{^[\d\.]+$}' %}
|
||||
{% endif %}
|
||||
|
||||
Containment Operator
|
||||
~~~~~~~~~~~~~~~~~~~~
|
||||
|
||||
@@ -794,8 +815,8 @@ categories:
|
||||
{{ foo ? 'yes' : 'no' }}
|
||||
|
||||
{# as of Twig 1.12.0 #}
|
||||
{{ foo ?: 'no' }} == {{ foo ? foo : 'no' }}
|
||||
{{ foo ? 'yes' }} == {{ foo ? 'yes' : '' }}
|
||||
{{ foo ?: 'no' }} is the same as {{ foo ? foo : 'no' }}
|
||||
{{ foo ? 'yes' }} is the same as {{ foo ? 'yes' : '' }}
|
||||
|
||||
String Interpolation
|
||||
~~~~~~~~~~~~~~~~~~~~
|
||||
@@ -882,3 +903,4 @@ Extension<creating_extensions>` chapter.
|
||||
.. _`other Twig syntax mode`: https://github.com/muxx/Twig-HTML.mode
|
||||
.. _`Notepad++ Twig Highlighter`: https://github.com/Banane9/notepadplusplus-twig
|
||||
.. _`web-mode.el`: http://web-mode.org/
|
||||
.. _`regular expressions`: http://php.net/manual/en/pcre.pattern.php
|
||||
|
||||
+27
-24
@@ -253,30 +253,33 @@ class Twig_Extension_Core extends Twig_Extension
|
||||
'+' => array('precedence' => 500, 'class' => 'Twig_Node_Expression_Unary_Pos'),
|
||||
),
|
||||
array(
|
||||
'or' => array('precedence' => 10, 'class' => 'Twig_Node_Expression_Binary_Or', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'and' => array('precedence' => 15, 'class' => 'Twig_Node_Expression_Binary_And', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'b-or' => array('precedence' => 16, 'class' => 'Twig_Node_Expression_Binary_BitwiseOr', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'b-xor' => array('precedence' => 17, 'class' => 'Twig_Node_Expression_Binary_BitwiseXor', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'b-and' => array('precedence' => 18, 'class' => 'Twig_Node_Expression_Binary_BitwiseAnd', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'==' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_Equal', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'!=' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_NotEqual', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'<' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_Less', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'>' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_Greater', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'>=' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_GreaterEqual', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'<=' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_LessEqual', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'not in' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_NotIn', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'in' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_In', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'..' => array('precedence' => 25, 'class' => 'Twig_Node_Expression_Binary_Range', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'+' => array('precedence' => 30, 'class' => 'Twig_Node_Expression_Binary_Add', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'-' => array('precedence' => 30, 'class' => 'Twig_Node_Expression_Binary_Sub', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'~' => array('precedence' => 40, 'class' => 'Twig_Node_Expression_Binary_Concat', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'*' => array('precedence' => 60, 'class' => 'Twig_Node_Expression_Binary_Mul', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'/' => array('precedence' => 60, 'class' => 'Twig_Node_Expression_Binary_Div', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'//' => array('precedence' => 60, 'class' => 'Twig_Node_Expression_Binary_FloorDiv', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'%' => array('precedence' => 60, 'class' => 'Twig_Node_Expression_Binary_Mod', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'is' => array('precedence' => 100, 'callable' => array($this, 'parseTestExpression'), 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'is not' => array('precedence' => 100, 'callable' => array($this, 'parseNotTestExpression'), 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'**' => array('precedence' => 200, 'class' => 'Twig_Node_Expression_Binary_Power', 'associativity' => Twig_ExpressionParser::OPERATOR_RIGHT),
|
||||
'or' => array('precedence' => 10, 'class' => 'Twig_Node_Expression_Binary_Or', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'and' => array('precedence' => 15, 'class' => 'Twig_Node_Expression_Binary_And', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'b-or' => array('precedence' => 16, 'class' => 'Twig_Node_Expression_Binary_BitwiseOr', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'b-xor' => array('precedence' => 17, 'class' => 'Twig_Node_Expression_Binary_BitwiseXor', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'b-and' => array('precedence' => 18, 'class' => 'Twig_Node_Expression_Binary_BitwiseAnd', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'==' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_Equal', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'!=' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_NotEqual', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'<' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_Less', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'>' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_Greater', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'>=' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_GreaterEqual', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'<=' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_LessEqual', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'not in' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_NotIn', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'in' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_In', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'matches' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_Matches', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'starts with' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_StartsWith', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'ends with' => array('precedence' => 20, 'class' => 'Twig_Node_Expression_Binary_EndsWith', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'..' => array('precedence' => 25, 'class' => 'Twig_Node_Expression_Binary_Range', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'+' => array('precedence' => 30, 'class' => 'Twig_Node_Expression_Binary_Add', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'-' => array('precedence' => 30, 'class' => 'Twig_Node_Expression_Binary_Sub', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'~' => array('precedence' => 40, 'class' => 'Twig_Node_Expression_Binary_Concat', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'*' => array('precedence' => 60, 'class' => 'Twig_Node_Expression_Binary_Mul', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'/' => array('precedence' => 60, 'class' => 'Twig_Node_Expression_Binary_Div', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'//' => array('precedence' => 60, 'class' => 'Twig_Node_Expression_Binary_FloorDiv', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'%' => array('precedence' => 60, 'class' => 'Twig_Node_Expression_Binary_Mod', 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'is' => array('precedence' => 100, 'callable' => array($this, 'parseTestExpression'), 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'is not' => array('precedence' => 100, 'callable' => array($this, 'parseNotTestExpression'), 'associativity' => Twig_ExpressionParser::OPERATOR_LEFT),
|
||||
'**' => array('precedence' => 200, 'class' => 'Twig_Node_Expression_Binary_Power', 'associativity' => Twig_ExpressionParser::OPERATOR_RIGHT),
|
||||
),
|
||||
);
|
||||
}
|
||||
|
||||
@@ -0,0 +1,30 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of Twig.
|
||||
*
|
||||
* (c) 2013 Fabien Potencier
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
class Twig_Node_Expression_Binary_EndsWith extends Twig_Node_Expression_Binary
|
||||
{
|
||||
public function compile(Twig_Compiler $compiler)
|
||||
{
|
||||
$compiler
|
||||
->raw('(0 === substr_compare(')
|
||||
->subcompile($this->getNode('left'))
|
||||
->raw(', ')
|
||||
->subcompile($this->getNode('right'))
|
||||
->raw(', -strlen(')
|
||||
->subcompile($this->getNode('right'))
|
||||
->raw(')))')
|
||||
;
|
||||
}
|
||||
|
||||
public function operator(Twig_Compiler $compiler)
|
||||
{
|
||||
return $compiler->raw('');
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,28 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of Twig.
|
||||
*
|
||||
* (c) 2013 Fabien Potencier
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
class Twig_Node_Expression_Binary_Matches extends Twig_Node_Expression_Binary
|
||||
{
|
||||
public function compile(Twig_Compiler $compiler)
|
||||
{
|
||||
$compiler
|
||||
->raw('preg_match(')
|
||||
->subcompile($this->getNode('right'))
|
||||
->raw(', ')
|
||||
->subcompile($this->getNode('left'))
|
||||
->raw(')')
|
||||
;
|
||||
}
|
||||
|
||||
public function operator(Twig_Compiler $compiler)
|
||||
{
|
||||
return $compiler->raw('');
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,28 @@
|
||||
<?php
|
||||
|
||||
/*
|
||||
* This file is part of Twig.
|
||||
*
|
||||
* (c) 2013 Fabien Potencier
|
||||
*
|
||||
* For the full copyright and license information, please view the LICENSE
|
||||
* file that was distributed with this source code.
|
||||
*/
|
||||
class Twig_Node_Expression_Binary_StartsWith extends Twig_Node_Expression_Binary
|
||||
{
|
||||
public function compile(Twig_Compiler $compiler)
|
||||
{
|
||||
$compiler
|
||||
->raw('(0 === strpos(')
|
||||
->subcompile($this->getNode('left'))
|
||||
->raw(', ')
|
||||
->subcompile($this->getNode('right'))
|
||||
->raw('))')
|
||||
;
|
||||
}
|
||||
|
||||
public function operator(Twig_Compiler $compiler)
|
||||
{
|
||||
return $compiler->raw('');
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,12 @@
|
||||
--TEST--
|
||||
Twig supports the "ends with" operator
|
||||
--TEMPLATE--
|
||||
{{ 'foo' ends with 'o' ? 'OK' : 'KO' }}
|
||||
{{ not ('foo' ends with 'f') ? 'OK' : 'KO' }}
|
||||
{{ not ('foo' ends with 'foowaytoolong') ? 'OK' : 'KO' }}
|
||||
--DATA--
|
||||
return array()
|
||||
--EXPECT--
|
||||
OK
|
||||
OK
|
||||
OK
|
||||
@@ -0,0 +1,12 @@
|
||||
--TEST--
|
||||
Twig supports the "matches" operator
|
||||
--TEMPLATE--
|
||||
{{ 'foo' matches '/o/' ? 'OK' : 'KO' }}
|
||||
{{ 'foo' matches '/^fo/' ? 'OK' : 'KO' }}
|
||||
{{ 'foo' matches '/O/i' ? 'OK' : 'KO' }}
|
||||
--DATA--
|
||||
return array()
|
||||
--EXPECT--
|
||||
OK
|
||||
OK
|
||||
OK
|
||||
@@ -0,0 +1,12 @@
|
||||
--TEST--
|
||||
Twig supports the "starts with" operator
|
||||
--TEMPLATE--
|
||||
{{ 'foo' starts with 'f' ? 'OK' : 'KO' }}
|
||||
{{ not ('foo' starts with 'oo') ? 'OK' : 'KO' }}
|
||||
{{ not ('foo' starts with 'foowaytoolong') ? 'OK' : 'KO' }}
|
||||
--DATA--
|
||||
return array()
|
||||
--EXPECT--
|
||||
OK
|
||||
OK
|
||||
OK
|
||||
Reference in New Issue
Block a user