From c1c76539cc2878c058de15892dd05d6dd8b4b9a5 Mon Sep 17 00:00:00 2001 From: Bart Visscher Date: Sat, 27 Oct 2012 16:24:24 +0200 Subject: [PATCH] Include copy of Symfony routing component, and don't use composer --- .gitignore | 4 - 3rdparty/bin/composer | Bin 631359 -> 0 bytes .../Component/Routing/Annotation/Route.php | 103 ++++++ .../Component/Routing/CompiledRoute.php | 134 ++++++++ .../Routing/Exception/ExceptionInterface.php | 23 ++ .../Exception/InvalidParameterException.php | 23 ++ .../Exception/MethodNotAllowedException.php | 38 +++ .../MissingMandatoryParametersException.php | 24 ++ .../Exception/ResourceNotFoundException.php | 25 ++ .../Exception/RouteNotFoundException.php | 23 ++ .../Generator/Dumper/GeneratorDumper.php | 39 +++ .../Dumper/GeneratorDumperInterface.php | 45 +++ .../Generator/Dumper/PhpGeneratorDumper.php | 150 +++++++++ .../Routing/Generator/UrlGenerator.php | 176 ++++++++++ .../Generator/UrlGeneratorInterface.php | 37 +++ .../routing/Symfony/Component/Routing/LICENSE | 19 ++ .../Routing/Loader/AnnotationClassLoader.php | 213 ++++++++++++ .../Loader/AnnotationDirectoryLoader.php | 77 +++++ .../Routing/Loader/AnnotationFileLoader.php | 125 +++++++ .../Routing/Loader/ClosureLoader.php | 54 +++ .../Routing/Loader/PhpFileLoader.php | 64 ++++ .../Routing/Loader/XmlFileLoader.php | 224 +++++++++++++ .../Routing/Loader/YamlFileLoader.php | 142 ++++++++ .../Loader/schema/routing/routing-1.0.xsd | 38 +++ .../Routing/Matcher/ApacheUrlMatcher.php | 76 +++++ .../Matcher/Dumper/ApacheMatcherDumper.php | 155 +++++++++ .../Routing/Matcher/Dumper/MatcherDumper.php | 44 +++ .../Matcher/Dumper/MatcherDumperInterface.php | 41 +++ .../Matcher/Dumper/PhpMatcherDumper.php | 293 ++++++++++++++++ .../Matcher/RedirectableUrlMatcher.php | 53 +++ .../RedirectableUrlMatcherInterface.php | 35 ++ .../Component/Routing/Matcher/UrlMatcher.php | 151 +++++++++ .../Routing/Matcher/UrlMatcherInterface.php | 38 +++ .../Symfony/Component/Routing/README.md | 32 ++ .../Component/Routing/RequestContext.php | 250 ++++++++++++++ .../Routing/RequestContextAwareInterface.php | 27 ++ .../Symfony/Component/Routing/Route.php | 312 ++++++++++++++++++ .../Component/Routing/RouteCollection.php | 259 +++++++++++++++ .../Component/Routing/RouteCompiler.php | 128 +++++++ .../Routing/RouteCompilerInterface.php | 29 ++ .../Symfony/Component/Routing/Router.php | 263 +++++++++++++++ .../Component/Routing/RouterInterface.php | 26 ++ .../Symfony/Component/Routing/composer.json | 29 ++ composer.json | 18 - 44 files changed, 4037 insertions(+), 22 deletions(-) delete mode 100755 3rdparty/bin/composer create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Annotation/Route.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/CompiledRoute.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Exception/ExceptionInterface.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Exception/InvalidParameterException.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Exception/MethodNotAllowedException.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Exception/MissingMandatoryParametersException.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Exception/ResourceNotFoundException.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Exception/RouteNotFoundException.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/GeneratorDumper.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/GeneratorDumperInterface.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/PhpGeneratorDumper.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Generator/UrlGenerator.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Generator/UrlGeneratorInterface.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/LICENSE create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationClassLoader.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationDirectoryLoader.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationFileLoader.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Loader/ClosureLoader.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Loader/PhpFileLoader.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Loader/XmlFileLoader.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Loader/YamlFileLoader.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Loader/schema/routing/routing-1.0.xsd create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/ApacheUrlMatcher.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/ApacheMatcherDumper.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/MatcherDumper.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/MatcherDumperInterface.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/PhpMatcherDumper.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/RedirectableUrlMatcher.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/RedirectableUrlMatcherInterface.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/UrlMatcher.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/UrlMatcherInterface.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/README.md create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/RequestContext.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/RequestContextAwareInterface.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Route.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/RouteCollection.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/RouteCompiler.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/RouteCompilerInterface.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/Router.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/RouterInterface.php create mode 100644 3rdparty/symfony/routing/Symfony/Component/Routing/composer.json delete mode 100644 composer.json diff --git a/.gitignore b/.gitignore index 4ae39ed7fac..4749dea19dc 100644 --- a/.gitignore +++ b/.gitignore @@ -54,7 +54,3 @@ nbproject # WebFinger .well-known /.buildpath -3rdparty/autoload.php -3rdparty/composer/ -3rdparty/symfony/ -composer.lock diff --git a/3rdparty/bin/composer b/3rdparty/bin/composer deleted file mode 100755 index 7999bd4ff6875d721d50c01d28e4b371c78d21d6..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 631359 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≧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

