Search moodle.org's
Developer Documentation

See Release Notes
Long Term Support Release

  • Bug fixes for general core bugs in 3.9.x will end* 10 May 2021 (12 months).
  • Bug fixes for security issues in 3.9.x will end* 8 May 2023 (36 months).
  • PHP version: minimum PHP 7.2.0 Note: minimum PHP version has increased since Moodle 3.8. PHP 7.3.x and 7.4.x are supported too.
   1  <?php
   2  
   3  /**

   4   * Definition that allows a set of elements, but disallows empty children.

   5   */
   6  class HTMLPurifier_ChildDef_Required extends HTMLPurifier_ChildDef
   7  {
   8      /**

   9       * Lookup table of allowed elements.

  10       * @type array

  11       */
  12      public $elements = array();
  13  
  14      /**

  15       * Whether or not the last passed node was all whitespace.

  16       * @type bool

  17       */
  18      protected $whitespace = false;
  19  
  20      /**

  21       * @param array|string $elements List of allowed element names (lowercase).

  22       */
  23      public function __construct($elements)
  24      {
  25          if (is_string($elements)) {
  26              $elements = str_replace(' ', '', $elements);
  27              $elements = explode('|', $elements);
  28          }
  29          $keys = array_keys($elements);
  30          if ($keys == array_keys($keys)) {
  31              $elements = array_flip($elements);
  32              foreach ($elements as $i => $x) {
  33                  $elements[$i] = true;
  34                  if (empty($i)) {
  35                      unset($elements[$i]);
  36                  } // remove blank

  37              }
  38          }
  39          $this->elements = $elements;
  40      }
  41  
  42      /**

  43       * @type bool

  44       */
  45      public $allow_empty = false;
  46  
  47      /**

  48       * @type string

  49       */
  50      public $type = 'required';
  51  
  52      /**

  53       * @param array $children

  54       * @param HTMLPurifier_Config $config

  55       * @param HTMLPurifier_Context $context

  56       * @return array

  57       */
  58      public function validateChildren($children, $config, $context)
  59      {
  60          // Flag for subclasses

  61          $this->whitespace = false;
  62  
  63          // if there are no tokens, delete parent node

  64          if (empty($children)) {
  65              return false;
  66          }
  67  
  68          // the new set of children

  69          $result = array();
  70  
  71          // whether or not parsed character data is allowed

  72          // this controls whether or not we silently drop a tag

  73          // or generate escaped HTML from it

  74          $pcdata_allowed = isset($this->elements['#PCDATA']);
  75  
  76          // a little sanity check to make sure it's not ALL whitespace

  77          $all_whitespace = true;
  78  
  79          $stack = array_reverse($children);
  80          while (!empty($stack)) {
  81              $node = array_pop($stack);
  82              if (!empty($node->is_whitespace)) {
  83                  $result[] = $node;
  84                  continue;
  85              }
  86              $all_whitespace = false; // phew, we're not talking about whitespace

  87  
  88              if (!isset($this->elements[$node->name])) {
  89                  // special case text

  90                  // XXX One of these ought to be redundant or something

  91                  if ($pcdata_allowed && $node instanceof HTMLPurifier_Node_Text) {
  92                      $result[] = $node;
  93                      continue;
  94                  }
  95                  // spill the child contents in

  96                  // ToDo: Make configurable

  97                  if ($node instanceof HTMLPurifier_Node_Element) {
  98                      for ($i = count($node->children) - 1; $i >= 0; $i--) {
  99                          $stack[] = $node->children[$i];
 100                      }
 101                      continue;
 102                  }
 103                  continue;
 104              }
 105              $result[] = $node;
 106          }
 107          if (empty($result)) {
 108              return false;
 109          }
 110          if ($all_whitespace) {
 111              $this->whitespace = true;
 112              return false;
 113          }
 114          return $result;
 115      }
 116  }
 117  
 118  // vim: et sw=4 sts=4