Search moodle.org's
Developer Documentation

See Release Notes

  • Bug fixes for general core bugs in 3.11.x will end 14 Nov 2022 (12 months plus 6 months extension).
  • Bug fixes for security issues in 3.11.x will end 13 Nov 2023 (18 months plus 12 months extension).
  • PHP version: minimum PHP 7.3.0 Note: minimum PHP version has increased since Moodle 3.10. PHP 7.4.x is supported too.

Differences Between: [Versions 311 and 401] [Versions 311 and 402] [Versions 311 and 403]

   1  <?php
   2  
   3  class HTMLPurifier_URIFilter_Munge extends HTMLPurifier_URIFilter
   4  {
   5      /**

   6       * @type string

   7       */
   8      public $name = 'Munge';
   9  
  10      /**

  11       * @type bool

  12       */
  13      public $post = true;
  14  
  15      /**

  16       * @type string

  17       */
  18      private $target;
  19  
  20      /**

  21       * @type HTMLPurifier_URIParser

  22       */
  23      private $parser;
  24  
  25      /**

  26       * @type bool

  27       */
  28      private $doEmbed;
  29  
  30      /**

  31       * @type string

  32       */
  33      private $secretKey;
  34  
  35      /**

  36       * @type array

  37       */
  38      protected $replace = array();
  39  
  40      /**

  41       * @param HTMLPurifier_Config $config

  42       * @return bool

  43       */
  44      public function prepare($config)
  45      {
  46          $this->target = $config->get('URI.' . $this->name);
  47          $this->parser = new HTMLPurifier_URIParser();
  48          $this->doEmbed = $config->get('URI.MungeResources');
  49          $this->secretKey = $config->get('URI.MungeSecretKey');
  50          if ($this->secretKey && !function_exists('hash_hmac')) {
  51              throw new Exception("Cannot use %URI.MungeSecretKey without hash_hmac support.");
  52          }
  53          return true;
  54      }
  55  
  56      /**

  57       * @param HTMLPurifier_URI $uri

  58       * @param HTMLPurifier_Config $config

  59       * @param HTMLPurifier_Context $context

  60       * @return bool

  61       */
  62      public function filter(&$uri, $config, $context)
  63      {
  64          if ($context->get('EmbeddedURI', true) && !$this->doEmbed) {
  65              return true;
  66          }
  67  
  68          $scheme_obj = $uri->getSchemeObj($config, $context);
  69          if (!$scheme_obj) {
  70              return true;
  71          } // ignore unknown schemes, maybe another postfilter did it

  72          if (!$scheme_obj->browsable) {
  73              return true;
  74          } // ignore non-browseable schemes, since we can't munge those in a reasonable way

  75          if ($uri->isBenign($config, $context)) {
  76              return true;
  77          } // don't redirect if a benign URL

  78  
  79          $this->makeReplace($uri, $config, $context);
  80          $this->replace = array_map('rawurlencode', $this->replace);
  81  
  82          $new_uri = strtr($this->target, $this->replace);
  83          $new_uri = $this->parser->parse($new_uri);
  84          // don't redirect if the target host is the same as the

  85          // starting host

  86          if ($uri->host === $new_uri->host) {
  87              return true;
  88          }
  89          $uri = $new_uri; // overwrite

  90          return true;
  91      }
  92  
  93      /**

  94       * @param HTMLPurifier_URI $uri

  95       * @param HTMLPurifier_Config $config

  96       * @param HTMLPurifier_Context $context

  97       */
  98      protected function makeReplace($uri, $config, $context)
  99      {
 100          $string = $uri->toString();
 101          // always available

 102          $this->replace['%s'] = $string;
 103          $this->replace['%r'] = $context->get('EmbeddedURI', true);
 104          $token = $context->get('CurrentToken', true);
 105          $this->replace['%n'] = $token ? $token->name : null;
 106          $this->replace['%m'] = $context->get('CurrentAttr', true);
 107          $this->replace['%p'] = $context->get('CurrentCSSProperty', true);
 108          // not always available

 109          if ($this->secretKey) {
 110              $this->replace['%t'] = hash_hmac("sha256", $string, $this->secretKey);
 111          }
 112      }
 113  }
 114  
 115  // vim: et sw=4 sts=4