cakephp/cakephp · error · InvalidArgumentException

Cannot find route class

Error message

Cannot find route class %s

What it means

RouteBuilder::_makeRoute() accepts a route class name string and resolves it with App::className() in the Routing/Route namespace. If the class does not exist (or is not autoloadable), the builder throws this InvalidArgumentException instead of instantiating an unknown class.

Solutions

  1. Create the class at src/Routing/Route/{Name}Route.php extending Cake\Routing\Route\Route.
  2. Correct the routeClass option spelling, e.g. 'routeClass' => 'DashedRoute' (name without the 'Route' suffix).
  3. Verify composer autoload/PSR-4 mapping includes the app namespace.
  4. Remove the routeClass option if the default (or an existing built-in) class suffices.

Example fix

// before
$routes->connect('/pages/*', ['controller' => 'Pages'], ['routeClass' => 'FancyRoute']);
// after (class exists or use built-in)
$routes->connect('/pages/*', ['controller' => 'Pages'], ['routeClass' => 'DashedRoute']);
Defensive patterns

Strategy: validation

Validate before calling

use Cake\Core\App;
if (App::className('FancyRoute', 'Routing/Route') === null) {
    throw new RuntimeException('Route class does not exist');
}

Try / catch

try {
    $builder->connect('/path', $defaults, ['routeClass' => $class]);
} catch (\InvalidArgumentException $e) {
    // fall back to default Route class
}

Prevention

When it happens

Trigger: connect('/path', [...], ['routeClass' => 'MyRoute']) where src/Routing/Route/MyRoute.php doesn't exist; typo in the routeClass name; forgetting to define the class in the app namespace; a plugin route class that is not loaded.

Common situations: Custom route classes after refactors; copying routeClass options from tutorials with nonexistent classes; PSR-4 namespace mismatch so autoloading fails.

Related errors


AI-assisted analysis of cakephp/cakephp@1128eba9b0 (2026-09-12). Data as JSON: /api/errors/1382eee3b42a3ef6. Report an issue: GitHub.

Appendix: source

Thrown at src/Routing/RouteBuilder.php:761

    }

    /**
     * Create a route object, or return the provided object.
     *
     * @param \Cake\Routing\Route\Route|string $route The route template or route object.
     * @param array $defaults Default parameters.
     * @param array<string, mixed> $options Additional options parameters.
     * @return \Cake\Routing\Route\Route
     * @throws \InvalidArgumentException when route class or route object is invalid.
     * @throws \BadMethodCallException when the route to make conflicts with the current scope
     */
    protected function _makeRoute(Route|string $route, array $defaults, array $options): Route
    {
        if (is_string($route)) {
            /** @var class-string<\Cake\Routing\Route\Route>|null $routeClass */
            $routeClass = App::className($options['routeClass'], 'Routing/Route');
            if ($routeClass === null) {
                throw new InvalidArgumentException(sprintf(
                    'Cannot find route class %s',
                    $options['routeClass'],
                ));
            }

            $route = str_replace('//', '/', $this->_path . $route);
            if ($route !== '/') {
                $route = rtrim($route, '/');
            }

            foreach ($this->_params as $param => $val) {
                if (isset($defaults[$param]) && $param !== 'prefix' && $defaults[$param] !== $val) {
                    $msg = 'You cannot define routes that conflict with the scope. ' .
                        'Scope had %s = %s, while route had %s = %s';
                    throw new BadMethodCallException(sprintf(
                        $msg,
                        $param,
                        $val,

View on GitHub (pinned to 1128eba9b0)