J{fW+SfXRq-eaET&qYo^DAbnH>1R3g` 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 diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Annotation/Route.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Annotation/Route.php new file mode 100644 index 00000000000..f60af463f2c --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Annotation/Route.php @@ -0,0 +1,103 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Annotation; + +/** + * Annotation class for @Route(). + * + * @Annotation + * + * @author Fabien Potencier + */ +class Route +{ + private $pattern; + private $name; + private $requirements; + private $options; + private $defaults; + + /** + * Constructor. + * + * @param array $data An array of key/value parameters. + */ + public function __construct(array $data) + { + $this->requirements = array(); + $this->options = array(); + $this->defaults = array(); + + if (isset($data['value'])) { + $data['pattern'] = $data['value']; + unset($data['value']); + } + + foreach ($data as $key => $value) { + $method = 'set'.$key; + if (!method_exists($this, $method)) { + throw new \BadMethodCallException(sprintf("Unknown property '%s' on annotation '%s'.", $key, get_class($this))); + } + $this->$method($value); + } + } + + public function setPattern($pattern) + { + $this->pattern = $pattern; + } + + public function getPattern() + { + return $this->pattern; + } + + public function setName($name) + { + $this->name = $name; + } + + public function getName() + { + return $this->name; + } + + public function setRequirements($requirements) + { + $this->requirements = $requirements; + } + + public function getRequirements() + { + return $this->requirements; + } + + public function setOptions($options) + { + $this->options = $options; + } + + public function getOptions() + { + return $this->options; + } + + public function setDefaults($defaults) + { + $this->defaults = $defaults; + } + + public function getDefaults() + { + return $this->defaults; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/CompiledRoute.php b/3rdparty/symfony/routing/Symfony/Component/Routing/CompiledRoute.php new file mode 100644 index 00000000000..c86c9eca5b2 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/CompiledRoute.php @@ -0,0 +1,134 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing; + +/** + * CompiledRoutes are returned by the RouteCompiler class. + * + * @author Fabien Potencier + */ +class CompiledRoute +{ + private $route; + private $variables; + private $tokens; + private $staticPrefix; + private $regex; + + /** + * Constructor. + * + * @param Route $route A original Route instance + * @param string $staticPrefix The static prefix of the compiled route + * @param string $regex The regular expression to use to match this route + * @param array $tokens An array of tokens to use to generate URL for this route + * @param array $variables An array of variables + */ + public function __construct(Route $route, $staticPrefix, $regex, array $tokens, array $variables) + { + $this->route = $route; + $this->staticPrefix = $staticPrefix; + $this->regex = $regex; + $this->tokens = $tokens; + $this->variables = $variables; + } + + /** + * Returns the Route instance. + * + * @return Route A Route instance + */ + public function getRoute() + { + return $this->route; + } + + /** + * Returns the static prefix. + * + * @return string The static prefix + */ + public function getStaticPrefix() + { + return $this->staticPrefix; + } + + /** + * Returns the regex. + * + * @return string The regex + */ + public function getRegex() + { + return $this->regex; + } + + /** + * Returns the tokens. + * + * @return array The tokens + */ + public function getTokens() + { + return $this->tokens; + } + + /** + * Returns the variables. + * + * @return array The variables + */ + public function getVariables() + { + return $this->variables; + } + + /** + * Returns the pattern. + * + * @return string The pattern + */ + public function getPattern() + { + return $this->route->getPattern(); + } + + /** + * Returns the options. + * + * @return array The options + */ + public function getOptions() + { + return $this->route->getOptions(); + } + + /** + * Returns the defaults. + * + * @return array The defaults + */ + public function getDefaults() + { + return $this->route->getDefaults(); + } + + /** + * Returns the requirements. + * + * @return array The requirements + */ + public function getRequirements() + { + return $this->route->getRequirements(); + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/ExceptionInterface.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/ExceptionInterface.php new file mode 100644 index 00000000000..5289f525fcd --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/ExceptionInterface.php @@ -0,0 +1,23 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Exception; + +/** + * ExceptionInterface + * + * @author Alexandre Salomé + * + * @api + */ +interface ExceptionInterface +{ +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/InvalidParameterException.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/InvalidParameterException.php new file mode 100644 index 00000000000..4f12469529d --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/InvalidParameterException.php @@ -0,0 +1,23 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Exception; + +/** + * Exception thrown when a parameter is not valid + * + * @author Alexandre Salomé + * + * @api + */ +class InvalidParameterException extends \InvalidArgumentException implements ExceptionInterface +{ +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/MethodNotAllowedException.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/MethodNotAllowedException.php new file mode 100644 index 00000000000..470ce52216e --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/MethodNotAllowedException.php @@ -0,0 +1,38 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Exception; + +/** + * The resource was found but the request method is not allowed. + * + * This exception should trigger an HTTP 405 response in your application code. + * + * @author Kris Wallsmith + * + * @api + */ +class MethodNotAllowedException extends \RuntimeException implements ExceptionInterface +{ + protected $allowedMethods; + + public function __construct(array $allowedMethods, $message = null, $code = 0, \Exception $previous = null) + { + $this->allowedMethods = array_map('strtoupper', $allowedMethods); + + parent::__construct($message, $code, $previous); + } + + public function getAllowedMethods() + { + return $this->allowedMethods; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/MissingMandatoryParametersException.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/MissingMandatoryParametersException.php new file mode 100644 index 00000000000..5a523fa5590 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/MissingMandatoryParametersException.php @@ -0,0 +1,24 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Exception; + +/** + * Exception thrown when a route cannot be generated because of missing + * mandatory parameters. + * + * @author Alexandre Salomé + * + * @api + */ +class MissingMandatoryParametersException extends \InvalidArgumentException implements ExceptionInterface +{ +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/ResourceNotFoundException.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/ResourceNotFoundException.php new file mode 100644 index 00000000000..362a0d61f36 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/ResourceNotFoundException.php @@ -0,0 +1,25 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Exception; + +/** + * The resource was not found. + * + * This exception should trigger an HTTP 404 response in your application code. + * + * @author Kris Wallsmith + * + * @api + */ +class ResourceNotFoundException extends \RuntimeException implements ExceptionInterface +{ +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/RouteNotFoundException.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/RouteNotFoundException.php new file mode 100644 index 00000000000..4d5f288e7ed --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Exception/RouteNotFoundException.php @@ -0,0 +1,23 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Exception; + +/** + * Exception thrown when a route does not exists + * + * @author Alexandre Salomé + * + * @api + */ +class RouteNotFoundException extends \InvalidArgumentException implements ExceptionInterface +{ +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/GeneratorDumper.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/GeneratorDumper.php new file mode 100644 index 00000000000..1291bd12d0e --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/GeneratorDumper.php @@ -0,0 +1,39 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Generator\Dumper; + +use Symfony\Component\Routing\RouteCollection; + +/** + * GeneratorDumper is the base class for all built-in generator dumpers. + * + * @author Fabien Potencier + */ +abstract class GeneratorDumper implements GeneratorDumperInterface +{ + private $routes; + + /** + * Constructor. + * + * @param RouteCollection $routes The RouteCollection to dump + */ + public function __construct(RouteCollection $routes) + { + $this->routes = $routes; + } + + public function getRoutes() + { + return $this->routes; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/GeneratorDumperInterface.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/GeneratorDumperInterface.php new file mode 100644 index 00000000000..6f5353caf26 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/GeneratorDumperInterface.php @@ -0,0 +1,45 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Generator\Dumper; + +use Symfony\Component\Routing\RouteCollection; + +/** + * GeneratorDumperInterface is the interface that all generator dumper classes must implement. + * + * @author Fabien Potencier + * + * @api + */ +interface GeneratorDumperInterface +{ + /** + * Dumps a set of routes to a PHP class. + * + * Available options: + * + * * class: The class name + * * base_class: The base class name + * + * @param array $options An array of options + * + * @return string A PHP class representing the generator class + */ + public function dump(array $options = array()); + + /** + * Gets the routes to dump. + * + * @return RouteCollection A RouteCollection instance + */ + public function getRoutes(); +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/PhpGeneratorDumper.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/PhpGeneratorDumper.php new file mode 100644 index 00000000000..080dd3a2539 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/Dumper/PhpGeneratorDumper.php @@ -0,0 +1,150 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Generator\Dumper; + +use Symfony\Component\Routing\Route; + +/** + * PhpGeneratorDumper creates a PHP class able to generate URLs for a given set of routes. + * + * @author Fabien Potencier + * + * @api + */ +class PhpGeneratorDumper extends GeneratorDumper +{ + /** + * Dumps a set of routes to a PHP class. + * + * Available options: + * + * * class: The class name + * * base_class: The base class name + * + * @param array $options An array of options + * + * @return string A PHP class representing the generator class + * + * @api + */ + public function dump(array $options = array()) + { + $options = array_merge(array( + 'class' => 'ProjectUrlGenerator', + 'base_class' => 'Symfony\\Component\\Routing\\Generator\\UrlGenerator', + ), $options); + + return + $this->startClass($options['class'], $options['base_class']). + $this->addConstructor(). + $this->addGenerator(). + $this->endClass() + ; + } + + private function addGenerator() + { + $methods = array(); + foreach ($this->getRoutes()->all() as $name => $route) { + $compiledRoute = $route->compile(); + + $variables = str_replace("\n", '', var_export($compiledRoute->getVariables(), true)); + $defaults = str_replace("\n", '', var_export($compiledRoute->getDefaults(), true)); + $requirements = str_replace("\n", '', var_export($compiledRoute->getRequirements(), true)); + $tokens = str_replace("\n", '', var_export($compiledRoute->getTokens(), true)); + + $escapedName = str_replace('.', '__', $name); + + $methods[] = <<{'get'.\$escapedName.'RouteInfo'}(); + + return \$this->doGenerate(\$variables, \$defaults, \$requirements, \$tokens, \$parameters, \$name, \$absolute); + } + +$methods +EOF; + } + + private function startClass($class, $baseClass) + { + $routes = array(); + foreach ($this->getRoutes()->all() as $name => $route) { + $routes[] = " '$name' => true,"; + } + $routes = implode("\n", $routes); + + return <<context = \$context; + } + +EOF; + } + + private function endClass() + { + return << + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Generator; + +use Symfony\Component\Routing\Route; +use Symfony\Component\Routing\RouteCollection; +use Symfony\Component\Routing\RequestContext; +use Symfony\Component\Routing\Exception\InvalidParameterException; +use Symfony\Component\Routing\Exception\RouteNotFoundException; +use Symfony\Component\Routing\Exception\MissingMandatoryParametersException; + +/** + * UrlGenerator generates URL based on a set of routes. + * + * @author Fabien Potencier + * + * @api + */ +class UrlGenerator implements UrlGeneratorInterface +{ + protected $context; + protected $decodedChars = array( + // %2F is not valid in a URL, so we don't encode it (which is fine as the requirements explicitly allowed it) + '%2F' => '/', + ); + + protected $routes; + protected $cache; + + /** + * Constructor. + * + * @param RouteCollection $routes A RouteCollection instance + * @param RequestContext $context The context + * + * @api + */ + public function __construct(RouteCollection $routes, RequestContext $context) + { + $this->routes = $routes; + $this->context = $context; + $this->cache = array(); + } + + /** + * Sets the request context. + * + * @param RequestContext $context The context + * + * @api + */ + public function setContext(RequestContext $context) + { + $this->context = $context; + } + + /** + * Gets the request context. + * + * @return RequestContext The context + */ + public function getContext() + { + return $this->context; + } + + /** + * Generates a URL from the given parameters. + * + * @param string $name The name of the route + * @param mixed $parameters An array of parameters + * @param Boolean $absolute Whether to generate an absolute URL + * + * @return string The generated URL + * + * @throws Symfony\Component\Routing\Exception\RouteNotFoundException When route doesn't exist + * + * @api + */ + public function generate($name, $parameters = array(), $absolute = false) + { + if (null === $route = $this->routes->get($name)) { + throw new RouteNotFoundException(sprintf('Route "%s" does not exist.', $name)); + } + + if (!isset($this->cache[$name])) { + $this->cache[$name] = $route->compile(); + } + + return $this->doGenerate($this->cache[$name]->getVariables(), $route->getDefaults(), $route->getRequirements(), $this->cache[$name]->getTokens(), $parameters, $name, $absolute); + } + + /** + * @throws Symfony\Component\Routing\Exception\MissingMandatoryParametersException When route has some missing mandatory parameters + * @throws Symfony\Component\Routing\Exception\InvalidParameterException When a parameter value is not correct + */ + protected function doGenerate($variables, $defaults, $requirements, $tokens, $parameters, $name, $absolute) + { + $variables = array_flip($variables); + + $originParameters = $parameters; + $parameters = array_replace($this->context->getParameters(), $parameters); + $tparams = array_replace($defaults, $parameters); + + // all params must be given + if ($diff = array_diff_key($variables, $tparams)) { + throw new MissingMandatoryParametersException(sprintf('The "%s" route has some missing mandatory parameters ("%s").', $name, implode('", "', array_keys($diff)))); + } + + $url = ''; + $optional = true; + foreach ($tokens as $token) { + if ('variable' === $token[0]) { + if (false === $optional || !array_key_exists($token[3], $defaults) || (isset($parameters[$token[3]]) && (string) $parameters[$token[3]] != (string) $defaults[$token[3]])) { + if (!$isEmpty = in_array($tparams[$token[3]], array(null, '', false), true)) { + // check requirement + if ($tparams[$token[3]] && !preg_match('#^'.$token[2].'$#', $tparams[$token[3]])) { + throw new InvalidParameterException(sprintf('Parameter "%s" for route "%s" must match "%s" ("%s" given).', $token[3], $name, $token[2], $tparams[$token[3]])); + } + } + + if (!$isEmpty || !$optional) { + $url = $token[1].strtr(rawurlencode($tparams[$token[3]]), $this->decodedChars).$url; + } + + $optional = false; + } + } elseif ('text' === $token[0]) { + $url = $token[1].$url; + $optional = false; + } + } + + if (!$url) { + $url = '/'; + } + + // add a query string if needed + $extra = array_diff_key($originParameters, $variables, $defaults); + if ($extra && $query = http_build_query($extra, '', '&')) { + $url .= '?'.$query; + } + + $url = $this->context->getBaseUrl().$url; + + if ($this->context->getHost()) { + $scheme = $this->context->getScheme(); + if (isset($requirements['_scheme']) && ($req = strtolower($requirements['_scheme'])) && $scheme != $req) { + $absolute = true; + $scheme = $req; + } + + if ($absolute) { + $port = ''; + if ('http' === $scheme && 80 != $this->context->getHttpPort()) { + $port = ':'.$this->context->getHttpPort(); + } elseif ('https' === $scheme && 443 != $this->context->getHttpsPort()) { + $port = ':'.$this->context->getHttpsPort(); + } + + $url = $scheme.'://'.$this->context->getHost().$port.$url; + } + } + + return $url; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/UrlGeneratorInterface.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/UrlGeneratorInterface.php new file mode 100644 index 00000000000..6f2800c27c1 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Generator/UrlGeneratorInterface.php @@ -0,0 +1,37 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Generator; + +use Symfony\Component\Routing\RequestContextAwareInterface; + +/** + * UrlGeneratorInterface is the interface that all URL generator classes must implements. + * + * @author Fabien Potencier + * + * @api + */ +interface UrlGeneratorInterface extends RequestContextAwareInterface +{ + /** + * Generates a URL from the given parameters. + * + * @param string $name The name of the route + * @param mixed $parameters An array of parameters + * @param Boolean $absolute Whether to generate an absolute URL + * + * @return string The generated URL + * + * @api + */ + public function generate($name, $parameters = array(), $absolute = false); +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/LICENSE b/3rdparty/symfony/routing/Symfony/Component/Routing/LICENSE new file mode 100644 index 00000000000..cdffe7aebc0 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/LICENSE @@ -0,0 +1,19 @@ +Copyright (c) 2004-2012 Fabien Potencier + +Permission is hereby granted, free of charge, to any person obtaining a copy +of this software and associated documentation files (the "Software"), to deal +in the Software without restriction, including without limitation the rights +to use, copy, modify, merge, publish, distribute, sublicense, and/or sell +copies of the Software, and to permit persons to whom the Software is furnished +to do so, subject to the following conditions: + +The above copyright notice and this permission notice shall be included in all +copies or substantial portions of the Software. + +THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE +AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, +OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN +THE SOFTWARE. diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationClassLoader.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationClassLoader.php new file mode 100644 index 00000000000..5f292d4589e --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationClassLoader.php @@ -0,0 +1,213 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Loader; + +use Doctrine\Common\Annotations\Reader; +use Symfony\Component\Config\Resource\FileResource; +use Symfony\Component\Routing\Route; +use Symfony\Component\Routing\RouteCollection; +use Symfony\Component\Config\Loader\LoaderInterface; +use Symfony\Component\Config\Loader\LoaderResolver; + +/** + * AnnotationClassLoader loads routing information from a PHP class and its methods. + * + * You need to define an implementation for the getRouteDefaults() method. Most of the + * time, this method should define some PHP callable to be called for the route + * (a controller in MVC speak). + * + * The @Route annotation can be set on the class (for global parameters), + * and on each method. + * + * The @Route annotation main value is the route pattern. The annotation also + * recognizes three parameters: requirements, options, and name. The name parameter + * is mandatory. Here is an example of how you should be able to use it: + * + * /** + * * @Route("/Blog") + * * / + * class Blog + * { + * /** + * * @Route("/", name="blog_index") + * * / + * public function index() + * { + * } + * + * /** + * * @Route("/{id}", name="blog_post", requirements = {"id" = "\d+"}) + * * / + * public function show() + * { + * } + * } + * + * @author Fabien Potencier + */ +abstract class AnnotationClassLoader implements LoaderInterface +{ + protected $reader; + protected $routeAnnotationClass = 'Symfony\\Component\\Routing\\Annotation\\Route'; + protected $defaultRouteIndex; + + /** + * Constructor. + * + * @param Reader $reader + */ + public function __construct(Reader $reader) + { + $this->reader = $reader; + } + + /** + * Sets the annotation class to read route properties from. + * + * @param string $class A fully-qualified class name + */ + public function setRouteAnnotationClass($class) + { + $this->routeAnnotationClass = $class; + } + + /** + * Loads from annotations from a class. + * + * @param string $class A class name + * @param string $type The resource type + * + * @return RouteCollection A RouteCollection instance + * + * @throws \InvalidArgumentException When route can't be parsed + */ + public function load($class, $type = null) + { + if (!class_exists($class)) { + throw new \InvalidArgumentException(sprintf('Class "%s" does not exist.', $class)); + } + + $globals = array( + 'pattern' => '', + 'requirements' => array(), + 'options' => array(), + 'defaults' => array(), + ); + + $class = new \ReflectionClass($class); + if ($class->isAbstract()) { + throw new \InvalidArgumentException(sprintf('Annotations from class "%s" cannot be read as it is abstract.', $class)); + } + + if ($annot = $this->reader->getClassAnnotation($class, $this->routeAnnotationClass)) { + if (null !== $annot->getPattern()) { + $globals['pattern'] = $annot->getPattern(); + } + + if (null !== $annot->getRequirements()) { + $globals['requirements'] = $annot->getRequirements(); + } + + if (null !== $annot->getOptions()) { + $globals['options'] = $annot->getOptions(); + } + + if (null !== $annot->getDefaults()) { + $globals['defaults'] = $annot->getDefaults(); + } + } + + $collection = new RouteCollection(); + $collection->addResource(new FileResource($class->getFileName())); + + foreach ($class->getMethods() as $method) { + $this->defaultRouteIndex = 0; + foreach ($this->reader->getMethodAnnotations($method) as $annot) { + if ($annot instanceof $this->routeAnnotationClass) { + $this->addRoute($collection, $annot, $globals, $class, $method); + } + } + } + + return $collection; + } + + protected function addRoute(RouteCollection $collection, $annot, $globals, \ReflectionClass $class, \ReflectionMethod $method) + { + $name = $annot->getName(); + if (null === $name) { + $name = $this->getDefaultRouteName($class, $method); + } + + $defaults = array_merge($globals['defaults'], $annot->getDefaults()); + $requirements = array_merge($globals['requirements'], $annot->getRequirements()); + $options = array_merge($globals['options'], $annot->getOptions()); + + $route = new Route($globals['pattern'].$annot->getPattern(), $defaults, $requirements, $options); + + $this->configureRoute($route, $class, $method, $annot); + + $collection->add($name, $route); + } + + /** + * Returns true if this class supports the given resource. + * + * @param mixed $resource A resource + * @param string $type The resource type + * + * @return Boolean True if this class supports the given resource, false otherwise + */ + public function supports($resource, $type = null) + { + return is_string($resource) && preg_match('/^(?:\\\\?[a-zA-Z_\x7f-\xff][a-zA-Z0-9_\x7f-\xff]*)+$/', $resource) && (!$type || 'annotation' === $type); + } + + /** + * Sets the loader resolver. + * + * @param LoaderResolver $resolver A LoaderResolver instance + */ + public function setResolver(LoaderResolver $resolver) + { + } + + /** + * Gets the loader resolver. + * + * @return LoaderResolver A LoaderResolver instance + */ + public function getResolver() + { + } + + /** + * Gets the default route name for a class method. + * + * @param \ReflectionClass $class + * @param \ReflectionMethod $method + * + * @return string + */ + protected function getDefaultRouteName(\ReflectionClass $class, \ReflectionMethod $method) + { + $name = strtolower(str_replace('\\', '_', $class->name).'_'.$method->name); + if ($this->defaultRouteIndex > 0) { + $name .= '_'.$this->defaultRouteIndex; + } + $this->defaultRouteIndex++; + + return $name; + } + + abstract protected function configureRoute(Route $route, \ReflectionClass $class, \ReflectionMethod $method, $annot); +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationDirectoryLoader.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationDirectoryLoader.php new file mode 100644 index 00000000000..8097cd67f96 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationDirectoryLoader.php @@ -0,0 +1,77 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Loader; + +use Symfony\Component\Routing\RouteCollection; +use Symfony\Component\Config\Resource\DirectoryResource; + +/** + * AnnotationDirectoryLoader loads routing information from annotations set + * on PHP classes and methods. + * + * @author Fabien Potencier + */ +class AnnotationDirectoryLoader extends AnnotationFileLoader +{ + /** + * Loads from annotations from a directory. + * + * @param string $path A directory path + * @param string $type The resource type + * + * @return RouteCollection A RouteCollection instance + * + * @throws \InvalidArgumentException When the directory does not exist or its routes cannot be parsed + */ + public function load($path, $type = null) + { + $dir = $this->locator->locate($path); + + $collection = new RouteCollection(); + $collection->addResource(new DirectoryResource($dir, '/\.php$/')); + foreach (new \RecursiveIteratorIterator(new \RecursiveDirectoryIterator($dir), \RecursiveIteratorIterator::LEAVES_ONLY) as $file) { + if (!$file->isFile() || '.php' !== substr($file->getFilename(), -4)) { + continue; + } + + if ($class = $this->findClass($file)) { + $refl = new \ReflectionClass($class); + if ($refl->isAbstract()) { + continue; + } + + $collection->addCollection($this->loader->load($class, $type)); + } + } + + return $collection; + } + + /** + * Returns true if this class supports the given resource. + * + * @param mixed $resource A resource + * @param string $type The resource type + * + * @return Boolean True if this class supports the given resource, false otherwise + */ + public function supports($resource, $type = null) + { + try { + $path = $this->locator->locate($resource); + } catch (\Exception $e) { + return false; + } + + return is_string($resource) && is_dir($path) && (!$type || 'annotation' === $type); + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationFileLoader.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationFileLoader.php new file mode 100644 index 00000000000..49e1cb2f775 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/AnnotationFileLoader.php @@ -0,0 +1,125 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Loader; + +use Symfony\Component\Routing\RouteCollection; +use Symfony\Component\Config\Resource\FileResource; +use Symfony\Component\Config\Loader\FileLoader; +use Symfony\Component\Config\FileLocator; + +/** + * AnnotationFileLoader loads routing information from annotations set + * on a PHP class and its methods. + * + * @author Fabien Potencier + */ +class AnnotationFileLoader extends FileLoader +{ + protected $loader; + + /** + * Constructor. + * + * @param FileLocator $locator A FileLocator instance + * @param AnnotationClassLoader $loader An AnnotationClassLoader instance + * @param string|array $paths A path or an array of paths where to look for resources + */ + public function __construct(FileLocator $locator, AnnotationClassLoader $loader, $paths = array()) + { + if (!function_exists('token_get_all')) { + throw new \RuntimeException('The Tokenizer extension is required for the routing annotation loaders.'); + } + + parent::__construct($locator, $paths); + + $this->loader = $loader; + } + + /** + * Loads from annotations from a file. + * + * @param string $file A PHP file path + * @param string $type The resource type + * + * @return RouteCollection A RouteCollection instance + * + * @throws \InvalidArgumentException When the file does not exist or its routes cannot be parsed + */ + public function load($file, $type = null) + { + $path = $this->locator->locate($file); + + $collection = new RouteCollection(); + if ($class = $this->findClass($path)) { + $collection->addResource(new FileResource($path)); + $collection->addCollection($this->loader->load($class, $type)); + } + + return $collection; + } + + /** + * Returns true if this class supports the given resource. + * + * @param mixed $resource A resource + * @param string $type The resource type + * + * @return Boolean True if this class supports the given resource, false otherwise + */ + public function supports($resource, $type = null) + { + return is_string($resource) && 'php' === pathinfo($resource, PATHINFO_EXTENSION) && (!$type || 'annotation' === $type); + } + + /** + * Returns the full class name for the first class in the file. + * + * @param string $file A PHP file path + * + * @return string|false Full class name if found, false otherwise + */ + protected function findClass($file) + { + $class = false; + $namespace = false; + $tokens = token_get_all(file_get_contents($file)); + for ($i = 0, $count = count($tokens); $i < $count; $i++) { + $token = $tokens[$i]; + + if (!is_array($token)) { + continue; + } + + if (true === $class && T_STRING === $token[0]) { + return $namespace.'\\'.$token[1]; + } + + if (true === $namespace && T_STRING === $token[0]) { + $namespace = ''; + do { + $namespace .= $token[1]; + $token = $tokens[++$i]; + } while ($i < $count && is_array($token) && in_array($token[0], array(T_NS_SEPARATOR, T_STRING))); + } + + if (T_CLASS === $token[0]) { + $class = true; + } + + if (T_NAMESPACE === $token[0]) { + $namespace = true; + } + } + + return false; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/ClosureLoader.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/ClosureLoader.php new file mode 100644 index 00000000000..ca49c8fa35a --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/ClosureLoader.php @@ -0,0 +1,54 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Loader; + +use Symfony\Component\Config\Loader\Loader; + +/** + * ClosureLoader loads routes from a PHP closure. + * + * The Closure must return a RouteCollection instance. + * + * @author Fabien Potencier + * + * @api + */ +class ClosureLoader extends Loader +{ + /** + * Loads a Closure. + * + * @param \Closure $closure A Closure + * @param string $type The resource type + * + * @api + */ + public function load($closure, $type = null) + { + return call_user_func($closure); + } + + /** + * Returns true if this class supports the given resource. + * + * @param mixed $resource A resource + * @param string $type The resource type + * + * @return Boolean True if this class supports the given resource, false otherwise + * + * @api + */ + public function supports($resource, $type = null) + { + return $resource instanceof \Closure && (!$type || 'closure' === $type); + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/PhpFileLoader.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/PhpFileLoader.php new file mode 100644 index 00000000000..ffd31f94442 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/PhpFileLoader.php @@ -0,0 +1,64 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Loader; + +use Symfony\Component\Config\Resource\FileResource; +use Symfony\Component\Config\Loader\FileLoader; + +/** + * PhpFileLoader loads routes from a PHP file. + * + * The file must return a RouteCollection instance. + * + * @author Fabien Potencier + * + * @api + */ +class PhpFileLoader extends FileLoader +{ + /** + * Loads a PHP file. + * + * @param mixed $file A PHP file path + * @param string $type The resource type + * + * @api + */ + public function load($file, $type = null) + { + // the loader variable is exposed to the included file below + $loader = $this; + + $path = $this->locator->locate($file); + $this->setCurrentDir(dirname($path)); + + $collection = include $path; + $collection->addResource(new FileResource($path)); + + return $collection; + } + + /** + * Returns true if this class supports the given resource. + * + * @param mixed $resource A resource + * @param string $type The resource type + * + * @return Boolean True if this class supports the given resource, false otherwise + * + * @api + */ + public function supports($resource, $type = null) + { + return is_string($resource) && 'php' === pathinfo($resource, PATHINFO_EXTENSION) && (!$type || 'php' === $type); + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/XmlFileLoader.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/XmlFileLoader.php new file mode 100644 index 00000000000..5dad9db3fae --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/XmlFileLoader.php @@ -0,0 +1,224 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Loader; + +use Symfony\Component\Routing\RouteCollection; +use Symfony\Component\Routing\Route; +use Symfony\Component\Config\Resource\FileResource; +use Symfony\Component\Config\Loader\FileLoader; + +/** + * XmlFileLoader loads XML routing files. + * + * @author Fabien Potencier + * + * @api + */ +class XmlFileLoader extends FileLoader +{ + /** + * Loads an XML file. + * + * @param string $file An XML file path + * @param string $type The resource type + * + * @return RouteCollection A RouteCollection instance + * + * @throws \InvalidArgumentException When a tag can't be parsed + * + * @api + */ + public function load($file, $type = null) + { + $path = $this->locator->locate($file); + + $xml = $this->loadFile($path); + + $collection = new RouteCollection(); + $collection->addResource(new FileResource($path)); + + // process routes and imports + foreach ($xml->documentElement->childNodes as $node) { + if (!$node instanceof \DOMElement) { + continue; + } + + $this->parseNode($collection, $node, $path, $file); + } + + return $collection; + } + + /** + * Parses a node from a loaded XML file. + * + * @param RouteCollection $collection the collection to associate with the node + * @param DOMElement $node the node to parse + * @param string $path the path of the XML file being processed + * @param string $file + */ + protected function parseNode(RouteCollection $collection, \DOMElement $node, $path, $file) + { + switch ($node->tagName) { + case 'route': + $this->parseRoute($collection, $node, $path); + break; + case 'import': + $resource = (string) $node->getAttribute('resource'); + $type = (string) $node->getAttribute('type'); + $prefix = (string) $node->getAttribute('prefix'); + $this->setCurrentDir(dirname($path)); + $collection->addCollection($this->import($resource, ('' !== $type ? $type : null), false, $file), $prefix); + break; + default: + throw new \InvalidArgumentException(sprintf('Unable to parse tag "%s"', $node->tagName)); + } + } + + /** + * Returns true if this class supports the given resource. + * + * @param mixed $resource A resource + * @param string $type The resource type + * + * @return Boolean True if this class supports the given resource, false otherwise + * + * @api + */ + public function supports($resource, $type = null) + { + return is_string($resource) && 'xml' === pathinfo($resource, PATHINFO_EXTENSION) && (!$type || 'xml' === $type); + } + + /** + * Parses a route and adds it to the RouteCollection. + * + * @param RouteCollection $collection A RouteCollection instance + * @param \DOMElement $definition Route definition + * @param string $file An XML file path + * + * @throws \InvalidArgumentException When the definition cannot be parsed + */ + protected function parseRoute(RouteCollection $collection, \DOMElement $definition, $file) + { + $defaults = array(); + $requirements = array(); + $options = array(); + + foreach ($definition->childNodes as $node) { + if (!$node instanceof \DOMElement) { + continue; + } + + switch ($node->tagName) { + case 'default': + $defaults[(string) $node->getAttribute('key')] = trim((string) $node->nodeValue); + break; + case 'option': + $options[(string) $node->getAttribute('key')] = trim((string) $node->nodeValue); + break; + case 'requirement': + $requirements[(string) $node->getAttribute('key')] = trim((string) $node->nodeValue); + break; + default: + throw new \InvalidArgumentException(sprintf('Unable to parse tag "%s"', $node->tagName)); + } + } + + $route = new Route((string) $definition->getAttribute('pattern'), $defaults, $requirements, $options); + + $collection->add((string) $definition->getAttribute('id'), $route); + } + + /** + * Loads an XML file. + * + * @param string $file An XML file path + * + * @return \DOMDocument + * + * @throws \InvalidArgumentException When loading of XML file returns error + */ + protected function loadFile($file) + { + $internalErrors = libxml_use_internal_errors(true); + $disableEntities = libxml_disable_entity_loader(true); + libxml_clear_errors(); + + $dom = new \DOMDocument(); + $dom->validateOnParse = true; + if (!$dom->loadXML(file_get_contents($file), LIBXML_NONET | (defined('LIBXML_COMPACT') ? LIBXML_COMPACT : 0))) { + libxml_disable_entity_loader($disableEntities); + + throw new \InvalidArgumentException(implode("\n", $this->getXmlErrors($internalErrors))); + } + $dom->normalizeDocument(); + + libxml_use_internal_errors($internalErrors); + libxml_disable_entity_loader($disableEntities); + + foreach ($dom->childNodes as $child) { + if ($child->nodeType === XML_DOCUMENT_TYPE_NODE) { + throw new \InvalidArgumentException('Document types are not allowed.'); + } + } + + $this->validate($dom); + + return $dom; + } + + /** + * Validates a loaded XML file. + * + * @param \DOMDocument $dom A loaded XML file + * + * @throws \InvalidArgumentException When XML doesn't validate its XSD schema + */ + protected function validate(\DOMDocument $dom) + { + $location = __DIR__.'/schema/routing/routing-1.0.xsd'; + + $current = libxml_use_internal_errors(true); + libxml_clear_errors(); + + if (!$dom->schemaValidate($location)) { + throw new \InvalidArgumentException(implode("\n", $this->getXmlErrors($current))); + } + libxml_use_internal_errors($current); + } + + /** + * Retrieves libxml errors and clears them. + * + * @return array An array of libxml error strings + */ + private function getXmlErrors($internalErrors) + { + $errors = array(); + foreach (libxml_get_errors() as $error) { + $errors[] = sprintf('[%s %s] %s (in %s - line %d, column %d)', + LIBXML_ERR_WARNING == $error->level ? 'WARNING' : 'ERROR', + $error->code, + trim($error->message), + $error->file ? $error->file : 'n/a', + $error->line, + $error->column + ); + } + + libxml_clear_errors(); + libxml_use_internal_errors($internalErrors); + + return $errors; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/YamlFileLoader.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/YamlFileLoader.php new file mode 100644 index 00000000000..ee723834355 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/YamlFileLoader.php @@ -0,0 +1,142 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Loader; + +use Symfony\Component\Routing\RouteCollection; +use Symfony\Component\Routing\Route; +use Symfony\Component\Config\Resource\FileResource; +use Symfony\Component\Yaml\Yaml; +use Symfony\Component\Config\Loader\FileLoader; + +/** + * YamlFileLoader loads Yaml routing files. + * + * @author Fabien Potencier + * + * @api + */ +class YamlFileLoader extends FileLoader +{ + private static $availableKeys = array( + 'type', 'resource', 'prefix', 'pattern', 'options', 'defaults', 'requirements' + ); + + /** + * Loads a Yaml file. + * + * @param string $file A Yaml file path + * @param string $type The resource type + * + * @return RouteCollection A RouteCollection instance + * + * @throws \InvalidArgumentException When route can't be parsed + * + * @api + */ + public function load($file, $type = null) + { + $path = $this->locator->locate($file); + + $config = Yaml::parse($path); + + $collection = new RouteCollection(); + $collection->addResource(new FileResource($path)); + + // empty file + if (null === $config) { + $config = array(); + } + + // not an array + if (!is_array($config)) { + throw new \InvalidArgumentException(sprintf('The file "%s" must contain a YAML array.', $file)); + } + + foreach ($config as $name => $config) { + $config = $this->normalizeRouteConfig($config); + + if (isset($config['resource'])) { + $type = isset($config['type']) ? $config['type'] : null; + $prefix = isset($config['prefix']) ? $config['prefix'] : null; + $this->setCurrentDir(dirname($path)); + $collection->addCollection($this->import($config['resource'], $type, false, $file), $prefix); + } else { + $this->parseRoute($collection, $name, $config, $path); + } + } + + return $collection; + } + + /** + * Returns true if this class supports the given resource. + * + * @param mixed $resource A resource + * @param string $type The resource type + * + * @return Boolean True if this class supports the given resource, false otherwise + * + * @api + */ + public function supports($resource, $type = null) + { + return is_string($resource) && 'yml' === pathinfo($resource, PATHINFO_EXTENSION) && (!$type || 'yaml' === $type); + } + + /** + * Parses a route and adds it to the RouteCollection. + * + * @param RouteCollection $collection A RouteCollection instance + * @param string $name Route name + * @param array $config Route definition + * @param string $file A Yaml file path + * + * @throws \InvalidArgumentException When config pattern is not defined for the given route + */ + protected function parseRoute(RouteCollection $collection, $name, $config, $file) + { + $defaults = isset($config['defaults']) ? $config['defaults'] : array(); + $requirements = isset($config['requirements']) ? $config['requirements'] : array(); + $options = isset($config['options']) ? $config['options'] : array(); + + if (!isset($config['pattern'])) { + throw new \InvalidArgumentException(sprintf('You must define a "pattern" for the "%s" route.', $name)); + } + + $route = new Route($config['pattern'], $defaults, $requirements, $options); + + $collection->add($name, $route); + } + + /** + * Normalize route configuration. + * + * @param array $config A resource config + * + * @return array + * + * @throws InvalidArgumentException if one of the provided config keys is not supported + */ + private function normalizeRouteConfig(array $config) + { + foreach ($config as $key => $value) { + if (!in_array($key, self::$availableKeys)) { + throw new \InvalidArgumentException(sprintf( + 'Yaml routing loader does not support given key: "%s". Expected one of the (%s).', + $key, implode(', ', self::$availableKeys) + )); + } + } + + return $config; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/schema/routing/routing-1.0.xsd b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/schema/routing/routing-1.0.xsd new file mode 100644 index 00000000000..a9554e64df3 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Loader/schema/routing/routing-1.0.xsd @@ -0,0 +1,38 @@ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/ApacheUrlMatcher.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/ApacheUrlMatcher.php new file mode 100644 index 00000000000..3003dfdebb0 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/ApacheUrlMatcher.php @@ -0,0 +1,76 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Matcher; + +use Symfony\Component\Routing\Exception\MethodNotAllowedException; + +/** + * ApacheUrlMatcher matches URL based on Apache mod_rewrite matching (see ApacheMatcherDumper). + * + * @author Fabien Potencier + */ +class ApacheUrlMatcher extends UrlMatcher +{ + /** + * Tries to match a URL based on Apache mod_rewrite matching. + * + * Returns false if no route matches the URL. + * + * @param string $pathinfo The pathinfo to be parsed + * + * @return array An array of parameters + * + * @throws MethodNotAllowedException If the current method is not allowed + */ + public function match($pathinfo) + { + $parameters = array(); + $defaults = array(); + $allow = array(); + $match = false; + + foreach ($_SERVER as $key => $value) { + $name = $key; + + if (0 === strpos($name, 'REDIRECT_')) { + $name = substr($name, 9); + } + + if (0 === strpos($name, '_ROUTING_DEFAULTS_')) { + $name = substr($name, 18); + $defaults[$name] = $value; + } elseif (0 === strpos($name, '_ROUTING_')) { + $name = substr($name, 9); + if ('_route' == $name) { + $match = true; + $parameters[$name] = $value; + } elseif (0 === strpos($name, '_allow_')) { + $allow[] = substr($name, 7); + } else { + $parameters[$name] = $value; + } + } else { + continue; + } + + unset($_SERVER[$key]); + } + + if ($match) { + return $this->mergeDefaults($parameters, $defaults); + } elseif (0 < count($allow)) { + throw new MethodNotAllowedException($allow); + } else { + return parent::match($pathinfo); + } + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/ApacheMatcherDumper.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/ApacheMatcherDumper.php new file mode 100644 index 00000000000..4f03b8d393b --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/ApacheMatcherDumper.php @@ -0,0 +1,155 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Matcher\Dumper; + +/** + * Dumps a set of Apache mod_rewrite rules. + * + * @author Fabien Potencier + * @author Kris Wallsmith + */ +class ApacheMatcherDumper extends MatcherDumper +{ + /** + * Dumps a set of Apache mod_rewrite rules. + * + * Available options: + * + * * script_name: The script name (app.php by default) + * * base_uri: The base URI ("" by default) + * + * @param array $options An array of options + * + * @return string A string to be used as Apache rewrite rules + * + * @throws \LogicException When the route regex is invalid + */ + public function dump(array $options = array()) + { + $options = array_merge(array( + 'script_name' => 'app.php', + 'base_uri' => '', + ), $options); + + $options['script_name'] = self::escape($options['script_name'], ' ', '\\'); + + $rules = array("# skip \"real\" requests\nRewriteCond %{REQUEST_FILENAME} -f\nRewriteRule .* - [QSA,L]"); + $methodVars = array(); + + foreach ($this->getRoutes()->all() as $name => $route) { + $compiledRoute = $route->compile(); + + // prepare the apache regex + $regex = $compiledRoute->getRegex(); + $delimiter = $regex[0]; + $regexPatternEnd = strrpos($regex, $delimiter); + if (strlen($regex) < 2 || 0 === $regexPatternEnd) { + throw new \LogicException('The "%s" route regex "%s" is invalid', $name, $regex); + } + $regex = preg_replace('/\?P<.+?>/', '', substr($regex, 1, $regexPatternEnd - 1)); + $regex = '^'.self::escape(preg_quote($options['base_uri']).substr($regex, 1), ' ', '\\'); + + $hasTrailingSlash = '/$' == substr($regex, -2) && '^/$' != $regex; + + $variables = array('E=_ROUTING__route:'.$name); + foreach ($compiledRoute->getVariables() as $i => $variable) { + $variables[] = 'E=_ROUTING_'.$variable.':%'.($i + 1); + } + foreach ($route->getDefaults() as $key => $value) { + $variables[] = 'E=_ROUTING_DEFAULTS_'.$key.':'.strtr($value, array( + ':' => '\\:', + '=' => '\\=', + '\\' => '\\\\', + ' ' => '\\ ', + )); + } + $variables = implode(',', $variables); + + $rule = array("# $name"); + + // method mismatch + if ($req = $route->getRequirement('_method')) { + $methods = explode('|', strtoupper($req)); + // GET and HEAD are equivalent + if (in_array('GET', $methods) && !in_array('HEAD', $methods)) { + $methods[] = 'HEAD'; + } + $allow = array(); + foreach ($methods as $method) { + $methodVars[] = $method; + $allow[] = 'E=_ROUTING__allow_'.$method.':1'; + } + + $rule[] = "RewriteCond %{REQUEST_URI} $regex"; + $rule[] = sprintf("RewriteCond %%{REQUEST_METHOD} !^(%s)$ [NC]", implode('|', $methods)); + $rule[] = sprintf('RewriteRule .* - [S=%d,%s]', $hasTrailingSlash ? 2 : 1, implode(',', $allow)); + } + + // redirect with trailing slash appended + if ($hasTrailingSlash) { + $rule[] = 'RewriteCond %{REQUEST_URI} '.substr($regex, 0, -2).'$'; + $rule[] = 'RewriteRule .* $0/ [QSA,L,R=301]'; + } + + // the main rule + $rule[] = "RewriteCond %{REQUEST_URI} $regex"; + $rule[] = "RewriteRule .* {$options['script_name']} [QSA,L,$variables]"; + + $rules[] = implode("\n", $rule); + } + + if (0 < count($methodVars)) { + $rule = array('# 405 Method Not Allowed'); + $methodVars = array_values(array_unique($methodVars)); + foreach ($methodVars as $i => $methodVar) { + $rule[] = sprintf('RewriteCond %%{_ROUTING__allow_%s} !-z%s', $methodVar, isset($methodVars[$i + 1]) ? ' [OR]' : ''); + } + $rule[] = sprintf('RewriteRule .* %s [QSA,L]', $options['script_name']); + + $rules[] = implode("\n", $rule); + } + + return implode("\n\n", $rules)."\n"; + } + + /** + * Escapes a string. + * + * @param string $string The string to be escaped + * @param string $char The character to be escaped + * @param string $with The character to be used for escaping + * + * @return string The escaped string + */ + private static function escape($string, $char, $with) + { + $escaped = false; + $output = ''; + foreach (str_split($string) as $symbol) { + if ($escaped) { + $output .= $symbol; + $escaped = false; + continue; + } + if ($symbol === $char) { + $output .= $with.$char; + continue; + } + if ($symbol === $with) { + $escaped = true; + } + $output .= $symbol; + } + + return $output; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/MatcherDumper.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/MatcherDumper.php new file mode 100644 index 00000000000..423368b57ed --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/MatcherDumper.php @@ -0,0 +1,44 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Matcher\Dumper; + +use Symfony\Component\Routing\RouteCollection; + +/** + * MatcherDumper is the abstract class for all built-in matcher dumpers. + * + * @author Fabien Potencier + */ +abstract class MatcherDumper implements MatcherDumperInterface +{ + private $routes; + + /** + * Constructor. + * + * @param RouteCollection $routes The RouteCollection to dump + */ + public function __construct(RouteCollection $routes) + { + $this->routes = $routes; + } + + /** + * Gets the routes to dump. + * + * @return RouteCollection A RouteCollection instance + */ + public function getRoutes() + { + return $this->routes; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/MatcherDumperInterface.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/MatcherDumperInterface.php new file mode 100644 index 00000000000..fe09e067d7c --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/MatcherDumperInterface.php @@ -0,0 +1,41 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Matcher\Dumper; + +/** + * MatcherDumperInterface is the interface that all matcher dumper classes must implement. + * + * @author Fabien Potencier + */ +interface MatcherDumperInterface +{ + /** + * Dumps a set of routes to a PHP class. + * + * Available options: + * + * * class: The class name + * * base_class: The base class name + * + * @param array $options An array of options + * + * @return string A PHP class representing the matcher class + */ + public function dump(array $options = array()); + + /** + * Gets the routes to match. + * + * @return RouteCollection A RouteCollection instance + */ + public function getRoutes(); +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/PhpMatcherDumper.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/PhpMatcherDumper.php new file mode 100644 index 00000000000..fdaad513a19 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/Dumper/PhpMatcherDumper.php @@ -0,0 +1,293 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Matcher\Dumper; + +use Symfony\Component\Routing\Route; +use Symfony\Component\Routing\RouteCollection; + +/** + * PhpMatcherDumper creates a PHP class able to match URLs for a given set of routes. + * + * @author Fabien Potencier + */ +class PhpMatcherDumper extends MatcherDumper +{ + /** + * Dumps a set of routes to a PHP class. + * + * Available options: + * + * * class: The class name + * * base_class: The base class name + * + * @param array $options An array of options + * + * @return string A PHP class representing the matcher class + */ + public function dump(array $options = array()) + { + $options = array_merge(array( + 'class' => 'ProjectUrlMatcher', + 'base_class' => 'Symfony\\Component\\Routing\\Matcher\\UrlMatcher', + ), $options); + + // trailing slash support is only enabled if we know how to redirect the user + $interfaces = class_implements($options['base_class']); + $supportsRedirections = isset($interfaces['Symfony\Component\Routing\Matcher\RedirectableUrlMatcherInterface']); + + return + $this->startClass($options['class'], $options['base_class']). + $this->addConstructor(). + $this->addMatcher($supportsRedirections). + $this->endClass() + ; + } + + private function addMatcher($supportsRedirections) + { + // we need to deep clone the routes as we will modify the structure to optimize the dump + $code = implode("\n", $this->compileRoutes(clone $this->getRoutes(), $supportsRedirections)); + + return <<getIterator(); + $keys = array_keys($routeIterator->getArrayCopy()); + $keysCount = count($keys); + + $i = 0; + foreach ($routeIterator as $name => $route) { + $i++; + + if ($route instanceof RouteCollection) { + $prefix = $route->getPrefix(); + $optimizable = $prefix && count($route->all()) > 1 && false === strpos($route->getPrefix(), '{'); + $indent = ''; + if ($optimizable) { + for ($j = $i; $j < $keysCount; $j++) { + if ($keys[$j] === null) { + continue; + } + + $testRoute = $routeIterator->offsetGet($keys[$j]); + $isCollection = ($testRoute instanceof RouteCollection); + + $testPrefix = $isCollection ? $testRoute->getPrefix() : $testRoute->getPattern(); + + if (0 === strpos($testPrefix, $prefix)) { + $routeIterator->offsetUnset($keys[$j]); + + if ($isCollection) { + $route->addCollection($testRoute); + } else { + $route->add($keys[$j], $testRoute); + } + + $i++; + $keys[$j] = null; + } + } + + if ($prefix !== $parentPrefix) { + $code[] = sprintf(" if (0 === strpos(\$pathinfo, %s)) {", var_export($prefix, true)); + $indent = ' '; + } + } + + foreach ($this->compileRoutes($route, $supportsRedirections, $prefix) as $line) { + foreach (explode("\n", $line) as $l) { + if ($l) { + $code[] = $indent.$l; + } else { + $code[] = $l; + } + } + } + + if ($optimizable && $prefix !== $parentPrefix) { + $code[] = " }\n"; + } + } else { + foreach ($this->compileRoute($route, $name, $supportsRedirections, $parentPrefix) as $line) { + $code[] = $line; + } + } + } + + return $code; + } + + private function compileRoute(Route $route, $name, $supportsRedirections, $parentPrefix = null) + { + $code = array(); + $compiledRoute = $route->compile(); + $conditions = array(); + $hasTrailingSlash = false; + $matches = false; + if (!count($compiledRoute->getVariables()) && false !== preg_match('#^(.)\^(?P.*?)\$\1#', $compiledRoute->getRegex(), $m)) { + if ($supportsRedirections && substr($m['url'], -1) === '/') { + $conditions[] = sprintf("rtrim(\$pathinfo, '/') === %s", var_export(rtrim(str_replace('\\', '', $m['url']), '/'), true)); + $hasTrailingSlash = true; + } else { + $conditions[] = sprintf("\$pathinfo === %s", var_export(str_replace('\\', '', $m['url']), true)); + } + } else { + if ($compiledRoute->getStaticPrefix() && $compiledRoute->getStaticPrefix() != $parentPrefix) { + $conditions[] = sprintf("0 === strpos(\$pathinfo, %s)", var_export($compiledRoute->getStaticPrefix(), true)); + } + + $regex = $compiledRoute->getRegex(); + if ($supportsRedirections && $pos = strpos($regex, '/$')) { + $regex = substr($regex, 0, $pos).'/?$'.substr($regex, $pos + 2); + $hasTrailingSlash = true; + } + $conditions[] = sprintf("preg_match(%s, \$pathinfo, \$matches)", var_export($regex, true)); + + $matches = true; + } + + $conditions = implode(' && ', $conditions); + + $gotoname = 'not_'.preg_replace('/[^A-Za-z0-9_]/', '', $name); + + $code[] = <<getRequirement('_method')) { + $methods = explode('|', strtoupper($req)); + // GET and HEAD are equivalent + if (in_array('GET', $methods) && !in_array('HEAD', $methods)) { + $methods[] = 'HEAD'; + } + if (1 === count($methods)) { + $code[] = <<context->getMethod() != '$methods[0]') { + \$allow[] = '$methods[0]'; + goto $gotoname; + } +EOF; + } else { + $methods = implode('\', \'', $methods); + $code[] = <<context->getMethod(), array('$methods'))) { + \$allow = array_merge(\$allow, array('$methods')); + goto $gotoname; + } +EOF; + } + } + + if ($hasTrailingSlash) { + $code[] = sprintf(<<redirect(\$pathinfo.'/', '%s'); + } +EOF + , $name); + } + + if ($scheme = $route->getRequirement('_scheme')) { + if (!$supportsRedirections) { + throw new \LogicException('The "_scheme" requirement is only supported for route dumper that implements RedirectableUrlMatcherInterface.'); + } + + $code[] = sprintf(<<context->getScheme() !== '$scheme') { + return \$this->redirect(\$pathinfo, '%s', '$scheme'); + } +EOF + , $name); + } + + // optimize parameters array + if (true === $matches && $compiledRoute->getDefaults()) { + $code[] = sprintf(" return array_merge(\$this->mergeDefaults(\$matches, %s), array('_route' => '%s'));" + , str_replace("\n", '', var_export($compiledRoute->getDefaults(), true)), $name); + } elseif (true === $matches) { + $code[] = sprintf(" \$matches['_route'] = '%s';", $name); + $code[] = sprintf(" return \$matches;", $name); + } elseif ($compiledRoute->getDefaults()) { + $code[] = sprintf(' return %s;', str_replace("\n", '', var_export(array_merge($compiledRoute->getDefaults(), array('_route' => $name)), true))); + } else { + $code[] = sprintf(" return array('_route' => '%s');", $name); + } + $code[] = " }"; + + if ($req) { + $code[] = " $gotoname:"; + } + + $code[] = ''; + + return $code; + } + + private function startClass($class, $baseClass) + { + return <<context = \$context; + } + +EOF; + } + + private function endClass() + { + return << + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Matcher; + +use Symfony\Component\Routing\Exception\ResourceNotFoundException; + +/** + * @author Fabien Potencier + * + * @api + */ +abstract class RedirectableUrlMatcher extends UrlMatcher implements RedirectableUrlMatcherInterface +{ + private $trailingSlashTest = false; + + /** + * @see UrlMatcher::match() + * + * @api + */ + public function match($pathinfo) + { + try { + $parameters = parent::match($pathinfo); + } catch (ResourceNotFoundException $e) { + if ('/' === substr($pathinfo, -1)) { + throw $e; + } + + // try with a / at the end + $this->trailingSlashTest = true; + + return $this->match($pathinfo.'/'); + } + + if ($this->trailingSlashTest) { + $this->trailingSlashTest = false; + + return $this->redirect($pathinfo, null); + } + + return $parameters; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/RedirectableUrlMatcherInterface.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/RedirectableUrlMatcherInterface.php new file mode 100644 index 00000000000..929ae9cc78f --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/RedirectableUrlMatcherInterface.php @@ -0,0 +1,35 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Matcher; + +/** + * RedirectableUrlMatcherInterface knows how to redirect the user. + * + * @author Fabien Potencier + * + * @api + */ +interface RedirectableUrlMatcherInterface +{ + /** + * Redirects the user to another URL. + * + * @param string $path The path info to redirect to. + * @param string $route The route that matched + * @param string $scheme The URL scheme (null to keep the current one) + * + * @return array An array of parameters + * + * @api + */ + public function redirect($path, $route, $scheme = null); +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/UrlMatcher.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/UrlMatcher.php new file mode 100644 index 00000000000..5ff8070ea0c --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/UrlMatcher.php @@ -0,0 +1,151 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Matcher; + +use Symfony\Component\Routing\Exception\MethodNotAllowedException; +use Symfony\Component\Routing\Exception\ResourceNotFoundException; +use Symfony\Component\Routing\RouteCollection; +use Symfony\Component\Routing\RequestContext; + +/** + * UrlMatcher matches URL based on a set of routes. + * + * @author Fabien Potencier + * + * @api + */ +class UrlMatcher implements UrlMatcherInterface +{ + protected $context; + protected $allow; + + private $routes; + + /** + * Constructor. + * + * @param RouteCollection $routes A RouteCollection instance + * @param RequestContext $context The context + * + * @api + */ + public function __construct(RouteCollection $routes, RequestContext $context) + { + $this->routes = $routes; + $this->context = $context; + } + + /** + * Sets the request context. + * + * @param RequestContext $context The context + * + * @api + */ + public function setContext(RequestContext $context) + { + $this->context = $context; + } + + /** + * Gets the request context. + * + * @return RequestContext The context + */ + public function getContext() + { + return $this->context; + } + + /** + * Tries to match a URL with a set of routes. + * + * @param string $pathinfo The path info to be parsed + * + * @return array An array of parameters + * + * @throws ResourceNotFoundException If the resource could not be found + * @throws MethodNotAllowedException If the resource was found but the request method is not allowed + * + * @api + */ + public function match($pathinfo) + { + $this->allow = array(); + + if ($ret = $this->matchCollection($pathinfo, $this->routes)) { + return $ret; + } + + throw 0 < count($this->allow) + ? new MethodNotAllowedException(array_unique(array_map('strtoupper', $this->allow))) + : new ResourceNotFoundException(); + } + + protected function matchCollection($pathinfo, RouteCollection $routes) + { + $pathinfo = urldecode($pathinfo); + + foreach ($routes as $name => $route) { + if ($route instanceof RouteCollection) { + if (false === strpos($route->getPrefix(), '{') && $route->getPrefix() !== substr($pathinfo, 0, strlen($route->getPrefix()))) { + continue; + } + + if (!$ret = $this->matchCollection($pathinfo, $route)) { + continue; + } + + return $ret; + } + + $compiledRoute = $route->compile(); + + // check the static prefix of the URL first. Only use the more expensive preg_match when it matches + if ('' !== $compiledRoute->getStaticPrefix() && 0 !== strpos($pathinfo, $compiledRoute->getStaticPrefix())) { + continue; + } + + if (!preg_match($compiledRoute->getRegex(), $pathinfo, $matches)) { + continue; + } + + // check HTTP method requirement + if ($req = $route->getRequirement('_method')) { + // HEAD and GET are equivalent as per RFC + if ('HEAD' === $method = $this->context->getMethod()) { + $method = 'GET'; + } + + if (!in_array($method, $req = explode('|', strtoupper($req)))) { + $this->allow = array_merge($this->allow, $req); + + continue; + } + } + + return array_merge($this->mergeDefaults($matches, $route->getDefaults()), array('_route' => $name)); + } + } + + protected function mergeDefaults($params, $defaults) + { + $parameters = $defaults; + foreach ($params as $key => $value) { + if (!is_int($key)) { + $parameters[$key] = rawurldecode($value); + } + } + + return $parameters; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/UrlMatcherInterface.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/UrlMatcherInterface.php new file mode 100644 index 00000000000..5823d3201bc --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Matcher/UrlMatcherInterface.php @@ -0,0 +1,38 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing\Matcher; + +use Symfony\Component\Routing\RequestContextAwareInterface; + +/** + * UrlMatcherInterface is the interface that all URL matcher classes must implement. + * + * @author Fabien Potencier + * + * @api + */ +interface UrlMatcherInterface extends RequestContextAwareInterface +{ + /** + * Tries to match a URL with a set of routes. + * + * @param string $pathinfo The path info to be parsed + * + * @return array An array of parameters + * + * @throws ResourceNotFoundException If the resource could not be found + * @throws MethodNotAllowedException If the resource was found but the request method is not allowed + * + * @api + */ + public function match($pathinfo); +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/README.md b/3rdparty/symfony/routing/Symfony/Component/Routing/README.md new file mode 100644 index 00000000000..eb72334d2ea --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/README.md @@ -0,0 +1,32 @@ +Routing Component +================= + +Routing associates a request with the code that will convert it to a response. + +The example below demonstrates how you can set up a fully working routing +system: + + use Symfony\Component\HttpFoundation\Request; + use Symfony\Component\Routing\Matcher\UrlMatcher; + use Symfony\Component\Routing\RequestContext; + use Symfony\Component\Routing\RouteCollection; + use Symfony\Component\Routing\Route; + + $routes = new RouteCollection(); + $routes->add('hello', new Route('/hello', array('controller' => 'foo'))); + + $context = new RequestContext(); + + // this is optional and can be done without a Request instance + $context->fromRequest(Request::createFromGlobals()); + + $matcher = new UrlMatcher($routes, $context); + + $parameters = $matcher->match('/hello'); + +Resources +--------- + +Unit tests: + +https://github.com/symfony/symfony/tree/master/tests/Symfony/Tests/Component/Routing diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/RequestContext.php b/3rdparty/symfony/routing/Symfony/Component/Routing/RequestContext.php new file mode 100644 index 00000000000..fef85b6bb34 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/RequestContext.php @@ -0,0 +1,250 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing; + +/** + * Holds information about the current request. + * + * @author Fabien Potencier + * + * @api + */ +class RequestContext +{ + private $baseUrl; + private $method; + private $host; + private $scheme; + private $httpPort; + private $httpsPort; + private $parameters; + + /** + * Constructor. + * + * @param string $baseUrl The base URL + * @param string $method The HTTP method + * @param string $host The HTTP host name + * @param string $scheme The HTTP scheme + * @param integer $httpPort The HTTP port + * @param integer $httpsPort The HTTPS port + * + * @api + */ + public function __construct($baseUrl = '', $method = 'GET', $host = 'localhost', $scheme = 'http', $httpPort = 80, $httpsPort = 443) + { + $this->baseUrl = $baseUrl; + $this->method = strtoupper($method); + $this->host = $host; + $this->scheme = strtolower($scheme); + $this->httpPort = $httpPort; + $this->httpsPort = $httpsPort; + $this->parameters = array(); + } + + /** + * Gets the base URL. + * + * @return string The base URL + */ + public function getBaseUrl() + { + return $this->baseUrl; + } + + /** + * Sets the base URL. + * + * @param string $baseUrl The base URL + * + * @api + */ + public function setBaseUrl($baseUrl) + { + $this->baseUrl = $baseUrl; + } + + /** + * Gets the HTTP method. + * + * The method is always an uppercased string. + * + * @return string The HTTP method + */ + public function getMethod() + { + return $this->method; + } + + /** + * Sets the HTTP method. + * + * @param string $method The HTTP method + * + * @api + */ + public function setMethod($method) + { + $this->method = strtoupper($method); + } + + /** + * Gets the HTTP host. + * + * @return string The HTTP host + */ + public function getHost() + { + return $this->host; + } + + /** + * Sets the HTTP host. + * + * @param string $host The HTTP host + * + * @api + */ + public function setHost($host) + { + $this->host = $host; + } + + /** + * Gets the HTTP scheme. + * + * @return string The HTTP scheme + */ + public function getScheme() + { + return $this->scheme; + } + + /** + * Sets the HTTP scheme. + * + * @param string $scheme The HTTP scheme + * + * @api + */ + public function setScheme($scheme) + { + $this->scheme = strtolower($scheme); + } + + /** + * Gets the HTTP port. + * + * @return string The HTTP port + */ + public function getHttpPort() + { + return $this->httpPort; + } + + /** + * Sets the HTTP port. + * + * @param string $httpPort The HTTP port + * + * @api + */ + public function setHttpPort($httpPort) + { + $this->httpPort = $httpPort; + } + + /** + * Gets the HTTPS port. + * + * @return string The HTTPS port + */ + public function getHttpsPort() + { + return $this->httpsPort; + } + + /** + * Sets the HTTPS port. + * + * @param string $httpsPort The HTTPS port + * + * @api + */ + public function setHttpsPort($httpsPort) + { + $this->httpsPort = $httpsPort; + } + + /** + * Returns the parameters. + * + * @return array The parameters + */ + public function getParameters() + { + return $this->parameters; + } + + /** + * Sets the parameters. + * + * This method implements a fluent interface. + * + * @param array $parameters The parameters + * + * @return Route The current Route instance + */ + public function setParameters(array $parameters) + { + $this->parameters = $parameters; + + return $this; + } + + /** + * Gets a parameter value. + * + * @param string $name A parameter name + * + * @return mixed The parameter value + */ + public function getParameter($name) + { + return isset($this->parameters[$name]) ? $this->parameters[$name] : null; + } + + /** + * Checks if a parameter value is set for the given parameter. + * + * @param string $name A parameter name + * + * @return Boolean true if the parameter value is set, false otherwise + */ + public function hasParameter($name) + { + return array_key_exists($name, $this->parameters); + } + + /** + * Sets a parameter value. + * + * @param string $name A parameter name + * @param mixed $parameter The parameter value + * + * @api + */ + public function setParameter($name, $parameter) + { + $this->parameters[$name] = $parameter; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/RequestContextAwareInterface.php b/3rdparty/symfony/routing/Symfony/Component/Routing/RequestContextAwareInterface.php new file mode 100644 index 00000000000..38443a88b7c --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/RequestContextAwareInterface.php @@ -0,0 +1,27 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing; + +/** + * @api + */ +interface RequestContextAwareInterface +{ + /** + * Sets the request context. + * + * @param RequestContext $context The context + * + * @api + */ + public function setContext(RequestContext $context); +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Route.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Route.php new file mode 100644 index 00000000000..548568334d1 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Route.php @@ -0,0 +1,312 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing; + +/** + * A Route describes a route and its parameters. + * + * @author Fabien Potencier + * + * @api + */ +class Route +{ + private $pattern; + private $defaults; + private $requirements; + private $options; + private $compiled; + + private static $compilers = array(); + + /** + * Constructor. + * + * Available options: + * + * * compiler_class: A class name able to compile this route instance (RouteCompiler by default) + * + * @param string $pattern The pattern to match + * @param array $defaults An array of default parameter values + * @param array $requirements An array of requirements for parameters (regexes) + * @param array $options An array of options + * + * @api + */ + public function __construct($pattern, array $defaults = array(), array $requirements = array(), array $options = array()) + { + $this->setPattern($pattern); + $this->setDefaults($defaults); + $this->setRequirements($requirements); + $this->setOptions($options); + } + + public function __clone() + { + $this->compiled = null; + } + + /** + * Returns the pattern. + * + * @return string The pattern + */ + public function getPattern() + { + return $this->pattern; + } + + /** + * Sets the pattern. + * + * This method implements a fluent interface. + * + * @param string $pattern The pattern + * + * @return Route The current Route instance + */ + public function setPattern($pattern) + { + $this->pattern = trim($pattern); + + // a route must start with a slash + if (empty($this->pattern) || '/' !== $this->pattern[0]) { + $this->pattern = '/'.$this->pattern; + } + + return $this; + } + + /** + * Returns the options. + * + * @return array The options + */ + public function getOptions() + { + return $this->options; + } + + /** + * Sets the options. + * + * This method implements a fluent interface. + * + * @param array $options The options + * + * @return Route The current Route instance + */ + public function setOptions(array $options) + { + $this->options = array_merge(array( + 'compiler_class' => 'Symfony\\Component\\Routing\\RouteCompiler', + ), $options); + + return $this; + } + + /** + * Sets an option value. + * + * This method implements a fluent interface. + * + * @param string $name An option name + * @param mixed $value The option value + * + * @return Route The current Route instance + * + * @api + */ + public function setOption($name, $value) + { + $this->options[$name] = $value; + + return $this; + } + + /** + * Get an option value. + * + * @param string $name An option name + * + * @return mixed The option value + */ + public function getOption($name) + { + return isset($this->options[$name]) ? $this->options[$name] : null; + } + + /** + * Returns the defaults. + * + * @return array The defaults + */ + public function getDefaults() + { + return $this->defaults; + } + + /** + * Sets the defaults. + * + * This method implements a fluent interface. + * + * @param array $defaults The defaults + * + * @return Route The current Route instance + */ + public function setDefaults(array $defaults) + { + $this->defaults = array(); + foreach ($defaults as $name => $default) { + $this->defaults[(string) $name] = $default; + } + + return $this; + } + + /** + * Gets a default value. + * + * @param string $name A variable name + * + * @return mixed The default value + */ + public function getDefault($name) + { + return isset($this->defaults[$name]) ? $this->defaults[$name] : null; + } + + /** + * Checks if a default value is set for the given variable. + * + * @param string $name A variable name + * + * @return Boolean true if the default value is set, false otherwise + */ + public function hasDefault($name) + { + return array_key_exists($name, $this->defaults); + } + + /** + * Sets a default value. + * + * @param string $name A variable name + * @param mixed $default The default value + * + * @return Route The current Route instance + * + * @api + */ + public function setDefault($name, $default) + { + $this->defaults[(string) $name] = $default; + + return $this; + } + + /** + * Returns the requirements. + * + * @return array The requirements + */ + public function getRequirements() + { + return $this->requirements; + } + + /** + * Sets the requirements. + * + * This method implements a fluent interface. + * + * @param array $requirements The requirements + * + * @return Route The current Route instance + */ + public function setRequirements(array $requirements) + { + $this->requirements = array(); + foreach ($requirements as $key => $regex) { + $this->requirements[$key] = $this->sanitizeRequirement($key, $regex); + } + + return $this; + } + + /** + * Returns the requirement for the given key. + * + * @param string $key The key + * + * @return string The regex + */ + public function getRequirement($key) + { + return isset($this->requirements[$key]) ? $this->requirements[$key] : null; + } + + /** + * Sets a requirement for the given key. + * + * @param string $key The key + * @param string $regex The regex + * + * @return Route The current Route instance + * + * @api + */ + public function setRequirement($key, $regex) + { + $this->requirements[$key] = $this->sanitizeRequirement($key, $regex); + + return $this; + } + + /** + * Compiles the route. + * + * @return CompiledRoute A CompiledRoute instance + */ + public function compile() + { + if (null !== $this->compiled) { + return $this->compiled; + } + + $class = $this->getOption('compiler_class'); + + if (!isset(self::$compilers[$class])) { + self::$compilers[$class] = new $class; + } + + return $this->compiled = self::$compilers[$class]->compile($this); + } + + private function sanitizeRequirement($key, $regex) + { + if (is_array($regex)) { + throw new \InvalidArgumentException(sprintf('Routing requirements must be a string, array given for "%s"', $key)); + } + + if ('^' == $regex[0]) { + $regex = substr($regex, 1); + } + + if ('$' == substr($regex, -1)) { + $regex = substr($regex, 0, -1); + } + + return $regex; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/RouteCollection.php b/3rdparty/symfony/routing/Symfony/Component/Routing/RouteCollection.php new file mode 100644 index 00000000000..b3289d337c4 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/RouteCollection.php @@ -0,0 +1,259 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing; + +use Symfony\Component\Config\Resource\ResourceInterface; + +/** + * A RouteCollection represents a set of Route instances. + * + * When adding a route, it overrides existing routes with the + * same name defined in the instance or its children and parents. + * + * @author Fabien Potencier + * + * @api + */ +class RouteCollection implements \IteratorAggregate +{ + private $routes; + private $resources; + private $prefix; + private $parent; + + /** + * Constructor. + * + * @api + */ + public function __construct() + { + $this->routes = array(); + $this->resources = array(); + $this->prefix = ''; + } + + public function __clone() + { + foreach ($this->routes as $name => $route) { + $this->routes[$name] = clone $route; + if ($route instanceof RouteCollection) { + $this->routes[$name]->setParent($this); + } + } + } + + /** + * Gets the parent RouteCollection. + * + * @return RouteCollection The parent RouteCollection + */ + public function getParent() + { + return $this->parent; + } + + /** + * Sets the parent RouteCollection. + * + * @param RouteCollection $parent The parent RouteCollection + */ + public function setParent(RouteCollection $parent) + { + $this->parent = $parent; + } + + /** + * Gets the current RouteCollection as an Iterator. + * + * @return \ArrayIterator An \ArrayIterator interface + */ + public function getIterator() + { + return new \ArrayIterator($this->routes); + } + + /** + * Adds a route. + * + * @param string $name The route name + * @param Route $route A Route instance + * + * @throws \InvalidArgumentException When route name contains non valid characters + * + * @api + */ + public function add($name, Route $route) + { + if (!preg_match('/^[a-z0-9A-Z_.]+$/', $name)) { + throw new \InvalidArgumentException(sprintf('The provided route name "%s" contains non valid characters. A route name must only contain digits (0-9), letters (a-z and A-Z), underscores (_) and dots (.).', $name)); + } + + $parent = $this; + while ($parent->getParent()) { + $parent = $parent->getParent(); + } + + if ($parent) { + $parent->remove($name); + } + + $this->routes[$name] = $route; + } + + /** + * Returns the array of routes. + * + * @return array An array of routes + */ + public function all() + { + $routes = array(); + foreach ($this->routes as $name => $route) { + if ($route instanceof RouteCollection) { + $routes = array_merge($routes, $route->all()); + } else { + $routes[$name] = $route; + } + } + + return $routes; + } + + /** + * Gets a route by name. + * + * @param string $name The route name + * + * @return Route $route A Route instance + */ + public function get($name) + { + // get the latest defined route + foreach (array_reverse($this->routes) as $routes) { + if (!$routes instanceof RouteCollection) { + continue; + } + + if (null !== $route = $routes->get($name)) { + return $route; + } + } + + if (isset($this->routes[$name])) { + return $this->routes[$name]; + } + } + + /** + * Removes a route by name. + * + * @param string $name The route name + */ + public function remove($name) + { + if (isset($this->routes[$name])) { + unset($this->routes[$name]); + } + + foreach ($this->routes as $routes) { + if ($routes instanceof RouteCollection) { + $routes->remove($name); + } + } + } + + /** + * Adds a route collection to the current set of routes (at the end of the current set). + * + * @param RouteCollection $collection A RouteCollection instance + * @param string $prefix An optional prefix to add before each pattern of the route collection + * + * @api + */ + public function addCollection(RouteCollection $collection, $prefix = '') + { + $collection->setParent($this); + $collection->addPrefix($prefix); + + // remove all routes with the same name in all existing collections + foreach (array_keys($collection->all()) as $name) { + $this->remove($name); + } + + $this->routes[] = $collection; + } + + /** + * Adds a prefix to all routes in the current set. + * + * @param string $prefix An optional prefix to add before each pattern of the route collection + * + * @api + */ + public function addPrefix($prefix) + { + // a prefix must not end with a slash + $prefix = rtrim($prefix, '/'); + + if (!$prefix) { + return; + } + + // a prefix must start with a slash + if ('/' !== $prefix[0]) { + $prefix = '/'.$prefix; + } + + $this->prefix = $prefix.$this->prefix; + + foreach ($this->routes as $name => $route) { + if ($route instanceof RouteCollection) { + $route->addPrefix($prefix); + } else { + $route->setPattern($prefix.$route->getPattern()); + } + } + } + + public function getPrefix() + { + return $this->prefix; + } + + /** + * Returns an array of resources loaded to build this collection. + * + * @return ResourceInterface[] An array of resources + */ + public function getResources() + { + $resources = $this->resources; + foreach ($this as $routes) { + if ($routes instanceof RouteCollection) { + $resources = array_merge($resources, $routes->getResources()); + } + } + + return array_unique($resources); + } + + /** + * Adds a resource for this collection. + * + * @param ResourceInterface $resource A resource instance + */ + public function addResource(ResourceInterface $resource) + { + $this->resources[] = $resource; + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/RouteCompiler.php b/3rdparty/symfony/routing/Symfony/Component/Routing/RouteCompiler.php new file mode 100644 index 00000000000..72ececc5caa --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/RouteCompiler.php @@ -0,0 +1,128 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing; + +/** + * RouteCompiler compiles Route instances to CompiledRoute instances. + * + * @author Fabien Potencier + */ +class RouteCompiler implements RouteCompilerInterface +{ + /** + * Compiles the current route instance. + * + * @param Route $route A Route instance + * + * @return CompiledRoute A CompiledRoute instance + */ + public function compile(Route $route) + { + $pattern = $route->getPattern(); + $len = strlen($pattern); + $tokens = array(); + $variables = array(); + $pos = 0; + preg_match_all('#.\{([\w\d_]+)\}#', $pattern, $matches, PREG_OFFSET_CAPTURE | PREG_SET_ORDER); + foreach ($matches as $match) { + if ($text = substr($pattern, $pos, $match[0][1] - $pos)) { + $tokens[] = array('text', $text); + } + $seps = array($pattern[$pos]); + $pos = $match[0][1] + strlen($match[0][0]); + $var = $match[1][0]; + + if ($req = $route->getRequirement($var)) { + $regexp = $req; + } else { + if ($pos !== $len) { + $seps[] = $pattern[$pos]; + } + $regexp = sprintf('[^%s]+?', preg_quote(implode('', array_unique($seps)), '#')); + } + + $tokens[] = array('variable', $match[0][0][0], $regexp, $var); + + if (in_array($var, $variables)) { + throw new \LogicException(sprintf('Route pattern "%s" cannot reference variable name "%s" more than once.', $route->getPattern(), $var)); + } + + $variables[] = $var; + } + + if ($pos < $len) { + $tokens[] = array('text', substr($pattern, $pos)); + } + + // find the first optional token + $firstOptional = INF; + for ($i = count($tokens) - 1; $i >= 0; $i--) { + $token = $tokens[$i]; + if ('variable' === $token[0] && $route->hasDefault($token[3])) { + $firstOptional = $i; + } else { + break; + } + } + + // compute the matching regexp + $regexp = ''; + for ($i = 0, $nbToken = count($tokens); $i < $nbToken; $i++) { + $regexp .= $this->computeRegexp($tokens, $i, $firstOptional); + } + + return new CompiledRoute( + $route, + 'text' === $tokens[0][0] ? $tokens[0][1] : '', + sprintf("#^%s$#s", $regexp), + array_reverse($tokens), + $variables + ); + } + + /** + * Computes the regexp used to match the token. + * + * @param array $tokens The route tokens + * @param integer $index The index of the current token + * @param integer $firstOptional The index of the first optional token + * + * @return string The regexp + */ + private function computeRegexp(array $tokens, $index, $firstOptional) + { + $token = $tokens[$index]; + if ('text' === $token[0]) { + // Text tokens + return preg_quote($token[1], '#'); + } else { + // Variable tokens + if (0 === $index && 0 === $firstOptional && 1 == count($tokens)) { + // When the only token is an optional variable token, the separator is required + return sprintf('%s(?P<%s>%s)?', preg_quote($token[1], '#'), $token[3], $token[2]); + } else { + $nbTokens = count($tokens); + $regexp = sprintf('%s(?P<%s>%s)', preg_quote($token[1], '#'), $token[3], $token[2]); + if ($index >= $firstOptional) { + // Enclose each optional tokens in a subpattern to make it optional + $regexp = "(?:$regexp"; + if ($nbTokens - 1 == $index) { + // Close the optional subpatterns + $regexp .= str_repeat(")?", $nbTokens - $firstOptional); + } + } + + return $regexp; + } + } + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/RouteCompilerInterface.php b/3rdparty/symfony/routing/Symfony/Component/Routing/RouteCompilerInterface.php new file mode 100644 index 00000000000..5c988adafba --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/RouteCompilerInterface.php @@ -0,0 +1,29 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing; + +/** + * RouteCompilerInterface is the interface that all RouteCompiler classes must implements. + * + * @author Fabien Potencier + */ +interface RouteCompilerInterface +{ + /** + * Compiles the current route instance. + * + * @param Route $route A Route instance + * + * @return CompiledRoute A CompiledRoute instance + */ + public function compile(Route $route); +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/Router.php b/3rdparty/symfony/routing/Symfony/Component/Routing/Router.php new file mode 100644 index 00000000000..eadb2231e11 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/Router.php @@ -0,0 +1,263 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing; + +use Symfony\Component\Config\Loader\LoaderInterface; +use Symfony\Component\Config\ConfigCache; + +/** + * The Router class is an example of the integration of all pieces of the + * routing system for easier use. + * + * @author Fabien Potencier + */ +class Router implements RouterInterface +{ + protected $matcher; + protected $generator; + protected $defaults; + protected $context; + protected $loader; + protected $collection; + protected $resource; + protected $options; + + /** + * Constructor. + * + * @param LoaderInterface $loader A LoaderInterface instance + * @param mixed $resource The main resource to load + * @param array $options An array of options + * @param RequestContext $context The context + * @param array $defaults The default values + */ + public function __construct(LoaderInterface $loader, $resource, array $options = array(), RequestContext $context = null, array $defaults = array()) + { + $this->loader = $loader; + $this->resource = $resource; + $this->context = null === $context ? new RequestContext() : $context; + $this->defaults = $defaults; + $this->setOptions($options); + } + + /** + * Sets options. + * + * Available options: + * + * * cache_dir: The cache directory (or null to disable caching) + * * debug: Whether to enable debugging or not (false by default) + * * resource_type: Type hint for the main resource (optional) + * + * @param array $options An array of options + * + * @throws \InvalidArgumentException When unsupported option is provided + */ + public function setOptions(array $options) + { + $this->options = array( + 'cache_dir' => null, + 'debug' => false, + 'generator_class' => 'Symfony\\Component\\Routing\\Generator\\UrlGenerator', + 'generator_base_class' => 'Symfony\\Component\\Routing\\Generator\\UrlGenerator', + 'generator_dumper_class' => 'Symfony\\Component\\Routing\\Generator\\Dumper\\PhpGeneratorDumper', + 'generator_cache_class' => 'ProjectUrlGenerator', + 'matcher_class' => 'Symfony\\Component\\Routing\\Matcher\\UrlMatcher', + 'matcher_base_class' => 'Symfony\\Component\\Routing\\Matcher\\UrlMatcher', + 'matcher_dumper_class' => 'Symfony\\Component\\Routing\\Matcher\\Dumper\\PhpMatcherDumper', + 'matcher_cache_class' => 'ProjectUrlMatcher', + 'resource_type' => null, + ); + + // check option names and live merge, if errors are encountered Exception will be thrown + $invalid = array(); + $isInvalid = false; + foreach ($options as $key => $value) { + if (array_key_exists($key, $this->options)) { + $this->options[$key] = $value; + } else { + $isInvalid = true; + $invalid[] = $key; + } + } + + if ($isInvalid) { + throw new \InvalidArgumentException(sprintf('The Router does not support the following options: "%s".', implode('\', \'', $invalid))); + } + } + + /** + * Sets an option. + * + * @param string $key The key + * @param mixed $value The value + * + * @throws \InvalidArgumentException + */ + public function setOption($key, $value) + { + if (!array_key_exists($key, $this->options)) { + throw new \InvalidArgumentException(sprintf('The Router does not support the "%s" option.', $key)); + } + + $this->options[$key] = $value; + } + + /** + * Gets an option value. + * + * @param string $key The key + * + * @return mixed The value + * + * @throws \InvalidArgumentException + */ + public function getOption($key) + { + if (!array_key_exists($key, $this->options)) { + throw new \InvalidArgumentException(sprintf('The Router does not support the "%s" option.', $key)); + } + + return $this->options[$key]; + } + + /** + * Gets the RouteCollection instance associated with this Router. + * + * @return RouteCollection A RouteCollection instance + */ + public function getRouteCollection() + { + if (null === $this->collection) { + $this->collection = $this->loader->load($this->resource, $this->options['resource_type']); + } + + return $this->collection; + } + + /** + * Sets the request context. + * + * @param RequestContext $context The context + */ + public function setContext(RequestContext $context) + { + $this->context = $context; + + $this->getMatcher()->setContext($context); + $this->getGenerator()->setContext($context); + } + + /** + * Gets the request context. + * + * @return RequestContext The context + */ + public function getContext() + { + return $this->context; + } + + /** + * Generates a URL from the given parameters. + * + * @param string $name The name of the route + * @param mixed $parameters An array of parameters + * @param Boolean $absolute Whether to generate an absolute URL + * + * @return string The generated URL + */ + public function generate($name, $parameters = array(), $absolute = false) + { + return $this->getGenerator()->generate($name, $parameters, $absolute); + } + + /** + * Tries to match a URL with a set of routes. + * + * Returns false if no route matches the URL. + * + * @param string $url URL to be parsed + * + * @return array|false An array of parameters or false if no route matches + */ + public function match($url) + { + return $this->getMatcher()->match($url); + } + + /** + * Gets the UrlMatcher instance associated with this Router. + * + * @return UrlMatcherInterface A UrlMatcherInterface instance + */ + public function getMatcher() + { + if (null !== $this->matcher) { + return $this->matcher; + } + + if (null === $this->options['cache_dir'] || null === $this->options['matcher_cache_class']) { + return $this->matcher = new $this->options['matcher_class']($this->getRouteCollection(), $this->context, $this->defaults); + } + + $class = $this->options['matcher_cache_class']; + $cache = new ConfigCache($this->options['cache_dir'].'/'.$class.'.php', $this->options['debug']); + if (!$cache->isFresh($class)) { + $dumper = new $this->options['matcher_dumper_class']($this->getRouteCollection()); + + $options = array( + 'class' => $class, + 'base_class' => $this->options['matcher_base_class'], + ); + + $cache->write($dumper->dump($options), $this->getRouteCollection()->getResources()); + } + + require_once $cache; + + return $this->matcher = new $class($this->context, $this->defaults); + } + + /** + * Gets the UrlGenerator instance associated with this Router. + * + * @return UrlGeneratorInterface A UrlGeneratorInterface instance + */ + public function getGenerator() + { + if (null !== $this->generator) { + return $this->generator; + } + + if (null === $this->options['cache_dir'] || null === $this->options['generator_cache_class']) { + return $this->generator = new $this->options['generator_class']($this->getRouteCollection(), $this->context, $this->defaults); + } + + $class = $this->options['generator_cache_class']; + $cache = new ConfigCache($this->options['cache_dir'].'/'.$class.'.php', $this->options['debug']); + if (!$cache->isFresh($class)) { + $dumper = new $this->options['generator_dumper_class']($this->getRouteCollection()); + + $options = array( + 'class' => $class, + 'base_class' => $this->options['generator_base_class'], + ); + + $cache->write($dumper->dump($options), $this->getRouteCollection()->getResources()); + } + + require_once $cache; + + return $this->generator = new $class($this->context, $this->defaults); + } +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/RouterInterface.php b/3rdparty/symfony/routing/Symfony/Component/Routing/RouterInterface.php new file mode 100644 index 00000000000..961342bf09c --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/RouterInterface.php @@ -0,0 +1,26 @@ + + * + * For the full copyright and license information, please view the LICENSE + * file that was distributed with this source code. + */ + +namespace Symfony\Component\Routing; + +use Symfony\Component\Routing\Generator\UrlGeneratorInterface; +use Symfony\Component\Routing\Matcher\UrlMatcherInterface; + +/** + * RouterInterface is the interface that all Router classes must implements. + * + * This interface is the concatenation of UrlMatcherInterface and UrlGeneratorInterface. + * + * @author Fabien Potencier + */ +interface RouterInterface extends UrlMatcherInterface, UrlGeneratorInterface +{ +} diff --git a/3rdparty/symfony/routing/Symfony/Component/Routing/composer.json b/3rdparty/symfony/routing/Symfony/Component/Routing/composer.json new file mode 100644 index 00000000000..8d29398b243 --- /dev/null +++ b/3rdparty/symfony/routing/Symfony/Component/Routing/composer.json @@ -0,0 +1,29 @@ +{ + "name": "symfony/routing", + "type": "library", + "description": "Symfony Routing Component", + "keywords": [], + "homepage": "http://symfony.com", + "license": "MIT", + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "http://symfony.com/contributors" + } + ], + "require": { + "php": ">=5.3.2" + }, + "suggest": { + "symfony/config": "self.version", + "symfony/yaml": "self.version" + }, + "autoload": { + "psr-0": { "Symfony\\Component\\Routing": "" } + }, + "target-dir": "Symfony/Component/Routing" +} diff --git a/composer.json b/composer.json deleted file mode 100644 index 7916b15cb9f..00000000000 --- a/composer.json +++ /dev/null @@ -1,18 +0,0 @@ -{ - "description": "ownCloud gives you universal access to your files/contacts/calendar through a web interface or WebDAV.", - "homepage": "http://owncloud.org", - "license": "AGPL-3.0+", - "support": { - "email": "owncloud@kde.org", - "irc": "irc://irc.freenode.org/owncloud", - "forum": "http://forum.owncloud.org/", - "issues": "https://github.com/owncloud/core/issues" - }, - "require": { - "php": ">=5.3.2", - "symfony/routing": "2.0.*" - }, - "config": { - "vendor-dir": "3rdparty" - } -} -- 2.39.5