symfony/routing
57.6
Adequate · 26 September 2026
7.6k
lines of production code
PHP
primary language
4
measurements over time
What this system is
This system is the Symfony Routing component, a standalone library responsible for mapping HTTP requests to controller actions and generating URLs. It provides core capabilities for defining routes via PHP attributes, XML, YAML, or a fluent PHP DSL, while supporting advanced features like internationalization, environment-specific configurations, and strict parameter validation. The system optimizes performance through compiled URL matchers and generators, and includes debugging tools to trace route matching failures.
How it got here
2010–2012 — Routing component modernization
15 changes.
The Symfony Routing component was restructured into a standalone package and modernized to support PHP 8 attributes, replacing legacy annotation and class-based approaches. This period involved significant refactoring of the generator and matcher to use compiled arrays for improved performance, alongside comprehensive updates to the XML schema and exception handling.
2015–2020 — PHP DSL routing and component decoupling
12 changes.
The project introduced a fluent PHP-DSL configurator for defining routes, replacing traditional array structures with a method-chaining API. Concurrently, routing dependency injection logic was extracted from the FrameworkBundle into the dedicated Routing component to improve modularity. Extensive test coverage was added to validate the new configurators, attribute support, and compiled URL matching infrastructure.
2021–2026 — Routing component decoupling and enhancement
15 changes.
The Symfony Routing component was significantly refactored to decouple core utilities like the cache warmer and redirect controller from the FrameworkBundle, improving modularity. This period also introduced advanced routing features, including PHP 8 attribute-based configuration with environment and alias support, universal parameter requirements, and a new debug command for route matching.
Features
Introduces PHP-DSL configurators for route definitions
Adds a new set of classes in the \Loader/Configurator\ namespace (\RoutingConfigurator\, \CollectionConfigurator\, \RouteConfigurator\, \ImportConfigurator\, \AliasConfigurator\, and \RoutesReference\) that provide a fluent, object-oriented API for defining routes in PHP configuration files. This allows users to configure route paths, hosts, prefixes, imports, and aliases using method chaining instead of traditional array structures, while also supporting environment-specific configuration via the \env()\ method.
Loader/Configurator · high confidence
New PHP DSL traits for route configuration
The routing loader configurator now includes a set of internal PHP traits (AddTrait, HostTrait, LocalizedRouteTrait, PrefixTrait, RouteTrait) that enable a fluent, object-oriented way to define routes. Users can now configure route properties such as paths, hosts, prefixes, locales, UTF-8 support, conditions, schemes, methods, controllers, and firewall associations using method chaining. This includes support for localized routes with per-locale paths and prefixes, route aliasing, and stateless route attributes.
Loader/Configurator/Traits · high confidence
New PHP attribute-based routing loaders
The Loader component introduces a new family of loaders to support PHP 8 attributes for route definitions. \AttributeClassLoader\ reads \\#\[Route\]\ attributes from classes and methods, while \AttributeFileLoader\ and \AttributeDirectoryLoader\ allow loading these routes from specific files or entire directories. \AttributeRouteControllerLoader\ automatically configures the \\_controller\ default based on the class and method names, and \AttributeServicesLoader\ enables auto-registering routes from tagged controller services. These new loaders replace the legacy annotation-based approach, providing a modern, native PHP syntax for defining routing.
Loader · high confidence
New Requirement namespace with universal route parameter patterns and EnumRequirement
The Symfony Routing component introduces a new \Symfony\\Component\\Routing\\Requirement\ namespace containing a \Requirement\ enum and an \EnumRequirement\ class. The \Requirement\ enum provides a collection of universal regular-expression constants for common route parameter validations, including specific patterns for MongoDB IDs, positive integers, ASCII slugs, dates, and various UUID versions (V1–V8) as well as ULIDs and base32/base58 formats. Additionally, the new \EnumRequirement\ class allows developers to generate route requirements dynamically from PHP \BackedEnum\ cases, simplifying the validation of route parameters against enum values.
Requirement · high confidence
New router:match command for debugging route matching
A new console command, \router:match\, has been added to the Routing component to help debug route matching. This command allows users to simulate a request against the router by providing a path info and optional parameters such as HTTP method, scheme, and host. It displays which routes match the given request and explains why others do not, including details on routes that almost match. If a route matches, it automatically runs the \debug:router\ command to provide further details about the matched route.
Command · high confidence
Routing component restructured as a standalone package with new RouterBundle and modernized core classes
The Symfony Routing component has been reorganized into a standalone package, introducing the \RouterBundle\ to handle configuration and service wiring previously managed by \FrameworkBundle\. Core classes like \Route\, \CompiledRoute\, and \RequestContext\ have been modernized with constructor property promotion, native types, and new serialization methods (\\_\serialize\/\\\_unserialize\) to replace deprecated \Serializable\ implementations. The \Route\ class now uses \path\ instead of \pattern\, and \RequestContext\ supports parameter injection and context isolation via \runWith()\. Additionally, new attributes like \\#\[AsRouteLoader\]\ and \\#\[AsRoutingConditionService\]\ replace older interfaces, and the component now includes a \CHANGELOG.md\ and \README.md\ for documentation.
(repo-wide) · high confidence
Removals
Removal of Resource interface and FileResource class from Routing component
The \Symfony\\Component\\Routing\\Resource\ namespace has been removed, specifically deleting the \ResourceInterface\ and \FileResource\ classes. This change eliminates the previous abstraction for representing filesystem-based routing resources, meaning any code relying on these specific classes for resource management or uptodate checks will no longer function as before.
Resource · high confidence
Architecture
Routing dependency injection logic moved to the Routing component
The dependency injection compiler passes and router implementation previously located in FrameworkBundle have been relocated to the Symfony Routing component. This change introduces new classes such as AddExpressionLanguageProvidersPass, LocalizedRoutesPass, RoutingControllerPass, and RoutingResolverPass to handle service registration and route configuration, while the Router class now implements ServiceSubscriberInterface and WarmableInterface to manage loader instantiation and cache warming directly within the component.
DependencyInjection · high confidence
Routing service definitions moved to dedicated configuration file
The service definitions for the routing system (including loaders, the router, cache warmers, and listeners) have been extracted from the main console configuration into a new dedicated \Resources/config/routing.php\ file. This change improves modularity by isolating routing-related services, while the \console.command.router\_match\ service remains in \Resources/config/console.php\.
Resources · high confidence
Behavioural changes
Major overhaul of the XML routing schema (routing-1.0.xsd)
The XML routing schema has been significantly expanded and restructured to support new configuration capabilities. Key changes include the addition of environment-based conditional routing via the new \\<when\>\ element, support for internationalized routes with locale-specific paths and hosts, and the introduction of a \stateless\ attribute for routes and imports. The schema now allows importing resources with specific options (such as name prefixes, exclusions, and host/scheme/method constraints) and supports complex data types for defaults (lists and maps). Additionally, the namespace has been updated from symfony-project.org to symfony.com, and several attributes have been renamed or made required (e.g., \id\ is now required, \pattern\ is renamed to \path\).
Loader/schema/routing · high confidence
Refactored URL matching with request-aware interfaces and debuggability
The Matcher component has been refactored to improve request handling, debugging, and extensibility. A new RequestMatcherInterface and matchRequest() method allow matchers to operate directly on Request objects, enabling proper handling of HTTP methods and schemes. The UrlMatcher now implements this interface and supports expression language providers for dynamic route conditions. A new TraceableUrlMatcher provides detailed debugging traces for route matching failures. Additionally, new RedirectableUrlMatcher and CompiledUrlMatcher classes offer optimized and redirect-capable matching, while the legacy ApacheUrlMatcher has been removed.
Matcher · high confidence
Refactored routing matcher dumpers and introduced compiled route matching
The Matcher/Dumper component has been significantly refactored to improve performance and maintainability. The legacy PhpMatcherDumper and ApacheMatcherDumper classes have been removed and replaced by a new CompiledUrlMatcherDumper and CompiledUrlMatcherTrait, which generate optimized PHP arrays for a compiled URL matcher that processes static and dynamic routes more efficiently. Additionally, the base MatcherDumper and MatcherDumperInterface have been updated to use constructor property promotion and modern PHP syntax, and a new StaticPrefixCollection class has been added to handle route prefix grouping and ordering.
Matcher/Dumper · high confidence
Replaced class-based URL generator with compiled array dumper
The Routing component's generator dumper has shifted from producing a PHP class (PhpGeneratorDumper) to generating a static PHP array (CompiledUrlGeneratorDumper). This change improves performance by allowing the generator to operate on a pre-compiled array structure rather than instantiating and calling methods on a generated class. The base dumper classes now use constructor property promotion and expose routes via a getter, while the interface now explicitly defines the dump method as returning a string representation of executable code.
Generator/Dumper · high confidence
Routing attributes now support multiple environments, aliases, and firewall configuration
The \\#\[Route\]\ attribute in the \Symfony\\Component\\Routing\\Attribute\ namespace has been updated to allow defining multiple environments via the \env\ parameter (accepting a string or array), support route aliases through the \alias\ parameter (including deprecation metadata via \DeprecatedAlias\), and specify a firewall name via the \firewall\ parameter. Additionally, new attributes \AsRouteLoader\ and \AsRoutingConditionService\ have been introduced to mark services as route loaders and routing condition services respectively, enabling cleaner service-based routing configurations.
Attribute · high confidence
Routing component extracts cache warmer and redirect controller
The Symfony Routing component now includes its own RouterCacheWarmer and RedirectController classes, moving them out of the FrameworkBundle. The RouterCacheWarmer handles generating the router matcher and generator classes during cache warming, while the RedirectController provides a generic way to handle redirects by route name or URL, supporting options for permanent redirects, query parameter preservation, and HTTP method retention. This change decouples these core routing utilities from the framework bundle, making them available directly from the Routing component.
CacheWarmer, Controller · high confidence
Routing exceptions now implement Symfony's ExceptionInterface
The Symfony Routing component's exception classes (such as ResourceNotFoundException, MethodNotAllowedException, and RouteNotFoundException) now implement the new ExceptionInterface, which extends PHP's native \\Throwable. This change allows applications to catch all routing-related errors via a single interface, improving consistency with other Symfony components and enabling more robust error handling for routing failures.
Exception · high confidence
URL generation behavior and configuration overhaul
The URL generator now implements the ConfigurableRequirementsInterface, allowing you to disable strict parameter validation via setStrictRequirements() to prevent exceptions during generation (useful for production environments with third-party parameters). The generate() method signature has changed to use named constants (ABSOLUTE\_URL, ABSOLUTE\_PATH, RELATIVE\_PATH, NETWORK\_PATH) instead of a boolean, and it now supports internationalized routes by automatically resolving locale-specific route aliases. Additionally, a new CompiledUrlGenerator class is introduced to generate URLs from pre-compiled route data for improved performance, and URL encoding rules have been adjusted to comply with RFC 3986, specifically handling query string parameters and path segments more strictly.
Generator · high confidence
Test coverage
Add test fixtures for missing PHP start tags and variadic route arguments; Added comprehensive unit tests for the UrlGenerator component; Added test fixtures for PSR-4 controller directory loading; Added test fixtures for attribute parameter ordering; Added test fixtures for attributed routing classes; Added test fixtures for compiled URL matchers; Added test fixtures for enum types; Added test fixtures for glob pattern routing imports; Added test fixtures for locale-specific host routing; Added test fixtures for localized routing and UTF-8 support; Added test fixtures for route aliasing configuration; Added test fixtures for the new PHP 8 Route attribute; Added tests for CompiledUrlGeneratorDumper; Added tests for Route attribute configuration; Added tests for RouterCacheWarmer, RedirectController, and routing fixtures; Added tests for Routing dependency injection compiler passes and router; Added tests for localized prefix alias handling; Added tests for new Routing Requirement constants and EnumRequirement; Added tests for the compiled URL matcher dumper and static prefix collection; Added unit tests for the RouterMatchCommand; Added unit tests for the Routing Matcher components; Added unit tests for the Routing component; Added unit tests for the Routing component's loader classes; Expanded test fixtures for routing configuration and loading.
Dependencies
Initial composer.json for Symfony Routing
Added the composer.json manifest for the symfony/routing component, establishing a minimum PHP version of 8.4.1 and defining runtime dependencies on symfony/deprecation-contracts. The file also specifies development dependencies for testing and integration with other Symfony components (such as config, console, and http-kernel versions 7.4 and 8.0) and enforces a conflict with symfony/dependency-injection versions prior to 8.2.
(dependencies) · high confidence
Written by watchdog.canine.dev from the codebase's own history, inside the signed delivery this page is composed from.
How this codebase got here
Score
- CAI 47 → 58 (+11.0)
- Rubric changed (rubric-2026.08.15 → rubric-2026.09.15) — scores are not directly comparable.
Lenses
- Code Health 91 → 83 (-7.5)
- Architecture 94 → 98 (+3.6)
- Maturity 54 → 52 (-1.4)
- Readiness 17 → 42 (+25.7)
- Security 100 → 100 (+0.0)
Resolved (21)
- Coverage not measured — test suite did not build
- Dimension evaluation failed
- Duplicated block (10 lines × 2) (Loader/ContentLoaderTrait.php)
- Duplicated block (10 lines × 2) (Matcher/Dumper/CompiledUrlMatcherDumper.php)
- Duplicated block (15 lines × 2) (Tests/RouteCompilerTest.php)
- Duplicated block (20 lines × 3) (Tests/Matcher/Dumper/CompiledUrlMatcherDumperTest.php)
- Duplicated block (21 lines × 5) (Tests/Matcher/Dumper/CompiledUrlMatcherDumperTest.php)
- Duplicated block (34 lines × 2) (Tests/Generator/UrlGeneratorTest.php)
- Duplicated block (5 lines × 2) (Tests/Generator/Dumper/CompiledUrlGeneratorDumperTest.php)
- Duplicated block (5 lines × 2) (Tests/Matcher/Dumper/CompiledUrlMatcherDumperTest.php)
- Duplicated block (6 lines × 2) (Tests/Loader/Psr4DirectoryLoaderTest.php)
- Duplicated block (6 lines × 2) (Tests/Matcher/Dumper/CompiledUrlMatcherDumperTest.php)
- Duplicated block (6 lines × 2) (Tests/Matcher/RedirectableUrlMatcherTest.php)
- Duplicated block (7 lines × 2) (Tests/Matcher/Dumper/CompiledUrlMatcherDumperTest.php)
- Duplicated block (7 lines × 2) (Tests/Matcher/Dumper/CompiledUrlMatcherDumperTest.php)
- Duplicated block (7 lines × 2) (Tests/RouteTest.php)
- Duplicated block (8 lines × 2) (Tests/Matcher/UrlMatcherTest.php)
- Duplicated block (8 lines × 2) (Tests/RouteCollectionTest.php)
- No exposed public API
- No tests found
- …and 1 more
New (64)
- AttributeClassLoader.addRoute (cognitive 52) (Loader/AttributeClassLoader.php)
- AttributeClassLoader.addRoute (cyclomatic 29) (Loader/AttributeClassLoader.php)
- AttributeClassLoader.getGlobals (cognitive 25) (Loader/AttributeClassLoader.php)
- AttributeClassLoader.load (cognitive 31) (Loader/AttributeClassLoader.php)
- AttributeClassLoader.load (cyclomatic 20) (Loader/AttributeClassLoader.php)
- AttributeFileLoader.findClass (cognitive 39) (Loader/AttributeFileLoader.php)
- AttributeFileLoader.findClass (cyclomatic 20) (Loader/AttributeFileLoader.php)
- Change coupling: CollectionConfigurator.php ↔ ImportConfigurator.php (Loader/Configurator/CollectionConfigurator.php)
- CompiledUrlGeneratorDumper.getCompiledAliases (cognitive 16) (Generator/Dumper/CompiledUrlGeneratorDumper.php)
- CompiledUrlMatcherTrait.doMatch (cognitive 121) (Matcher/Dumper/CompiledUrlMatcherTrait.php)
- CompiledUrlMatcherTrait.doMatch (cyclomatic 61) (Matcher/Dumper/CompiledUrlMatcherTrait.php)
- ContentLoaderTrait.parseImport (cognitive 21) (Loader/ContentLoaderTrait.php)
- ContentLoaderTrait.parseImport (cyclomatic 16) (Loader/ContentLoaderTrait.php)
- ContentLoaderTrait.validate (cyclomatic 16) (Loader/ContentLoaderTrait.php)
- Dependency hygiene PARTLY measured — Composer dependencies read, no committed lock to grade for currency
- Duplicated block (10 lines × 2) (Loader/ContentLoaderTrait.php)
- Duplicated block (13 lines × 2) (Matcher/TraceableUrlMatcher.php)
- Duplicated block (6 lines × 2) (Generator/CompiledUrlGenerator.php)
- Duplicated block (8 lines × 2) (Loader/ContentLoaderTrait.php)
- Duplicated block (9 lines × 2) (Matcher/TraceableUrlMatcher.php)
- …and 44 more
Changes since last survey
- 26 commits — 26 feature/other, 0 fixes
By area
- (repo) — 10 commits
- (root) — 10 commits
- Generator/UrlGenerator.php — 2 commits
- DependencyInjection/RoutingResolverPass.php — 1 commit
- Tests/Generator — 1 commit
- Tests/Loader — 1 commit
- Tests/Matcher — 1 commit
Notable commits
- change: Check arrays and bools directly instead of comparing them to count()/true/false/[]
- change: Check arrays and bools directly instead of comparing them to count()/true/false/[]
- change: Merge branch '6.4' into 7.4
- change: Merge branch '6.4' into 7.4
- change: Merge branch '7.4' into 8.1
- change: Merge branch '7.4' into 8.1
- change: Merge branch '7.4' into 8.1
- change: Merge branch '8.1' into 8.2
- change: Merge branch '8.1' into 8.2
- change: Merge branch '8.1' into 8.2
- change: [BrowserKit][HttpClient][Routing] Don't pass objects to http_build_query()
- change: [FrameworkBundle] Collapse what the bundle split left repetitive
- change: [FrameworkBundle] Move the passes and commands that act on another package to that package
- change: [FrameworkBundle][Cache][Routing][Translation] Move the classes CacheBundle, RouterBundle and TranslationBundle wire into their own components
- change: [FrameworkBundle][Routing][Translation][TwigBundle] Move the last classes the components name into their own packages
- change: [HttpKernel][Routing] Perform scheme redirects before any other listener runs
- change: [Routing] Add a test about removing default query params
- change: [Routing] Add addCondition() to combine a condition with the existing ones
- change: [Routing] Allow defining default query parameters
- change: [Routing] Reject "_firewall" as a host parameter
- …and 6 more
Written by watchdog.canine.dev from the codebase's own history, inside the signed delivery this page is composed from.
Survey your own repository
symfony/routing was measured the same way every project in this corpus was: the same rubric, at a pinned commit, with the result published in full. Point a surveyor at a repository you know and see whether you agree with it.
About this page
- The score is its most recent published measurement, taken on 26 September 2026 at a pinned commit. It is not a live figure and does not change until the project is measured again.
- Measured at commit 4b4de147b756e186ef1aca646d3cb6177a651b4f — the exact code this score is about.
- Scored under rubric-2026.09.15 — the same rubric and the same method as every other entry in this index.
- Measured by watchdog.canine.dev using codehealth-analyzer preprod-a15879f6f801.