2015-4-11 20:51:06

又搞了一天, 解决了一堆bug, 重新规划了类文件夹, 改善自动加载功能

最新的特性就是支持子域名路由了

因为整个框架还在完善当中, 而且里边有好多接口有我自己申请的第三方appkey 和 secretkey, 所以还不方便提供下载

但是路由功能完成以后,整体的框架也就快完工了, 再修修补补就行了

四年啦, 从零开始, 终于有模有样了....

比如:

访问 www.zhangzhibin.com 是会跳转到网站首页的

访问 www.zhangzhibin.com/bbs 是会跳转到bbs论坛页面

但是我想在访问 love.zhangzhibin.com时也跳转到bbs论坛页面 (因为在大众点评留下的开发者信息是love.zhangzhibin.com)

此时可以在路由文件中设置一个对应关系就可以了(第8行):

 public function setRoute()
{
$this->route_config = array(
'subdomain' => array(),
'uri' => array()
); //================子域名路由
$this->route_config['subdomain']['#love_(\d)_([a-z])#'] = 'test/index/safe/$1/$2';
$this->route_config['subdomain']['#love_(\d)#'] = 'test/index/safe/$1';
$this->route_config['subdomain']['#love#'] = 'bbs/index/index'; //================ uri路由
$this->route_config['uri']['#([a-z]+)_(\d+)\.html#'] = 'test/index/testroute/$1/$2';
$this->route_config['uri']['#map\.html#'] = 'map/index/line';
}

测试结果:

 http://love_1.zhangzhibin.com/
Array
(
[$1] => 1
) http://love_1_a.zhangzhibin.com/
Array
(
[$1] => 1
[$2] => a
)

注意, 这里的路由项的键两边有两个'#'做为边界符是需要自己去写的, 如果担心冲突, 大家可以根据需要自己去设定边界符

整体的逻辑是这样的

先匹配子域名的路由, 然后匹配uri的路由(不匹配?后边的查询串)

将两步匹配到的参数合并起来, 因为uri在第二步匹配, 所以uri的匹配结果会覆盖掉子域名的路由结果

下边贴出代码:

 <?php
