如何自定义Laravel 9中Lighthouse GraphQL的响应格式?
自定义Laravel Lighthouse GraphQL响应格式方案
要实现包含status、code、message、data字段的响应格式,同时保留GraphQL字段选择的功能,推荐使用Lighthouse的响应中间件来处理,具体步骤如下:
1. 创建响应格式化中间件
在app/Http/Middleware目录下新建FormatGraphQLResponse.php文件,代码如下:
<?php namespace App\Http\Middleware; use Closure; use Illuminate\Http\Request; use Symfony\Component\HttpFoundation\Response; class FormatGraphQLResponse { public function handle(Request $request, Closure $next): Response { $response = $next($request); // 解析原始GraphQL响应内容 $content = json_decode($response->getContent(), true); if (json_last_error() !== JSON_ERROR_NONE) { return $response; } // 初始化格式化响应结构 $formatted = [ 'status' => true, 'code' => 200, 'message' => '', 'data' => [] ]; // 处理成功响应:提取GraphQL返回的操作数据 if (isset($content['data'])) { // 取data中第一个操作的结果(适配单查询/变更场景) $operationData = reset($content['data']); $formatted['data'] = $operationData ?? []; } // 处理错误响应:提取错误信息和错误码 if (isset($content['errors'])) { $formatted['status'] = false; // 优先取Lighthouse扩展字段中的错误码,默认500 $formatted['code'] = $content['errors'][0]['extensions']['code'] ?? 500; $formatted['message'] = $content['errors'][0]['message'] ?? '服务器内部错误'; $formatted['data'] = []; } // 更新响应内容为格式化后的结构 $response->setContent(json_encode($formatted)); return $response; } }
2. 注册中间件到Lighthouse配置
打开config/lighthouse.php配置文件,找到middleware数组,添加刚才创建的中间件:
'middleware' => [ // 保留原有中间件 \App\Http\Middleware\FormatGraphQLResponse::class, ],
原理说明
这种方式的核心是在Lighthouse完成GraphQL字段解析之后再修改响应格式:
- Lighthouse会根据请求中的字段选择规则,自动过滤模型字段,只返回请求指定的内容
- 中间件仅对响应结构进行包装,不会破坏Lighthouse原有的字段解析逻辑,避免返回模型全部字段的问题
效果验证
使用你提供的查询请求:
query Translations { translations { name slug } }
将得到期望的响应格式:
{ "status": true, "code": 200, "message": "", "data": [ { "name": "English", "slug": "en_US" }, { "name": "English (United Kingdom)", "slug": "en_UK" } ] }
内容的提问来源于stack exchange,提问作者Niraj Pathak
相关产品推荐
相关产品推荐

