Seditio Source
Root |
./othercms/phpBB3/vendor/s9e/text-formatter/src/Configurator/Items/Regexp.php
<?php

/**
* @package   s9e\TextFormatter
* @copyright Copyright (c) 2010-2021 The s9e authors
* @license   http://www.opensource.org/licenses/mit-license.php The MIT License
*/
namespace s9e\TextFormatter\Configurator\Items;

use
InvalidArgumentException;
use
s9e\TextFormatter\Configurator\ConfigProvider;
use
s9e\TextFormatter\Configurator\FilterableConfigValue;
use
s9e\TextFormatter\Configurator\Helpers\RegexpParser;
use
s9e\TextFormatter\Configurator\JavaScript\Code;
use
s9e\TextFormatter\Configurator\JavaScript\RegexpConvertor;

class
Regexp implements ConfigProvider, FilterableConfigValue
{
   
/**
    * @var bool Whether this regexp should have the global flag set in JavaScript
    */
   
protected $isGlobal;

   
/**
    * @var string JavaScript regexp, with delimiters and modifiers, e.g. "/foo/i"
    */
   
protected $jsRegexp;

   
/**
    * @var string PCRE regexp, with delimiters and modifiers, e.g. "/foo/i"
    */
   
protected $regexp;

   
/**
    * Constructor
    *
    * @param string $regexp   PCRE regexp, with delimiters and modifiers, e.g. "/foo/i"
    * @param bool   $isGlobal Whether this regexp should have the global flag set in JavaScript
    */
   
public function __construct($regexp, $isGlobal = false)
    {
        if (@
preg_match($regexp, '') === false)
        {
            throw new
InvalidArgumentException('Invalid regular expression ' . var_export($regexp, true));
        }

       
$this->regexp   = $regexp;
       
$this->isGlobal = $isGlobal;
    }

   
/**
    * Return this regexp as a string
    *
    * @return string
    */
   
public function __toString()
    {
        return
$this->regexp;
    }

   
/**
    * {@inheritdoc}
    */
   
public function asConfig()
    {
        return
$this;
    }

   
/**
    * {@inheritdoc}
    */
   
public function filterConfig($target)
    {
        return (
$target === 'JS') ? new Code($this->getJS()) : (string) $this;
    }

   
/**
    * Return the name of each capture in this regexp
    *
    * @return string[]
    */
   
public function getCaptureNames()
    {
        return
RegexpParser::getCaptureNames($this->regexp);
    }

   
/**
    * Return this regexp's JavaScript representation
    *
    * @return string
    */
   
public function getJS()
    {
        if (!isset(
$this->jsRegexp))
        {
           
$this->jsRegexp = RegexpConvertor::toJS($this->regexp, $this->isGlobal);
        }

        return
$this->jsRegexp;
    }

   
/**
    * Return all the named captures with a standalone regexp that matches them
    *
    * @return array Array of [capture name => regexp]
    */
   
public function getNamedCaptures()
    {
       
$captures   = [];
       
$regexpInfo = RegexpParser::parse($this->regexp);

       
// Prepare the start/end of the regexp and ensure that we use the D modifier
       
$start = $regexpInfo['delimiter'] . '^';
       
$end   = '$' . $regexpInfo['delimiter'] . $regexpInfo['modifiers'];
        if (
strpos($regexpInfo['modifiers'], 'D') === false)
        {
           
$end .= 'D';
        }

        foreach (
$this->getNamedCapturesExpressions($regexpInfo['tokens']) as $name => $expr)
        {
           
$captures[$name] = $start . $expr . $end;
        }

        return
$captures;
    }

   
/**
    * Return the expression used in each named capture
    *
    * @param  array[] $tokens
    * @return array
    */
   
protected function getNamedCapturesExpressions(array $tokens)
    {
       
$exprs = [];
        foreach (
$tokens as $token)
        {
            if (
$token['type'] !== 'capturingSubpatternStart' || !isset($token['name']))
            {
                continue;
            }

           
$expr = $token['content'];
            if (
strpos($expr, '|') !== false)
            {
               
$expr = '(?:' . $expr . ')';
            }

           
$exprs[$token['name']] = $expr;
        }

        return
$exprs;
    }

   
/**
    * Set this regexp's JavaScript representation
    *
    * @param  string $jsRegexp
    * @return void
    */
   
public function setJS($jsRegexp)
    {
       
$this->jsRegexp = $jsRegexp;
    }
}