class Route
{
public $subdomain = '';
public $uri = ''; public $ismatch = false;
public $DomainMatchName = false;
public $UriMatchName = false;
public $MatchName = false; public $module = 'index';
public $controller = 'index';
public $action = 'index'; public $args = array(); public $error = ''; public $route_config = array(
'subdomain' => array(),
'uri' => array()
); public function __construct($subdomain, $uri)
{
$this->subdomain = $subdomain;
$this->uri = $uri; //设置路由配置信息
$this->setRoute(); //先检查子域名路由
//如果子域名中只有英文字母就不再匹配
if (!empty($this->route_config['subdomain']) || !ctype_alpha($this->subdomain)) {
$this->DomainMatchName = $this->preg_parse($this->route_config['subdomain'], $this->subdomain);
} //再检查uri路由
//如果uri中不含有"/"才会走正则匹配
if (!empty($this->route_config['uri']) && strpos($this->uri, '/') === false) {
$this->UriMatchName = $this->preg_parse($this->route_config['uri'], $this->uri);
} else {
$this->arr_parse();
} ($this->DomainMatchName || $this->UriMatchName) && ($this->ismatch = true); $this->MatchName = $this->UriMatchName ? $this->UriMatchName : $this->DomainMatchName; return $this;
} public function setRoute()
{
//================子域名路由
$this->route_config['subdomain']['#love_(\d)_([a-z])#'] = 'test/index/safe/$1/$2';
$this->route_config['subdomain']['#love_(\d)#'] = 'test/index/safe/$1';
$this->route_config['subdomain']['#love#'] = 'bbs/index/index'; //================ uri路由
$this->route_config['uri']['#svnsort#'] = 'index/index/svnsort';
$this->route_config['uri']['#nicename_json#'] = 'index/index/nicenamejson';
$this->route_config['uri']['#nicename#'] = 'index/index/nicename';
$this->route_config['uri']['#\btest\b[^\/]#'] = 'test/index/rtest'; //是下边路由的前缀, 加上\b就是全词匹配了
$this->route_config['uri']['#\btest1\b#'] = 'test/index/rtest'; // 不会匹配test, 只会匹配test1 } //正则匹配分析
public function preg_parse($routeconfig, $subject)
{
$routename = false;
foreach ($routeconfig as $pattern => $route) {
$arrRoute = explode('/', $route); preg_match($pattern, $subject, $matches); if (empty($matches)) {
continue;
} else {
$routename = $pattern; $arrMCA = array_slice($arrRoute, 0, 3);
$arrArg = array_slice($arrRoute, 3); $this->module = $arrMCA[0];
$this->controller = $arrMCA[1];
$this->action = $arrMCA[2]; $arrMatchArg = array();
foreach ($matches as $key => $value) {
$arrMatchArg['$'.$key] = $value;
} foreach ($arrArg as $value) {
$this->args[$value] = $arrMatchArg[$value];
} break;
}
} return $routename;
} //正则检查uri没有匹配上的情况下, 数组匹配分析
public function arr_parse()
{
//获得module/controller/action
$arrPathInfo = explode('/', $this->uri);//存放URL中以正斜线隔开的内容的数组 !empty($arrPathInfo[0]) && ($this->module = $arrPathInfo[0]);
!empty($arrPathInfo[1]) && ($this->controller = $arrPathInfo[1]);
!empty($arrPathInfo[2]) && ($this->action = $arrPathInfo[2]); //存放除module/controller/action之外的参数
// /a/1/b/2/c/3 ==> ?a=1&b=2&c=3
// 当键和值不成对出现时,默认最后一个键的值为0
// 参数中不要出现数字键,否则在合并post,get参数时会出错
$intPathInfo = count($arrPathInfo);
if ($intPathInfo > 3) {
$arrPath = array_slice($arrPathInfo, 3);
$intArgNum = count($arrPath);
if ($intArgNum % 2 != 0) {
$arrPath[] = 0;
}
$intArgNum = count($arrPath); for ($i=0; $i<$intArgNum; $i=$i+2) {
$this->args[$arrPath[$i]] = $arrPath[$i+1];
}
}
}
}

当然你也可以写自己的路由类, 只需要返回给框架所需要的数据就行啦~

     //可以自己实现路由类, 只要要返回 module, controller, action, 以及匹配到的参数就行了
//返回是否匹配了路由, 匹配路由的名字, 路由指向的module,controller,action, 路由错误信息,方便调试
public function route()
{
$this->route = new Route($this->subdomain, $this->document_uri); $this->isRouteMatch = $this->route->ismatch;
$this->RouteMatchName = $this->route->MatchName; $this->module = $this->route->module;
$this->controller = $this->route->controller;
$this->action = $this->route->action; $this->setData();
}

zpf 路由功能的更多相关文章

  1. 吐血原创:mini2440和win7笔记本利用无路由功能的交换机共享上网(使用x-router软路由)

    真的是要吐血了,为了使自己的win7系统笔记本和mini2440,通过交换机(没有路由功能,才5口,和HUB差不多)共享宽带上网,并且连接上的宽带还是长城宽带,我用尽各种cmd命令都查不到长城宽带的默 ...

  2. PHP实现一个简单url路由功能

