天天看点

ThinkPHP 5.0 中的控制器

简介

ThinkPHP 5.0 的控制器定义比较灵活,可以无需继承任何的基础类,也可以继承官方封装的 \think\Controller 类或者其他的控制器类。

一个典型的控制器类定义如下:

<?php
namespace app\index\controller;

class Blog
{
    public function index()
    {
        return view('index');
    }
}
           

控制器类文件的实际位置是 application\index\controller\Blog.php。

控制器类可以无需继承任何类,命名空间默认以 app 为根命名空间。

默认情况下,控制器的输出全部采用 return 的方式,无需进行任何的手动输出,系统会自动完成渲染内容的输出。

ThinkPHP 5.0 中,控制器主要分为以下几种:

  • 访问控制器(主控制器)
  • 空控制器
  • 多级控制器
  • 分层控制器
  • Rest 控制器
  • 资源控制器

访问控制器

可通过 URL 直接访问的控制器就是访问控制器(Controller)或者主控制器,访问控制器是由 \think\App 类负责调用和实例化的,无需手动实例化。

URL 解析和路由后,会把当前的 URL 地址解析到 [ 模块/控制器/操作 ],其实也就是执行某个控制器类的某个操作方法。

上面的一段代码,就是一个访问控制器的例子。可访问的 URL 为:http://serverName/index/blog/index

空控制器

空控制器是指当系统找不到指定的控制器名称的时候,系统会尝试定位到空控制器(Error),利用这个机制可以用来定制错误页面和URL优化。

默认的空控制器的名称为 Error。

我们给项目定义一个Error控制器类。

<?php
namespace app\index\controller;
use think\Request;

class Error
{
    public function index(Request $request)
    {
       $controllerName =  $request->controller();
       return $controllerName.'不存在';
    }
}
           

多级控制器

多级控制器是指在application\index\controller目录中,创建子目录,用于存放控制器类文件。

ThinkPHP5.0 支持任意层次级别的控制器,并且支持路由。例如:

<?php
namespace app\index\controller\api;

class Blog
{
    public function index()
    {
        return view('index');
    }
}
           

该控制器类的文件位置为:application/index/controller/api/Blog.php。

可访问的URL为:http://serverName/index.php/index/api.blog/index

修改配置文件,设置controller_auto_search参数开启自动定位控制器,便于URL访问。

'controller_auto_search' => true,
           

之后,就可以使用这个URL地址:http://serverName/index.php/index/api/blog/index

分层控制器

分层控制器是对外隔离的,不能被URL直接访问,只能在访问控制器、模型类的内部,或者视图模板文件中进行调用。

分层控制器的目录和访问控制器的目录平级。

分层控制器可用于实现逻辑层控制器,给访问控制器调用;或者用于实现widget(挂件)功能,给视图模板调用,如更改网站皮肤、显示菜单、面包屑、公共头中的信息、广告位等等。

逻辑控制器

利用分层控制器的机制,我们定义Blog逻辑控制器。

<?php
namespace app\index\logic;

class Blog 
{
    public function insert($data)
    {
        // 逻辑层代码
        return true;
    }
}
           

在访问控制器或模型类中的调用方式如下:

$logic = \think\Loader::controller('Blog', 'logic');
$logic->insert($data);
           

$logic = controller('Blog', 'logic');
$logic->insert($data);
           

action('Blog/insert', ['data' => $data], 'logic');
           

支持跨模块调用,例如:

$logic = controller('Admin/Blog', 'logic');
$logic->insert($data);
           

widget 挂件控制器

利用分层控制器的机制,我们定义widget挂件控制器。

<?php
namespace app\index\widget;

class User
{
    public function info()
    {
        $user_id = session('user.id');    // 获取用户的id
        $userinfo = db('user')->where('id', $user_id)->find();
        return view("widget/info", ['userinfo' => $userinfo])->getContent();
    }
}
           

在模板中的调用方式如下:

{:action('User/info', '', 'widget')}
           

{:widget('User/info')}
           

Rest 控制器

如果需要让你的控制器支持 RESTful 的话,可以使用 Rest 控制器,在定义访问控制器的时候直接继承 think\controller\Rest 即可。

新版不再推荐使用 Rest 控制器,建议用资源控制器替代。下一个大版本即将废弃 Rest 控制器。

配合示例需要,首先在应用配置文件中添加:

// URL伪静态后缀
'url_html_suffix'   => 'html|xml|json|jsonp',
           

RESTFul方法和标准模式的操作方法定义主要区别在于,需要对请求类型和资源类型进行判断,大多数情况下,通过路由定义可以把操作方法绑定到某个请求类型和资源类型。如果你没有定义路由的话,需要自己在操作方法里面添加判断代码,示例:

<?php
namespace app\index\controller;
use think\controller\Rest;

class Blog extends Rest
{
    public function index()
    {
        switch ($this->method){
            case 'get': // get请求处理代码
                if ($this->type == 'json'){
                    
                }elseif ($this->type == 'xml'){
                    
                }
                break;         
                
            case 'post': // post请求处理代码
                break;
                
            case 'put': // put请求处理代码
                break;
            
            default:
                break;
        }
    }
}
           

在Rest操作方法中,可以使用$this->type获取当前访问的资源类型,用$this->method获取当前的请求类型。

RESTFul 输出,有以下三种方式:

使用Rest类提供的 response 方法,进行输出:

$this->response($data, 'json', );
           

使用think\Response类中的方法,进行输出:

Response::create($data, 'json')->code();
           

使用助手函数,进行输出:

资源控制器

资源控制器可以轻松的创建 RESTFul 资源控制器,可以通过命令行创建资源控制器。

// 生成 index 模块的 Blog 资源控制器
php think make:controller index/Blog
           

或者使用完整的命名空间生成。

php think make:controller app\index\controller\Blog
           

为资源控制器注册一个资源路由。

Route::resource('blog','index/Blog');
           

设置后会自动注册 7 个路由规则,如下:

请求类型 路由规则 对应的方法 说明
GET blog index 文章列表页(首页)
GET blog/create create 创建新文章的界面
POST blog save 执行创建新文章
GET blog/:id read 查看指定的文章
GET blog/:id/edit edit 更新文章的界面
PUT blog/:id update 执行更新文章
DELETE blog/:id delete 执行删除文章

推荐使用资源控制器,来进行增、删、改、查的操作。