路由组件将 HTTP 请求映射到一组预存变量中。主要用于为 Web 应用程序构建路由系统。
composer require constanze-standard/routing
routing 有两个概念:
RouteCollection
路由表数据的集合,负责收集 URL 匹配的信息。Matcher
负责将请求数据和路由表进行匹配,并返回匹配结果。
使用 RouteCollection
添加一条路由数据:
use ConstanzeStandard\Routing\RouteCollection;
$collection = new RouteCollection();
$collection->add('GET', '/foo/{bar:\d+}', 'serializable data', 'unserializable data');
上例演示了使用 ConstanzeStandard\Routing\RouteCollection
的 add
方法添加一条路由数据。add 方法的参数:
$method
可以接受的 HTTP Method, 可以用字符串或数组表示一个或多个 method.$url
请求的 URL, 可以用花括号标记一个 url 参数,并用:
符号分隔定义参数的正则表达式规则。$serializable
表示可以被序列化的数据。$unserializable
表示不可序列化的参数,在我们对RouteCollection
使用缓存时,将不会缓存这个参数传入的数据,而是生成一个对应id
, 进行映射。这解决了某些类型的数据(如 \Closure)无法序列化的问题。
使用 Matcher
匹配请求数据:
use ConstanzeStandard\Routing\Matcher;
...
$matcher = new Matcher($collection);
$result = $matcher->match('GET', '/foo/12');
Matcher
接受一个 RouteCollection
作为初始化参数,然后可以调用 match
方法进行请求匹配。match
方法的返回值受匹配结果影响,分为三种情况:
- 匹配成功的情况。将返回包含 4 个元素的数组:
array(Matcher::STATUS_OK, $serializable, $unserializable, $arguments)
, 第一个元素固定为Matcher::STATUS_OK
的值,表示匹配成功;第二个元素为可序列化数据
;第三个元素为不可序列化数据
;第四个元素为 URL 参数的 mapping(如:array('id' => 10)). - URL 匹配成功,但 HTTP Method 匹配失败的情况。将返回包含 3 个元素的数组:
array(Matcher::STATUS_ERROR, Matcher::ERROR_METHOD_NOT_ALLOWED, $allowedMethods)
, 第一个元素固定为Matcher::STATUS_ERROR
的值,表示匹配出错;第二个元素为错误类型Matcher::ERROR_METHOD_NOT_ALLOWED
,表示不支持的 HTTP Method;第三个元素是一个数组,包含了这个 URL 所支持的 HTTP Method(如 array('GET', 'POST')). - 匹配失败的情况。将返回包含 2 个元素的数组:
array(Matcher::STATUS_ERROR, Matcher::ERROR_NOT_FOUND)
, 第一个元素固定为Matcher::STATUS_ERROR
的值,表示匹配出错;第二个元素为错误类型Matcher::ERROR_NOT_FOUND
表示找不到匹配项。
当路由数据变得庞大时,一次请求将会面临频繁的读写操作,这时可以使用路由缓存来加速 RouteCollection
的构建。
RouteCollection
唯一的初始化参数 $cacheFile
默认值是 null
, 表示不使用缓存,如果希望开启缓存功能,则需要通过这个参数定义缓存文件的路径:
use ConstanzeStandard\Routing\RouteCollection;
$file = __DIR__ . '/cacheFile.php';
$collection = new RouteCollection($file);
$collection->add('GET', '/foo/{bar:\d+}', 'serializable data', 'unserializable data');
...
if (file_exists($file)) {
$collection->loadCache();
} else {
$collection->cache();
}
在你第一次开启缓存时,首先要确保缓存文件是不存在的。当缓存文件不存在时,RouteCollection::cache
会根据收集到的路由数据创建缓存文件,如果缓存文件存在,RouteCollection
会直接从缓存文件一次性读取数据,并忽略 cache
方法。
你的程序必须对缓存文件所在的位置有写入权限。