Appearance
概述
EBAOZU 系统基于 ThinkPHP 8.0 框架的中间件机制,提供请求预处理、响应后处理、权限校验、日志记录、跨域处理等拦截功能。本文档详细说明系统中各个中间件的作用、配置方式及二次开发规范。
中间件架构与分类
app/http/middleware/
├── AllowOriginMiddleware.php # 全局跨域处理中间件
├── BlockerMiddleware.php # 接口防刷 / 防重复提交中间件
├── InstallMiddleware.php # 系统安装检测中间件
├── StationOpenMiddleware.php # 站点开关检测中间件
├── SystemLogMiddleware.php # 业务操作日志记录中间件
├── admin/ # 平台后台专属中间件
│ ├── AdminAuthTokenMiddleware.php # 后台管理员 Token 校验
│ └── AdminCkeckRoleMiddleware.php # 后台 RBAC 权限校验
├── api/ # 移动端/API 专属中间件
│ ├── AuthTokenMiddleware.php # 用户 Token 校验(支持可选登录模式)
│ └── ClientMiddleware.php # 客户端环境检测
├── store/ # 门店后台专属中间件
│ ├── AuthTokenMiddleware.php # 门店管理员 Token 校验
│ └── StoreCkeckRoleMiddleware.php # 门店权限校验
└── supplier/ # 供应商后台专属中间件
├── AuthTokenMiddleware.php # 供应商 Token 校验
└── SupplierCkeckRoleMiddleware.php # 供应商权限校验常用核心中间件说明
全局跨域中间件 (AllowOriginMiddleware)
负责处理 HTTP OPTIONS 预检请求并注入 CORS 响应头,通常配置在全局中间件 app/middleware.php 中。
php
namespace app\http\middleware;
use app\Request;
use think\Response;
class AllowOriginMiddleware
{
public function handle(Request $request, \Closure $next)
{
if ($request->isOptions()) {
return response()->code(204)->header([
'Access-Control-Allow-Origin' => '*',
'Access-Control-Allow-Headers' => 'Authori-zation, Content-Type, If-Match, If-Modified-Since, If-None-Match, If-Unmodified-Since, X-Requested-With, Form-type',
'Access-Control-Allow-Methods' => 'GET, POST, PATCH, PUT, DELETE, OPTIONS',
'Access-Control-Allow-Credentials' => 'true'
]);
}
/** @var Response $response */
$response = $next($request);
$response->header([
'Access-Control-Allow-Origin' => '*',
'Access-Control-Allow-Credentials' => 'true'
]);
return $response;
}
}用户鉴权中间件 (api\AuthTokenMiddleware)
用于移动端和 API 接口鉴权,支持通过参数控制强制登录或可选登录:
php
// route/api.php 示例
// 1. 必须登录接口(强制登录)
Route::group(function () {
Route::get('user/info', 'v1.user.User/info');
})->middleware(\app\http\middleware\api\AuthTokenMiddleware::class, true);
// 2. 可选登录接口(未登录也能访问,但获取游客态数据)
Route::group(function () {
Route::get('product/detail/:id', 'v1.product.StoreProduct/detail');
})->middleware(\app\http\middleware\api\AuthTokenMiddleware::class, false);中间件在验证成功后会将用户信息和 UID 注入到 $request 对象中:
php
// 控制器中直接获取:
$uid = $request->uid();
$userInfo = $request->user();后台鉴权与权限中间件 (admin)
平台后台路由通常组合使用 AdminAuthTokenMiddleware 和 AdminCkeckRoleMiddleware:
php
Route::group('adminapi', function () {
// 业务路由
})->middleware([
\app\http\middleware\admin\AdminAuthTokenMiddleware::class,
\app\http\middleware\admin\AdminCkeckRoleMiddleware::class
]);- AdminAuthTokenMiddleware:校验请求头中的 Token 并注入
$request->adminId与$request->adminInfo。 - AdminCkeckRoleMiddleware:根据管理员的角色规则(
eb_system_role),匹配当前访问的 API URL 与请求方法,无权限则直接抛出AuthException。
接口防刷中间件 (BlockerMiddleware)
利用 Redis 分布式锁,基于用户 UID 或请求特征防止高频重复提交(如重复下单、重复领券)。
自定义中间件开发
第一步:创建中间件类
在 app/http/middleware/ 目录下创建新类:
php
<?php
namespace app\http\middleware;
use app\Request;
use think\Response;
class CustomCheckMiddleware
{
public function handle(Request $request, \Closure $next, ...$args)
{
// 1. 请求前置检查
if (!$request->has('app_version')) {
return app('json')->fail('缺少应用版本号');
}
// 2. 继续执行后续逻辑
$response = $next($request);
// 3. 响应后置处理(如添加自定义 Header)
$response->header(['X-Custom-Time' => (string)time()]);
return $response;
}
}第二步:注册到路由
在对应的路由定义文件中绑定:
php
Route::get('custom/action', 'v1.custom.Custom/action')
->middleware(\app\http\middleware\CustomCheckMiddleware::class);注意事项
- 执行顺序:中间件按照配置的数组顺序依次执行前置处理,返回响应时按逆序执行后置处理。
- 异常处理:中间件中抛出
\app\exceptions\AuthException或\think\exception\ValidateException会由系统全局ExceptionHandle统一捕获转为标准 JSON 输出。 - 控制器注入:中间件中注入到
$request的属性必须在控制器生命周期内按标准 API 读取,避免在各层之间传递非标准上下文。