Yii的版本化

本文链接:https://www.cnblogs.com/alanabc/p/10246023.html

讲解思路

把关系提到前面来讲,希望能够大致说清楚吧:

  • 版本化需要路由支持,这样才能从URL中解析并定位到方法;
  • 定位方法需要先定位到控制器;
  • 控制器有两种:
    • 一种是默认的,通过controllerNamespace进行指定
    • 另一种是组件里的,通过组件的“加载”进行指定

Yii的版本化,说白了就是通过路由,把URL定位到对应的方法去。

我们这里用Yii的基础版(basic)作为讲解模板吧。

路由机制

路由机制的工作过程,简单来说就是:

  • 当客户端(比如浏览器)发起请求时,先通过URL定位文件,然后把请求送达这个文件进行处理和响应。
  • 若无法通过URL直接定位到文件,则通过index.php来接收请求(这里可能需要配置一下你的web服务器)。

  • index.php接收到请求后,先送达路由管理器,通过路由解析出URL对应的方法,然后送达这个方法,由方法受理请求并作出响应。

  • 当无法定位到文件也无法解析出方法时,一般来说做404错误处理,表示资源不存在。

如何定位

在框架中,除了静态资源是直接定位文件,其他的请求都是路由到某个方法进行处理。Yii是一个面向对象的框架,路由表通过命名空间来一步一步的解析class、action,确定处理请求的方法。比如,在基础版中,请求URL<域名>/index.php?r=site/index,定位到SiteControlleractionIndex方法。

那么路由表是怎么知道,URL里的site指的就是SiteController呢?继续看:

控制器命名空间 - controllerNamespace

Yii的配置文件里,有一项很重要的配置是controllerNamespace,顾名思义就是控制器的命名空间。在基础版里,它大概是这么配置的:'controllerNamespace' => 'app\controllers',根据这个命名空间,路由就能找到控制器的目录,然后就能定位到控制器和方法了。当然,你看不到它,因为这是核心框架的默认配置。如果你想要验证我的说法,那么:

vendor\yiisoft\yii2\base\Application.php line 95

/**
 * @var string the namespace that controller classes are located in.
 * This namespace will be used to load controller classes by prepending it to the controller class name.
 * The default namespace is `app\controllers`.
 *
 * Please refer to the [guide about class autoloading](guide:concept-autoloading.md) for more details.
 */
public $controllerNamespace = 'app\\controllers';

当你请求URL<域名>?r=site/index时,路由会去寻找app\controllers\SiteController这个类(其实就是去应用根目录下的controllers里寻找SiteController.php文件),然后找到里面的actionIndex方法。

凭什么site就对应SiteController类,index就对应actionIndex方法?它也是默认的配置!不过那就是另一件话题了。

模块 - modules

你使用过Yii自带的debug组件吗?如果没有,那你应该知道,当启用了这个组件,你就有两种方式可以使用它:一是在页面的右下角,会有一个Yii的小logo,展开它就是debug组件;二是通过<域名>/index.php?r=debug/default/index,直接打开debug页面。

yii-debug组件必然是有处理请求的方法的,可是为啥上面这个URL可以准确定位到方法呢,controllerNamespace里没有配置过它呀?

其实yii-debug是一个组件(module),每一个组件都由控制器、模型、视图等构成,是一个独立的小应用。对于这样的组件,我们要在$config['modules']里配置,然后就能挂载它,你就可以正常使用了。也正是这个“挂载”的过程,框架寻找到了对应的命名空间,就可以准确的找到控制器和方法了。

1547022485527.png

我们来找找这个组件吧:vendor\yiisoft\yii2-debug,会找到文件Module.php

<?php
namespace yii\debug;
//use ...
class Module extends \yii\base\Module implements BootstrapInterface
{
    //...
}

它继承了\yii\base\Module类,这是一个模块类,你只需要知道,继承模块类的文件在对应的目录时,会被自动加载。

模块和版本化

组件的“挂载”大致就是这样。可是这和版本化有什么关系?关系可大了,我们的版本化,就是依靠组件实现的。

先来梳理一下:

  • 版本化需要路由支持,这样才能从URL中解析并定位到方法;
  • 定位方法需要先定位到控制器;
  • 控制器有两种:
    • 一种是默认的,通过controllerNamespace进行指定
    • 另一种是组件里的,通过组件的“加载”进行指定

动手做

我们在上面看到,yii-debug组件是在配置项的$config['modules']里多加了一个debug组件,并且指明了'class' => 'yii\debug\Module'

仍然是拿Yii基础版来,做个简单的“版本化”:我现在打算增加一个version1应用,算是加了一个“版本1”吧。

编写配置

首先在配置文件web.php里:

$config = [
    //略...
    'modules' => [
        //这里class指定的是模块类,看下文
        'version1' => ['class' => 'app\version1\Version1'],
    ],
];

编写模块

上面配置里的class可不是乱写的哦!是有依据的。

在应用根目录下新建文件夹version1vendor同一级,兄弟文件夹),在文件夹内新建文件Version1.php作为一个模块类,继承\yii\base\Module。在这个类里面还指定了$controllerNamespace,注意跟上文提到的不一样:上文指定的是整个应用的,这里指定的是组件自己的:

<?php
namespace app\version1;

class Version1 extends \yii\base\Module
{
    //这里指定的是组件自己的控制器命名空间
    public $controllerNamespace = 'app\version1\controllers';

    public function init()
    {
        parent::init();
    }
}

接下来在version1文件夹里继续新建三个子文件夹:

  • controllers:控制器文件夹。里面的控制器文件,命名空间要写成namespace app\version1\controllers;
  • models:模型文件夹。里面的模型文件,命名空间要写成namespace app\version1\models;
  • views:视图文件夹

你只要像正常的那样在这三个文件夹里写你的代码就可以了。

编写路由

最后,去配置一下路由:

'urlManager' => [
    'enablePrettyUrl' => true,
    'enableStrictParsing' => true,
    'showScriptName' => false,
    'rules' => [
        'version1/<controller:[\w-]+>/<action:[\w-]+>'
            => 'version1/<controller>/<action>', //version1路由
        '<controller:[\w-]+>/<action:[\w-]+>'
            => '<controller>/<action>', //原有应用的路由(比如原本URL:<域名>/index.php?r=site/index,现在URL:<域名>/site/index)
        //其他略...
    ],
],

这样,访问URL<域名>/version1/site/index的时候,就路由到version1SiteControlleractionIndex方法进行处理。

结语

语言组织的不够好见谅!

API的版本化和上面的也没什么太大的区别,你可以试着把API做个版本化;还可以试着把Yii基础版配置成Yii高级版的样子,这样可以加深理解。

转载于:https://www.cnblogs.com/alanabc/p/10246023.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值