🔥码云GVP开源项目 12k star Uniapp+ElementUI 功能强大 支持多语言、二开方便! 广告
## 响应处理器 响应处理器可以格式化响应输出结构,规范请求输出。 目录 `app\Responses` . 示例: ```php /** * 商品详情响应结构 */ namespace App\Responses\Goods; use App\Responses\Response; class GoodsShowResponse extends Response { public function messages() { return [ 'id' => [ 'integer', 'required' => true, 'default' => 0, 'demo' => 1, 'min' => 0, 'max' => 200, 'label' => '商品id', 'callback' => null,], 'type' => [ 'integer', 'required' => true, 'default' => 0, 'demo' => 1, 'min' => 0, 'max' => 200, 'label' => '商品类型:0虚拟,1实物', 'callback' => null,], 'cateid' => [ 'integer', 'required' => true, 'default' => 0, 'demo' => 1, 'min' => 0, 'max' => 200, 'label' => '分类id', 'callback' => null,], 'title' => [ 'string', 'required' => true, 'default' => '', 'demo' => 1, 'min' => 0, 'max' => 64, 'label' => '标题', 'callback' => null,], 'atitle' => [ 'string', 'required' => true, 'default' => '', 'demo' => 1, 'min' => 0, 'max' => 64, 'label' => '副标题', 'callback' => null,], 'sale' => [ 'integer', 'required' => true, 'default' => 0, 'demo' => 400, 'min' => 100, 'max' => 1000, 'label' => '销售数量', 'callback' => null,], 'months' => [ 'integer', 'required' => true, 'default' => 0, 'demo' => 49, 'min' => 1, 'max' => 64, 'label' => '时长', 'callback' => null,], 'price' => [ 'string', 'required' => true, 'default' => 0, 'demo' => 49, 'min' => 1, 'max' => 64, 'label' => '市场价格', 'callback' => null,], 'mprice' => [ 'string', 'required' => true, 'default' => 0, 'demo' => 0, 'min' => 0, 'max' => 10, 'label' => '市场价格', 'callback' => null,], 'tprice' => [ 'string', 'required' => true, 'default' => 0, 'demo' => 0, 'min' => 0, 'max' => 10, 'label' => '平均价格', 'callback' => null,], 'pinprice' => [ 'string', 'required' => true, 'default' => 0, 'demo' => 0, 'min' => 0, 'max' => 10, 'label' => '拼团价格', 'callback' => null,], 'ispin' => [ 'integer', 'required' => true, 'default' => 0, 'demo' => 0, 'min' => 0, 'max' => 10, 'label' => '是不是拼团', 'callback' => null,], 'ismsg' => [ 'integer', 'required' => true, 'default' => 0, 'demo' => 0, 'min' => 0, 'max' => 10, 'label' => '是否发短信', 'callback' => null,], 'state' => [ 'integer', 'required' => true, 'default' => 0, 'demo' => 0, 'min' => 0, 'max' => 10, 'label' => '状态 1正常 0下架', 'callback' => null,], 'sort' => [ 'integer', 'required' => true, 'default' => 0, 'demo' => 0, 'min' => 0, 'max' => 10, 'label' => '商品排序', 'callback' => null,], 'onpic' => [ 'string', 'required' => true, 'default' => '', 'demo' => '', 'min' => 0, 'max' => 10, 'label' => '商品封面', 'callback' => null,], 'ronpic' => [ 'string', 'required' => true, 'default' => '', 'demo' => '', 'min' => 0, 'max' => 10, 'label' => '首页推荐图片', 'callback' => null,], 'bgpic' => [ 'string', 'required' => true, 'default' => '', 'demo' => '', 'min' => 0, 'max' => 10, 'label' => '背景图', 'callback' => null,], 'vurl' => [ 'string', 'required' => true, 'default' => '', 'demo' => '', 'min' => 0, 'max' => 10, 'label' => '视频地址', 'callback' => null,], 'tdata' => [ 'string', 'required' => true, 'default' => '', 'demo' => '', 'min' => 0, 'max' => 10, 'label' => 'HTML介绍', 'callback' => null,], 'intro' => [ 'string', 'required' => true, 'default' => '', 'demo' => '', 'min' => 0, 'max' => 10, 'label' => '商品简介', 'callback' => null,], 'btime' => [ 'string', 'required' => true, 'default' => '', 'demo' => '', 'min' => 0, 'max' => 10, 'label' => '售卖开始时间', 'callback' => null,], 'etime' => [ 'string', 'required' => true, 'default' => '', 'demo' => '', 'min' => 0, 'max' => 10, 'label' => '售卖结束时间', 'callback' => null,], 'utime' => [ 'integer', 'required' => true, 'default' => 0, 'demo' => 0, 'min' => 0, 'max' => 10, 'label' => '更新时间', 'callback' => null,], 'ctime' => [ 'integer', 'required' => true, 'default' => 0, 'demo' => 0, 'min' => 0, 'max' => 10, 'label' => '添加时间', 'callback' => null,], ]; } } ``` 核心代码: ```php /** * Created by PhpStorm. * User: wll * Date: 2019-05-09 * Time: 10:39 */ namespace App\Fend\Http; class FormResponse { /** * 原始响应数据 * * @var array */ protected $rawBody = []; /** * 响应数据 * * @var array */ protected $body = []; /** * 接口返回字段说明 * * @return array */ public function messages(){ return [ 'name' => [ 'string', // 类型:string, integer, array, object 'required' => true, // 是否一定会返回 'default' => '', // 默认值 'demo' => 'wll', // 示例值,自动生成时填写: ?? (双问号) 'min' => 0, // 最大 [生成demo数据时可能用上] 'max' => 10, // 最小 [生成demo数据时可能用上] 'label' => '姓名', // 标签 'callback' => null, // 回调函数 ], 'age' => [ 'integer', // 类型:string, integer, array, object 'required' => true, // 是否一定会返回 'default' => '', // 默认值 'demo' => 12, // 示例值,自动生成时填写: ?? (双问号) 'min' => 0, // 最大 [生成demo数据时可能用上] 'max' => 200, // 最小 [生成demo数据时可能用上] 'label' => '年龄', // 标签 'callback' => null, // 回调函数 ], 'avatar' => [ 'string', // 类型:string, integer, array, object 'required' => true, // 是否一定会返回 'default' => 'images/user/default.jpg', // 默认值 'demo' => 'images/user/abc.jpg', // 示例值,自动生成时填写: ?? (双问号) 'min' => 0, // 最大 [生成demo数据时可能用上] 'max' => 50, // 最小 [生成demo数据时可能用上] 'label' => '姓名', // 标签 'callback' => function($val){ return 'https://img.txbapp.cn/'.$val; }, // 回调函数 ], 'wll' => [ 'object', 'required' => true, // 是否一定会返回 'default' => '', // 默认值 'demo' => 'wanglele', // 示例值,自动生成时填写: ?? (双问号) 'min' => 0, // 最大 [生成demo数据时可能用上] 'max' => 50, // 最小 [生成demo数据时可能用上] 'label' => '望乐乐', // 标签 'callback' => null, ], 'wll.name' => [ 'string', // 类型:string, integer, array, object 'required' => true, // 是否一定会返回 'default' => '', // 默认值 'demo' => 'wll', // 示例值,自动生成时填写: ?? (双问号) 'min' => 0, // 最大 [生成demo数据时可能用上] 'max' => 10, // 最小 [生成demo数据时可能用上] 'label' => 'w姓名', // 标签 'callback' => null, // 回调函数 ], 'wll.age' => [ 'integer', // 类型:string, integer, array, object 'required' => true, // 是否一定会返回 'default' => '', // 默认值 'demo' => 88, // 示例值,自动生成时填写: ?? (双问号) 'min' => 0, // 最大 [生成demo数据时可能用上] 'max' => 200, // 最小 [生成demo数据时可能用上] 'label' => 'w年龄', // 标签 'callback' => null, // 回调函数 ], 'wll.length' => [ 'object', 'required' => true, // 是否一定会返回 'default' => 'images/user/default.jpg', // 默认值 'demo' => 'images/user/abc.jpg', // 示例值,自动生成时填写: ?? (双问号) 'min' => 0, // 最大 [生成demo数据时可能用上] 'max' => 50, // 最小 [生成demo数据时可能用上] 'label' => 'w长度', // 标签 'callback' => null, ], 'wll.length.min' => [ 'integer', 'required' => true, // 是否一定会返回 'default' => '', // 默认值 'demo' => 12, // 示例值,自动生成时填写: ?? (双问号) 'min' => 0, // 最大 [生成demo数据时可能用上] 'max' => 200, // 最小 [生成demo数据时可能用上] 'label' => 'w最小长度', // 标签 'callback' => null, // 回调函数 ], 'wll.length.max' => [ 'integer', 'required' => true, // 是否一定会返回 'default' => '', // 默认值 'demo' => 12, // 示例值,自动生成时填写: ?? (双问号) 'min' => 0, // 最大 [生成demo数据时可能用上] 'max' => 200, // 最小 [生成demo数据时可能用上] 'label' => 'w最大长度', // 标签 'callback' => null, // 回调函数 ], ]; } /** * 响应提示 * * @return string */ public function notes() { return ''; } /** * 设置响应数据 * * @param $body */ public function setRawBody( $body ) { $this->rawBody = (array)$body; } /** * 获取响应数据 * * @return array */ public function getBody() { return $this->body; } /** * 格式化响应数据 * * @param array $body * @return array * @throws \Fend_Exception */ public function format($body = []) { if( !empty($body) ){ $this->setRawBody($body); } return $this->body = $this->cFormatData($this->getStructure(), $this->rawBody); } /** * 生成格式化数据 * * @param $message * @param $rawBody * @return array * @throws \Fend_Exception */ protected function cFormatData($message, $rawBody) { if( empty($message) ){ return []; } $data = []; // 遍历结构体生成数据 foreach($message as $key => $val) { // 如果值不存在,也不是必须的则不用列出key if( !isset($rawBody[$key]) && $val['required'] === false){ continue; } // 当响应结构没有值时,用默认值补全 if(!isset($rawBody[$key])){ $rawBody[$key] = $val['default']; } switch (strtolower($val[0])){ case 'string': $data[$key] = $this->rValue($val['callback'], strval(getValue($rawBody, $key, $val['default']))); break; case 'integer': $data[$key] = $this->rValue($val['callback'], getValue($rawBody, $key, $val['default']) + 0); break; case 'array': $tArr = []; // 数组的话遍历数据格式化 foreach($rawBody[$key] as $v) { $tArr[] = $this->cFormatData($val['item'], $v); } $data[$key] = $tArr; break; case 'object': $data[$key] = $this->cFormatData($val['item'], $rawBody[$key]); break; default: break; } } return $data; } /** * 获取 demo 数据 */ public function demo() { return $this->cDemoData($this->getStructure()); } /** * 生成演示数据 * * @param $message * @return array */ protected function cDemoData($message) { if( empty($message) ){ return []; } $data = []; // 遍历结构体生成数据 foreach($message as $key => $val) { switch (strtolower($val[0])){ case 'string': $value = strval($val['demo'] != '??' ? $val['demo'] : $this->cStringValue($val['default'], $val['min'], $val['max'])); $data[$key] = $this->rValue($val['callback'], $value); break; case 'integer': $value = ($val['demo'] != '??' ? $val['demo'] : $this->cIntegerValue($val['default'], $val['min'], $val['max'])) + 0; $data[$key] = $this->rValue($val['callback'], $value); break; case 'array': $data[$key] = $this->cArrayValue($this->cDemoData($val['item']), $val['min'], $val['max']); break; case 'object': $data[$key] = $this->cDemoData($val['item']); break; default: break; } } return $data; } /** * 生成随机字符串 * * @param $val * @param $min * @param $max * @return string */ protected function cStringValue($val, $min, $max) { return rand_str(rand($min, $max)); } /** * 生成随机数字 * * @param $val * @param $min * @param $max * @return int */ protected function cIntegerValue($val, $min, $max) { return rand($min, $max); } /** * 填充数据 * * @param $val * @param $min * @param $max * @return array */ protected function cArrayValue($val, $min, $max) { return array_fill(0, $max, $val); } /** * 执行回调 * * @param $callback * @param $value * @return mixed */ protected function rValue($callback, $value) { if(is_string($callback)){ switch (strtolower($callback)){ case 'image': return \Misc_Image::Factory()->getUrl($value); break; case 'video': return \Misc_Image::Factory()->getvideo($value); break; case 'json': return json_decode($value, true); break; } } if(! is_callable($callback) ){ return $value; } return $callback($value); } /** * 获取参数结构 */ protected function getStructure() { $messages = $this->messages(); if(empty($messages)){ return []; } // 预定义处理之后的规则 $sMessages = []; // 排序 ksort($messages); foreach($messages as $key => $item){ if(strpos($key, '.') < 1){ $sMessages[$key] = $item; }else{ // 过滤处理 key $keyArr = array_filter(explode('.', $key), function($val){ return $val != '*'; }); // 多维数组赋值 data_set($sMessages, implode('.item.', $keyArr), $item); } } return $sMessages; } } ```