1, 'message' => '订单ID必须是正整数'], // 用户姓名验证 ['user_name', 'string', 'max' => 64, 'message' => '收货人姓名长度不能超过64字符'], ['user_name', 'trim'], ['user_name', 'filter', 'filter' => function($value) { return strip_tags($value); // 过滤HTML标签 }], ['user_name', 'match', 'pattern' => '/^[\x{4e00}-\x{9fa5}a-zA-Z0-9\s]{1,64}$/u', 'message' => '收货人姓名只能包含中文、英文和数字'], // 用户电话验证 ['user_phone', 'string'], ['user_phone', 'match', 'pattern' => '/^(1[3-9]\d{9}|^0\d{2,3}\d{7,8})$/', 'message' => '手机号或固话格式不正确'], // 经纬度验证 ['user_lng', 'number', 'min' => -180, 'max' => 180, 'message' => '经度范围必须在-180到180之间'], ['user_lat', 'number', 'min' => -90, 'max' => 90, 'message' => '纬度范围必须在-90到90之间'], // 用户地址验证 ['user_address', 'string', 'max' => 512, 'message' => '收货地址长度不能超过512字符'], ['user_address', 'trim'], ['user_address', 'filter', 'filter' => function($value) { return strip_tags($value); // 过滤HTML标签 }], // 货物重量验证(单位:克) ['weight', 'number', 'min' => 0.1, 'max' => 30, 'message' => '货物重量必须在0.1-30千克之间'], // 货物价格验证(单位:分) ['price', 'number', 'min' => 0, 'max' => 1000000, 'message' => '货物价格必须在0-100万元之间'], // 包裹数量验证 ['packageNum', 'integer', 'min' => 1, 'max' => 10000, 'message' => '包裹数量必须在1-10000之间'], // 自定义验证规则 ['user_lng', 'validateCoordinates'], ['weight', 'validateWeight'], ['price', 'validatePrice'], ['cargo', 'validateCargo'], ]; } /** * @inheritdoc */ public function attributeLabels() { return [ 'wx_store_id' => '微信门店ID', 'use_sandbox' => '是否使用沙盒环境', 'cargo' => '货物信息', 'orderId' => '订单ID', 'user_name' => '收货人姓名', 'user_phone' => '收货人电话', 'user_lng' => '收货人经度', 'user_lat' => '收货人纬度', 'user_address' => '收货人地址', 'weight' => '货物重量', 'price' => '货物价格', 'packageNum' => '包裹数量', ]; } /** * 自定义验证:验证经纬度是否在合理范围内 */ public function validateCoordinates($attribute, $params) { if (!empty($this->user_lng) && !empty($this->user_lat)) { // 验证是否为中国境内坐标(粗略验证) $lng = floatval($this->user_lng); $lat = floatval($this->user_lat); // 中国境内经纬度大致范围:经度 73°-135°,纬度 18°-54° if ($lng < 73 || $lng > 135 || $lat < 18 || $lat > 54) { $this->addError($attribute, '坐标位置似乎不在服务范围内'); } } } /** * 自定义验证:验证货物重量限制 */ public function validateWeight($attribute, $params) { if (!empty($this->weight)) { $weight = floatval($this->weight); // 一般同城配送重量限制(例如:不超过30公斤) if ($weight > 30) { // 30公斤 $this->addError($attribute, '货物重量不能超过30公斤'); } } } /** * 自定义验证:验证货物价格合理性 */ public function validatePrice($attribute, $params) { if (!empty($this->price)) { $price = intval($this->price); // 货物价格上限验证(例如:不超过100万) if ($price > 1000000) { $this->addError($attribute, '货物价值过高,请联系客服'); } } } public function validateCargo($attribute, $params) { // 验证货物信息是否为数组且包含必要字段 if (empty($this->cargo) || !is_array($this->cargo)) { $this->addError($attribute, '货物信息必须是数组格式'); return; } // 检查必要字段是否存在 $requiredFields = ['cargo_name', 'cargo_weight', 'cargo_price', 'cargo_type', 'cargo_num']; $missingFields = []; foreach ($requiredFields as $field) { if (!isset($this->cargo[$field]) || empty($this->cargo[$field])) { $missingFields[] = $field; } } if (!empty($missingFields)) { $this->addError($attribute, '货物信息缺少必要字段:' . implode('、', $missingFields)); return; } // 验证货物重量 $weight = floatval($this->cargo['cargo_weight']); if ($weight <= 0 || $weight > 30000) { $this->addError($attribute, '货物重量必须在1-30000克之间'); } // 验证货物价格 $price = intval($this->cargo['cargo_price']); if ($price < 0 || $price > 1000000000) { $this->addError($attribute, '货物价格必须在0-100万元之间'); } // 验证货物数量 $num = intval($this->cargo['cargo_num']); if ($num <= 0 || $num > 1000) { $this->addError($attribute, '货物数量必须在1-1000之间'); } // 验证货物名称 $name = trim($this->cargo['cargo_name']); if (mb_strlen($name, 'UTF-8') > 100) { $this->addError($attribute, '货物名称长度不能超过100个字符'); } } /** * 场景定义 -- 不同场景下,需要验证的字段不同 * 1. store_fee 查询运费场景 * 2. query_fee 查询运费场景 */ public function scenarios() { $scenarios = parent::scenarios(); // 查询运费场景 $scenarios['store_fee'] = [ 'orderId', 'user_name', 'user_phone', 'user_lng', 'user_lat', 'user_address', 'weight', 'price', 'packageNum' ]; // 查询运费场景 $scenarios['query_fee'] = [ 'wx_store_id', 'user_name', 'user_phone', 'user_lng', 'user_lat', 'user_address', 'cargo', 'use_sandbox' ]; return $scenarios; } /** * 在验证前执行额外的自定义验证 */ // public function beforeValidate() // { // if (parent::beforeValidate()) { // return true; // } // return false; // } /** * 在验证后执行额外的自定义验证 */ // public function afterValidate() // { // // 添加自定义验证规则 // $this->validateCoordinates('user_lng', []); // $this->validateWeight('weight', []); // $this->validatePrice('price', []); // parent::afterValidate(); // } }