    如果一个页面的内容呈现,需要根据url上传递的参数来进行渲染.很多时候可能是这样子写:xxx.com/xx?c=x&m=x& t=..,而我们看到的url往往是这样子的(以新浪微游戏的 ...

  3. 玩转nodeJS系列:使用原生API实现简单灵活高效的路由功能(支持nodeJs单机集群),nodeJS本就应该这样轻快

    前言: 使用nodeJS原生API实现快速灵活路由,方便与其他库/框架进行整合: 1.原生API,简洁高效的轻度封装,加速路由解析,nodeJS本就应该这样轻快 2.不包含任何第三方库/框架,可以灵活 ...

  4. nodeJS实现路由功能

    前面的话 本文将使用NodeJS实现较复杂应用的路由功能 结构 项目结构如下 代码如下 功能 [router.js] // 加载所需模块 var http = require('http'); var ...

  5. 理解 angular 的路由功能

    相信很多人使用angular 都是因为他路由功能而用的 深入理解ANGULARUI路由_UI-ROUTER 最近在用 ionic写个webapp 看到几个demo中路由有好几种,搞的有点晕,查下资料研 ...

  6. Cisco 的基本配置实例之五----交换机的路由功能与DHCP 功能

    5.配置交换机的路由功能 说明:只有在三层交换机上才有路由功能,其他的二层接入交换机要想在不同的vlan之间传送数据需要通过trunk口到核心交换机上进行完路由交换后才可以. TEST(config) ...

  7. Android 的媒体路由功能应用与框架解析

    一.功能描述 Android 的媒体路由API被设计用来允许多种媒体(视频.音乐.图片)在与ANDROID设备连接(无线或有线)的辅助设备(如电视.立体声.家庭戏院系统.音乐播放机)上显示和播放,使用 ...

  8. SpringCloud系列八:Zuul 路由访问(Zuul 的基本使用、Zuul 路由功能、zuul 过滤访问、Zuul 服务降级)

    1.概念:Zuul 路由访问 2.具体内容 在现在为止所有的微服务都是通过 Eureka 找到的,但是在很多的开发之中为了规范微服务的使用,提供有一个路由的处理控制组件:Zuul,也就是说 Zuul ...

  9. 【学习笔记】node.js重构路由功能

    摘要:利用node.js模块化实现路由功能,将请求路径作为参数传递给一个route函数,这个函数会根据参数调用一个方法,最后输出浏览器响应内容 1.介绍 node.js是一个基于Chrome V8引擎 ...

随机推荐

  1. intelligencia.urlrewriter使用

    见github: https://github.com/sethyates/urlrewriter

  2. 一个Struts2的实例

    对Web应用程序而言,需要跨越HTTP协议的两个障碍——无状态和基于文本. 在没有使用struts的时候,你会有一个很真切的体会,就是如何把html页面上的数据提交给后台处理,以什么格式提交? 这是个 ...

  3. soj4271 Love Me, Love My Permutation (DFS)

    4271: Love Me, Love My Permutation Description Given a permutation of n: a[0], a[1] ... a[n-1], ( it ...

  4. 大数据之Ganglia安装1

    0.前期准备修改主机名.ip.iptables关闭:时间同步:ntpdate -s time.windows.com;软件准备ganglia-3.7.1.tar.gz.ganglia-web-3.7. ...

  5. Swift2.1 语法指南——嵌套类型

    原档:https://developer.apple.com/library/prerelease/ios/documentation/Swift/Conceptual/Swift_Programmi ...

  6. Android 实现简单音乐播放器(一)

    今天掐指一算,学习Android长达近两个月了,今天开始,对过去一段时间的学习收获以及遇到的疑难杂症做一些总结. 简单音乐播放器是我自己完成的第一个功能较为完整的APP,可以说是我的Android学习 ...

  7. CentOS-6.5安装zabbix2.4.4

    使用epel源  (检查网络连接是否正常)   //这里使用epel源 [root@localhost /]# wget -O /etc/yum.repos.d/CentOS-Base.repo ht ...

  8. webpack 教程 那些事儿04-webpack项目实战分析

    这节主要讲解真正项目用用到的 webpack配置问题,项目实战篇 就像我们不会完全做一个项目,不用别人的轮子一样.这个配置我们借用 vue-cli 搭建的配置来研究,因为它已经足够优秀. 有了前面的基 ...

  9. MySQL中快速复制数据表方法汇总

    本文将着重介绍两个MySQL命令的组合,它将以原有数据表为基础,创建相同结构和数据的新数据表. 这可以帮助你在开发过程中快速的复制表格作为测试数据,而不必冒险直接操作正在运行 的数据表. 示例如下: ...

  10. 微软“One Windows”的梦想已经破灭了吗?

    导读 Windows 10 正式公布的时候,微软曾表示该系统将开启更为个性化的计算新纪元,可让用户在使用各类设备处理各项事务时,享受到一致.熟悉和可兼容的体验,从 Xbox 到 PC 和手机,再到平板 ...