lloydzhou/router

该包已被废弃且不再维护。作者建议使用bephp/router包。

PHP的快速路由器。匹配URL并执行PHP函数。根据处理器函数参数列表自动获取变量。支持将路由器回调处理器编译成纯数组源代码。

v1.1.0 2016-04-15 07:49 UTC

README

Build Status Coverage Status Latest Stable Version Total Downloads Latest Unstable Version License
PHP的简单路由器。
匹配URL并执行PHP函数。
根据处理器函数参数列表自动获取变量。
支持将路由器回调处理器编译成纯数组源代码。

中文版.

安装

composer require bephp/router

API参考

group/prefix($prefix, $hook)

添加具有相同前缀的组路由器。如果不传递参数$prefix,则将路由器实例的$prefix属性重置为空字符串。将$hook合并到该组中。

match($method, $path, $callback, $hook)

根据给定的$method和$path创建路由树,将$callback和$hook存储在叶节点中。

get/post/put/delete/head/options($path, $callback, $hook)

包装没有$method参数的match方法。还定义了"post"、"put"、"delete"、"head"等。

execute()

应用程序的入口点。有3个可选参数,$params将与请求变量合并并传递给回调处理器。在不作为Web服务器部署时,可以传递$method和$path来测试此库。

error()

  1. 如果使用$error_code和$callback调用此API,只需为错误代码定义回调处理器。
  2. 如果使用$error_code和其他参数调用此API,将触发错误回调处理器,参数将传递给错误处理器。

hook()

  1. 如果使用$hook_name和$callback调用此API,只需为钩子名称定义回调处理器。
  2. 如果使用$hook_name和其他参数调用此API,将触发钩子处理器,参数将传递给钩子处理器。
  3. 有2个特殊钩子:"before"和"after",此库将在执行处理器之前自动调用"before"钩子,并在执行处理器之后调用"after"钩子。
  4. "after"钩子将自动触发回调处理器的返回值。
  5. "before"钩子和其他用户定义的钩子将自动触发当前路由对象$router和存储在$router->params中的合并参数。如果这些钩子返回false,将触发406错误处理器。

验证

使用ctype函数在pathinfo中验证参数
示例

如果定义了路由器:"/hello/:name:a.json",并使用URL:"/hello/lloyd.json"解析URL。
将调用函数"ctype_alpha"来验证"lloyd"。
验证命令将ctype函数映射

A => ctype_alnum
a => ctype_alpha
d => ctype_digit
x => ctype_xdigit
l => ctype_lower
u => ctype_upper

编译

PHP请求总是匹配回调处理程序。但是请求只匹配一个回调。因此,我们可以将路由树节点编译成普通数组,以节省时间。

开发模型

使用CRouter而不是Router,将始终编译源代码为目标文件。

$crouter = new CRouter("router.inc.php", true);

生产模型

仅包含目标源代码,并使用参数执行它。

$router = include("router.inc.php");
$router->execute();

性能

  1. 使用树结构在叶节点上存储回调处理程序。确保查找回调函数的时间复杂度为O(log n)。 树节点
  2. 使用CRouter类,支持将路由回调处理程序编译成普通数组源代码。因此可以节省时间,通过分割路径信息来创建存储回调的树节点。

基准测试

使用"php-router-benchmark"测试路由性能。

最坏情况匹配

此基准测试匹配最后一个路由和未知路由。它生成随机前缀和后缀的路由,以试图阻止任何优化。1,000个路由,每个路由有9个参数。

此基准测试由10个测试组成。每个测试执行1,000次,结果剪枝,然后取平均值。超出平均值3个标准差的值将被丢弃。

测试名称 结果 时间 + 间隔 变化
路由器 - 未知路由(1000个路由) 993 0.0000232719 +0.0000000000 基准线
路由器 - 最后一个路由(1000个路由) 981 0.0000955424 +0.0000722705 慢311%
FastRoute - 未知路由(1000个路由) 990 0.0005051955 +0.0004819236 慢2071%
FastRoute - 最后一个路由(1000个路由) 998 0.0005567203 +0.0005334484 慢2292%
Symfony2 Dumped - 未知路由(1000个路由) 998 0.0006116139 +0.0005883420 慢2528%
Symfony2 Dumped - 最后一个路由(1000个路由) 998 0.0007765370 +0.0007532651 慢3237%
Symfony2 - 未知路由(1000个路由) 996 0.0028456177 +0.0028223458 慢12128%
Symfony2 - 最后一个路由(1000个路由) 993 0.0030129542 +0.0029896823 慢12847%
Aura v2 - 最后一个路由(1000个路由) 989 0.1707107230 +0.1706874511 慢733450%
Aura v2 - 未知路由(1000个路由) 988 0.1798588730 +0.1798356011 慢772760%

示例

belong是一个简单的示例,请参阅example.php中的完整示例。

(new Router())
->error(405, function($message){
    header('Location: /hello/world', true, 302);
})
->get('/hello/:name', function($name){
    echo "Hello $name !!!";
})

启动服务器

php -S 0.0.0.0:8888 example.php

测试

URL不匹配,触发405错误处理程序。

curl -vvv 127.0.0.1:8888
> GET / HTTP/1.1
> User-Agent: curl/7.35.0
> Host: 127.0.0.1:8888
> Accept: */*
> 
< HTTP/1.1 302 Found
< Host: 127.0.0.1:8888
< Connection: close
< X-Powered-By: PHP/5.5.9-1ubuntu4.12
< Location: /hello/world
< Content-type: text/html
< 
* Closing connection 0

URL匹配获取当前结果。

curl -vvv 127.0.0.1:8888/hello/lloyd
* Connected to 127.0.0.1 (127.0.0.1) port 8888 (#0)
> GET /hello/lloyd HTTP/1.1
> User-Agent: curl/7.35.0
> Host: 127.0.0.1:8888
> Accept: */*
> 
< HTTP/1.1 200 OK
< Host: 127.0.0.1:8888
< Connection: close
< X-Powered-By: PHP/5.5.9-1ubuntu4.12
< Content-type: text/html
< 
* Closing connection 0
Hello lloyd !!!

演示

有一个博客演示,与ActiveRecordMicroTpl一起工作。