abstract class Twig_Template

Default base class for compiled templates.

@package twig @author Fabien Potencier <fabien@symfony.com>

Hierarchy

Expanded class hierarchy of Twig_Template

2 string references to 'Twig_Template'
Twig_Environment::__construct in drupal/core/vendor/twig/twig/lib/Twig/Environment.php
Constructor.
Twig_Error::guessTemplateInfo in drupal/core/vendor/twig/twig/lib/Twig/Error.php

File

drupal/core/vendor/twig/twig/lib/Twig/Template.php, line 19

View source
abstract class Twig_Template implements Twig_TemplateInterface {
  protected static $cache = array();
  protected $parent;
  protected $parents;
  protected $env;
  protected $blocks;
  protected $traits;

  /**
   * Constructor.
   *
   * @param Twig_Environment $env A Twig_Environment instance
   */
  public function __construct(Twig_Environment $env) {
    $this->env = $env;
    $this->blocks = array();
    $this->traits = array();
  }

  /**
   * Returns the template name.
   *
   * @return string The template name
   */
  public abstract function getTemplateName();

  /**
   * {@inheritdoc}
   */
  public function getEnvironment() {
    return $this->env;
  }

  /**
   * Returns the parent template.
   *
   * This method is for internal use only and should never be called
   * directly.
   *
   * @return Twig_TemplateInterface|false The parent template or false if there is no parent
   */
  public function getParent(array $context) {
    if (null !== $this->parent) {
      return $this->parent;
    }
    $parent = $this
      ->doGetParent($context);
    if (false === $parent) {
      return false;
    }
    elseif ($parent instanceof Twig_Template) {
      $name = $parent
        ->getTemplateName();
      $this->parents[$name] = $parent;
      $parent = $name;
    }
    elseif (!isset($this->parents[$parent])) {
      $this->parents[$parent] = $this->env
        ->loadTemplate($parent);
    }
    return $this->parents[$parent];
  }
  protected function doGetParent(array $context) {
    return false;
  }
  public function isTraitable() {
    return true;
  }

  /**
   * Displays a parent block.
   *
   * This method is for internal use only and should never be called
   * directly.
   *
   * @param string $name    The block name to display from the parent
   * @param array  $context The context
   * @param array  $blocks  The current set of blocks
   */
  public function displayParentBlock($name, array $context, array $blocks = array()) {
    $name = (string) $name;
    if (isset($this->traits[$name])) {
      $this->traits[$name][0]
        ->displayBlock($name, $context, $blocks);
    }
    elseif (false !== ($parent = $this
      ->getParent($context))) {
      $parent
        ->displayBlock($name, $context, $blocks);
    }
    else {
      throw new Twig_Error_Runtime(sprintf('The template has no parent and no traits defining the "%s" block', $name), -1, $this
        ->getTemplateName());
    }
  }

  /**
   * Displays a block.
   *
   * This method is for internal use only and should never be called
   * directly.
   *
   * @param string $name    The block name to display
   * @param array  $context The context
   * @param array  $blocks  The current set of blocks
   */
  public function displayBlock($name, array $context, array $blocks = array()) {
    $name = (string) $name;
    if (isset($blocks[$name])) {
      $b = $blocks;
      unset($b[$name]);
      call_user_func($blocks[$name], $context, $b);
    }
    elseif (isset($this->blocks[$name])) {
      call_user_func($this->blocks[$name], $context, $blocks);
    }
    elseif (false !== ($parent = $this
      ->getParent($context))) {
      $parent
        ->displayBlock($name, $context, array_merge($this->blocks, $blocks));
    }
  }

  /**
   * Renders a parent block.
   *
   * This method is for internal use only and should never be called
   * directly.
   *
   * @param string $name    The block name to render from the parent
   * @param array  $context The context
   * @param array  $blocks  The current set of blocks
   *
   * @return string The rendered block
   */
  public function renderParentBlock($name, array $context, array $blocks = array()) {
    ob_start();
    $this
      ->displayParentBlock($name, $context, $blocks);
    return ob_get_clean();
  }

  /**
   * Renders a block.
   *
   * This method is for internal use only and should never be called
   * directly.
   *
   * @param string $name    The block name to render
   * @param array  $context The context
   * @param array  $blocks  The current set of blocks
   *
   * @return string The rendered block
   */
  public function renderBlock($name, array $context, array $blocks = array()) {
    ob_start();
    $this
      ->displayBlock($name, $context, $blocks);
    return ob_get_clean();
  }

