CodeIgniter不支持嵌套路由分组,所有路由均为扁平数组映射,需按“具体到通用”顺序手动配置,通配符位置错误或顺序颠倒将导致匹配失效和大量404。

CodeIgniter 本身不支持嵌套路由分组
CodeIgniter(包括 CI3 和 CI4)的路由系统没有 group()、middleware() 这类分组概念,所谓“嵌套路由分组”其实是开发者误用或混淆了其他框架(如 ThinkPHP、Laravel)的术语。CI 的路由是纯扁平数组映射,所有规则都写在 application/config/routes.php 中,靠顺序和正则优先级决定匹配行为。
看似“嵌套”的写法实际只是路径前缀叠加
有人会这样写:
$route['admin'] = 'admin/dashboard'; $route['admin/users'] = 'admin/user/index'; $route['admin/users/(:num)'] = 'admin/user/view/$1';
这看起来像“admin 下嵌套 users”,但 CI 并不认为它们属于同一组——每条规则独立解析、按声明顺序从上到下尝试匹配。所以:
-
admin/users/123会命中第三条规则,跳过第二条 - 如果把第三条写在第二条前面,
admin/users/123就永远匹配不到——因为admin/users已被第二条吃掉,剩余/123不再参与后续匹配 - 不存在“子分组自动继承父前缀”或“退出分组作用域”的机制
容易踩的坑:通配符位置 + 顺序错乱 = 大量 404
最典型的问题是把宽泛规则写在具体规则之前,比如:
$route['(:any)'] = 'pages/view/$1'; // ❌ 错误:放太前,所有请求都被它截胡 $route['products/(:num)'] = 'products/detail/$1'; // 永远不执行
正确顺序必须是“从具体到通用”:
- 先写
$route['products/(:num)'] - 再写
$route['products'] - 最后才写
$route['(:any)']或$route['(:any)/(:any)/(:any)/.*']
否则你会看到大量本该进控制器的请求,全被兜底规则吞掉,参数传错、方法找不到、甚至 base_url() 在 404 视图里报错——因为兜底规则没加载 url 辅助函数。
想模拟分组效果?靠路径结构 + 正则约束
如果你需要统一处理 /api/v1/xxx 下所有路由,或限制某段必须是数字/小写/特定格式,只能手动控制:
- 用正则替代
(:any):比如$route['api/v1/([a-z]+)/(:num)'] = 'api/$1/handle/$2'; - 避免滥用
(:any):它等价于([^/]+),不匹配斜杠,所以/a/b/c是三个段,不是一段 - 要捕获“多段及以后全部”,必须显式加
/.+或/.*,且放在靠后位置
真正的复杂路由逻辑(比如权限隔离、模块化前缀管理)得靠控制器层做判断,而不是指望路由系统“分组”。



















