You are here

protected function TraceableUrlMatcher::matchCollection in Zircon Profile 8

Same name and namespace in other branches
  1. 8.0 vendor/symfony/routing/Matcher/TraceableUrlMatcher.php \Symfony\Component\Routing\Matcher\TraceableUrlMatcher::matchCollection()

Tries to match a URL with a set of routes.

Parameters

string $pathinfo The path info to be parsed:

RouteCollection $routes The set of routes:

Return value

array An array of parameters

Throws

ResourceNotFoundException If the resource could not be found

MethodNotAllowedException If the resource was found but the request method is not allowed

Overrides UrlMatcher::matchCollection

File

vendor/symfony/routing/Matcher/TraceableUrlMatcher.php, line 43

Class

TraceableUrlMatcher
TraceableUrlMatcher helps debug path info matching by tracing the match.

Namespace

Symfony\Component\Routing\Matcher

Code

protected function matchCollection($pathinfo, RouteCollection $routes) {
  foreach ($routes as $name => $route) {
    $compiledRoute = $route
      ->compile();
    if (!preg_match($compiledRoute
      ->getRegex(), $pathinfo, $matches)) {

      // does it match without any requirements?
      $r = new Route($route
        ->getPath(), $route
        ->getDefaults(), array(), $route
        ->getOptions());
      $cr = $r
        ->compile();
      if (!preg_match($cr
        ->getRegex(), $pathinfo)) {
        $this
          ->addTrace(sprintf('Path "%s" does not match', $route
          ->getPath()), self::ROUTE_DOES_NOT_MATCH, $name, $route);
        continue;
      }
      foreach ($route
        ->getRequirements() as $n => $regex) {
        $r = new Route($route
          ->getPath(), $route
          ->getDefaults(), array(
          $n => $regex,
        ), $route
          ->getOptions());
        $cr = $r
          ->compile();
        if (in_array($n, $cr
          ->getVariables()) && !preg_match($cr
          ->getRegex(), $pathinfo)) {
          $this
            ->addTrace(sprintf('Requirement for "%s" does not match (%s)', $n, $regex), self::ROUTE_ALMOST_MATCHES, $name, $route);
          continue 2;
        }
      }
      continue;
    }

    // check host requirement
    $hostMatches = array();
    if ($compiledRoute
      ->getHostRegex() && !preg_match($compiledRoute
      ->getHostRegex(), $this->context
      ->getHost(), $hostMatches)) {
      $this
        ->addTrace(sprintf('Host "%s" does not match the requirement ("%s")', $this->context
        ->getHost(), $route
        ->getHost()), self::ROUTE_ALMOST_MATCHES, $name, $route);
      continue;
    }

    // check HTTP method requirement
    if ($requiredMethods = $route
      ->getMethods()) {

      // HEAD and GET are equivalent as per RFC
      if ('HEAD' === ($method = $this->context
        ->getMethod())) {
        $method = 'GET';
      }
      if (!in_array($method, $requiredMethods)) {
        $this->allow = array_merge($this->allow, $requiredMethods);
        $this
          ->addTrace(sprintf('Method "%s" does not match any of the required methods (%s)', $this->context
          ->getMethod(), implode(', ', $requiredMethods)), self::ROUTE_ALMOST_MATCHES, $name, $route);
        continue;
      }
    }

    // check condition
    if ($condition = $route
      ->getCondition()) {
      if (!$this
        ->getExpressionLanguage()
        ->evaluate($condition, array(
        'context' => $this->context,
        'request' => $this->request,
      ))) {
        $this
          ->addTrace(sprintf('Condition "%s" does not evaluate to "true"', $condition), self::ROUTE_ALMOST_MATCHES, $name, $route);
        continue;
      }
    }

    // check HTTP scheme requirement
    if ($requiredSchemes = $route
      ->getSchemes()) {
      $scheme = $this->context
        ->getScheme();
      if (!$route
        ->hasScheme($scheme)) {
        $this
          ->addTrace(sprintf('Scheme "%s" does not match any of the required schemes (%s); the user will be redirected to first required scheme', $scheme, implode(', ', $requiredSchemes)), self::ROUTE_ALMOST_MATCHES, $name, $route);
        return true;
      }
    }
    $this
      ->addTrace('Route matches!', self::ROUTE_MATCHES, $name, $route);
    return true;
  }
}