  /**
   * Returns whether a block exists or not.
   *
   * This method is for internal use only and should never be called
   * directly.
   *
   * This method does only return blocks defined in the current template
   * or defined in "used" traits.
   *
   * It does not return blocks from parent templates as the parent
   * template name can be dynamic, which is only known based on the
   * current context.
   *
   * @param string $name The block name
   *
   * @return Boolean true if the block exists, false otherwise
   */
  public function hasBlock($name) {
    return isset($this->blocks[(string) $name]);
  }

  /**
   * Returns all block names.
   *
   * This method is for internal use only and should never be called
   * directly.
   *
   * @return array An array of block names
   *
   * @see hasBlock
   */
  public function getBlockNames() {
    return array_keys($this->blocks);
  }

  /**
   * Returns all blocks.
   *
   * This method is for internal use only and should never be called
   * directly.
   *
   * @return array An array of blocks
   *
   * @see hasBlock
   */
  public function getBlocks() {
    return $this->blocks;
  }

  /**
   * {@inheritdoc}
   */
  public function display(array $context, array $blocks = array()) {
    $this
      ->displayWithErrorHandling($this->env
      ->mergeGlobals($context), $blocks);
  }

  /**
   * {@inheritdoc}
   */
  public function render(array $context) {
    $level = ob_get_level();
    ob_start();
    try {
      $this
        ->display($context);
    } catch (Exception $e) {
      while (ob_get_level() > $level) {
        ob_end_clean();
      }
      throw $e;
    }
    return ob_get_clean();
  }
  protected function displayWithErrorHandling(array $context, array $blocks = array()) {
    try {
      $this
        ->doDisplay($context, $blocks);
    } catch (Twig_Error $e) {
      throw $e;
    } catch (Exception $e) {
      throw new Twig_Error_Runtime(sprintf('An exception has been thrown during the rendering of a template ("%s").', $e
        ->getMessage()), -1, null, $e);
    }
  }

  /**
   * Auto-generated method to display the template with the given context.
   *
   * @param array $context An array of parameters to pass to the template
   * @param array $blocks  An array of blocks to pass to the template
   */
  protected abstract function doDisplay(array $context, array $blocks = array());

  /**
   * Returns a variable from the context.
   *
   * This method is for internal use only and should never be called
   * directly.
   *
   * This method should not be overriden in a sub-class as this is an
   * implementation detail that has been introduced to optimize variable
   * access for versions of PHP before 5.4. This is not a way to override
   * the way to get a variable value.
   *
   * @param array   $context           The context
   * @param string  $item              The variable to return from the context
   * @param Boolean $ignoreStrictCheck Whether to ignore the strict variable check or not
   *
   * @return The content of the context variable
   *
   * @throws Twig_Error_Runtime if the variable does not exist and Twig is running in strict mode
   */
  protected final function getContext($context, $item, $ignoreStrictCheck = false) {
    if (!array_key_exists($item, $context)) {
      if ($ignoreStrictCheck || !$this->env
        ->isStrictVariables()) {
        return null;
      }
      throw new Twig_Error_Runtime(sprintf('Variable "%s" does not exist', $item));
    }
    return $context[$item];
  }

