'even' => new Twig_Filter_Function('twig_is_even_filter'),
'escape' => new Twig_Filter_Function('twig_escape_filter', array('needs_environment' => true)),
+ * added a way to specify variables to pass to an included template
* changed the automatic-escaping rules to be more sensible and more configurable in custom filters (the documentation lists all the rules)
* improved the filter system to allow object methods to be used as filters
* changed the Array and String loaders to actually make use of the cache mechanism
[twig]
{% include 'user.html' sandboxed %}
+You can also restrict the variables passed to the template by explicitly pass
+them as an array:
+
+ [twig]
+ {% include 'foo' with ['foo': 'bar'] %}
+
+ {% set vars as ['foo': 'bar'] %}
+ {% include 'foo' with vars %}
+
+The most secure way to include a template is to use both the `sandboxed` mode,
+and to pass the minimum amount of variables needed for the template to be
+rendered correctly:
+
+ [twig]
+ {% include 'foo' sandboxed with vars %}
+
+>**NOTE**
+>The `with` keyword is supported as of Twig 0.9.5.
+
### Import
Twig supports putting often used code into macros. These macros can go into
{
protected $expr;
protected $sandboxed;
+ protected $variables;
- public function __construct(Twig_Node_Expression $expr, $sandboxed, $lineno, $tag = null)
+ public function __construct(Twig_Node_Expression $expr, $sandboxed, $variables, $lineno, $tag = null)
{
parent::__construct($lineno, $tag);
$this->expr = $expr;
$this->sandboxed = $sandboxed;
+ $this->variables = $variables;
}
public function __toString()
{
if (!$compiler->getEnvironment()->hasExtension('sandbox') && $this->sandboxed)
{
- throw new Twig_SyntaxError('Unable to use the sanboxed attribute on an include if the sandbox extension is not enabled.');
+ throw new Twig_SyntaxError('Unable to use the sanboxed attribute on an include if the sandbox extension is not enabled.', $this->lineno);
}
$compiler->addDebugInfo($this);
$compiler
->write('$this->env->loadTemplate(')
->subcompile($this->expr)
- ->raw(')->display($context);'."\n")
+ ->raw(')->display(')
;
+ if (null === $this->variables)
+ {
+ $compiler->raw('$context');
+ }
+ else
+ {
+ $compiler->subcompile($this->variables);
+ }
+
+ $compiler->raw(");\n");
+
if ($this->sandboxed)
{
$compiler
$expr = $this->parser->getExpressionParser()->parseExpression();
$sandboxed = false;
- if ($this->parser->getStream()->test(Twig_Token::NAME_TYPE))
+ if ($this->parser->getStream()->test(Twig_Token::NAME_TYPE, 'sandboxed'))
{
- $this->parser->getStream()->expect(Twig_Token::NAME_TYPE);
+ $this->parser->getStream()->next();
$sandboxed = true;
}
+ $variables = null;
+ if ($this->parser->getStream()->test(Twig_Token::NAME_TYPE, 'with'))
+ {
+ $this->parser->getStream()->next();
+ $variables = $this->parser->getExpressionParser()->parseExpression();
+ }
+
$this->parser->getStream()->expect(Twig_Token::BLOCK_END_TYPE);
- return new Twig_Node_Include($expr, $sandboxed, $token->getLine(), $this->getTag());
+ return new Twig_Node_Include($expr, $sandboxed, $variables, $token->getLine(), $this->getTag());
}
public function getTag()
}
}
-$t = new LimeTest(58);
+$t = new LimeTest(59);
$fixturesDir = realpath(dirname(__FILE__).'/../fixtures/');
foreach (new RecursiveIteratorIterator(new RecursiveDirectoryIterator($fixturesDir), RecursiveIteratorIterator::LEAVES_ONLY) as $file)