  /**
   * Returns the attribute value for a given array/object.
   *
   * @param mixed   $object            The object or array from where to get the item
   * @param mixed   $item              The item to get from the array or object
   * @param array   $arguments         An array of arguments to pass if the item is an object method
   * @param string  $type              The type of attribute (@see Twig_TemplateInterface)
   * @param Boolean $isDefinedTest     Whether this is only a defined check
   * @param Boolean $ignoreStrictCheck Whether to ignore the strict attribute check or not
   *
   * @return mixed The attribute value, or a Boolean when $isDefinedTest is true, or null when the attribute is not set and $ignoreStrictCheck is true
   *
   * @throws Twig_Error_Runtime if the attribute does not exist and Twig is running in strict mode and $isDefinedTest is false
   */
  protected function getAttribute($object, $item, array $arguments = array(), $type = Twig_TemplateInterface::ANY_CALL, $isDefinedTest = false, $ignoreStrictCheck = false) {
    $item = ctype_digit((string) $item) ? (int) $item : (string) $item;

    // array
    if (Twig_TemplateInterface::METHOD_CALL !== $type) {
      if (is_array($object) && array_key_exists($item, $object) || $object instanceof ArrayAccess && isset($object[$item])) {
        if ($isDefinedTest) {
          return true;
        }
        return $object[$item];
      }
      if (Twig_TemplateInterface::ARRAY_CALL === $type) {
        if ($isDefinedTest) {
          return false;
        }
        if ($ignoreStrictCheck || !$this->env
          ->isStrictVariables()) {
          return null;
        }
        if (is_object($object)) {
          throw new Twig_Error_Runtime(sprintf('Key "%s" in object (with ArrayAccess) of type "%s" does not exist', $item, get_class($object)));
        }
        elseif (is_array($object)) {
          throw new Twig_Error_Runtime(sprintf('Key "%s" for array with keys "%s" does not exist', $item, implode(', ', array_keys($object))));
        }
        else {
          throw new Twig_Error_Runtime(sprintf('Impossible to access a key ("%s") on a "%s" variable', $item, gettype($object)));
        }
      }
    }
    if (!is_object($object)) {
      if ($isDefinedTest) {
        return false;
      }
      if ($ignoreStrictCheck || !$this->env
        ->isStrictVariables()) {
        return null;
      }
      throw new Twig_Error_Runtime(sprintf('Item "%s" for "%s" does not exist', $item, is_array($object) ? 'Array' : $object));
    }
    $class = get_class($object);

    // object property
    if (Twig_TemplateInterface::METHOD_CALL !== $type) {
      if (isset($object->{$item}) || array_key_exists($item, $object)) {
        if ($isDefinedTest) {
          return true;
        }
        if ($this->env
          ->hasExtension('sandbox')) {
          $this->env
            ->getExtension('sandbox')
            ->checkPropertyAllowed($object, $item);
        }
        return $object->{$item};
      }
    }

    // object method
    if (!isset(self::$cache[$class]['methods'])) {
      self::$cache[$class]['methods'] = array_change_key_case(array_flip(get_class_methods($object)));
    }
    $lcItem = strtolower($item);
    if (isset(self::$cache[$class]['methods'][$lcItem])) {
      $method = $item;
    }
    elseif (isset(self::$cache[$class]['methods']['get' . $lcItem])) {
      $method = 'get' . $item;
    }
    elseif (isset(self::$cache[$class]['methods']['is' . $lcItem])) {
      $method = 'is' . $item;
    }
    elseif (isset(self::$cache[$class]['methods']['__call'])) {
      $method = $item;
    }
    else {
      if ($isDefinedTest) {
        return false;
      }
      if ($ignoreStrictCheck || !$this->env
        ->isStrictVariables()) {
        return null;
      }
      throw new Twig_Error_Runtime(sprintf('Method "%s" for object "%s" does not exist', $item, get_class($object)));
    }
    if ($isDefinedTest) {
      return true;
    }
    if ($this->env
      ->hasExtension('sandbox')) {
      $this->env
        ->getExtension('sandbox')
        ->checkMethodAllowed($object, $method);
    }
    $ret = call_user_func_array(array(
      $object,
      $method,
    ), $arguments);

    // hack to be removed when macro calls are refactored
    if ($object instanceof Twig_TemplateInterface) {
      return $ret === '' ? '' : new Twig_Markup($ret, $this->env
        ->getCharset());
    }
    return $ret;
  }

  /**
   * This method is only useful when testing Twig. Do not use it.
   */
  public static function clearCache() {
    self::$cache = array();
  }

}

Members

Namesort descending Modifiers Type Description Overrides
Twig_Template::$blocks protected property
Twig_Template::$cache protected static property
Twig_Template::$env protected property
Twig_Template::$parent protected property
Twig_Template::$parents protected property
Twig_Template::$traits protected property
Twig_Template::clearCache public static function This method is only useful when testing Twig. Do not use it.
Twig_Template::display public function Displays the template with the given context. Overrides Twig_TemplateInterface::display
Twig_Template::displayBlock public function Displays a block.
Twig_Template::displayParentBlock public function Displays a parent block.
Twig_Template::displayWithErrorHandling protected function
Twig_Template::doDisplay abstract protected function Auto-generated method to display the template with the given context. 1
Twig_Template::doGetParent protected function 1
Twig_Template::getAttribute protected function Returns the attribute value for a given array/object. 1
Twig_Template::getBlockNames public function Returns all block names.
Twig_Template::getBlocks public function Returns all blocks.
Twig_Template::getContext final protected function Returns a variable from the context.
Twig_Template::getEnvironment public function Returns the bound environment for this template. Overrides Twig_TemplateInterface::getEnvironment
Twig_Template::getParent public function Returns the parent template.
Twig_Template::getTemplateName abstract public function Returns the template name. 1
Twig_Template::hasBlock public function Returns whether a block exists or not.
Twig_Template::isTraitable public function
Twig_Template::render public function Renders the template with the given context and returns it as string. Overrides Twig_TemplateInterface::render
Twig_Template::renderBlock public function Renders a block.
Twig_Template::renderParentBlock public function Renders a parent block.
Twig_Template::__construct public function Constructor. 1
Twig_TemplateInterface::ANY_CALL constant
Twig_TemplateInterface::ARRAY_CALL constant
Twig_TemplateInterface::METHOD_CALL constant