
嵌套数组字段名必须用方括号语法,否则 Laravel 不识别
Laravel 的 request() 和验证器默认只解析一层键名,比如 name 或 email;一旦你提交的是用户地址列表、多个文件、商品规格等嵌套结构,字段名就得写成 addresses[0][city]、files[1] 这种格式。浏览器表单原生支持这种命名,Laravel 也能自动展开成 PHP 多维数组。
常见错误现象:request(‘addresses’) 返回 null 或空数组,但 request()->all() 里明明能看到带方括号的键名——这是因为没按约定写字段名,或者前端用了 JSON 提交但后端没设 Content-Type: application/json。
表单中写 <input name="profile[nickname]">,不是 profile.nickname 或 profile_nickname动态添加的嵌套字段(如 JS 新增地址行),也要确保 name 属性实时更新为正确索引,比如 addresses[2][zip]如果用 Vue/React,别直接传对象给 FormData.append(),要手动扁平化:用 formData.append(‘items[0][id]’, 123)
验证嵌套字段要用点号语法,且需显式声明数组规则
Laravel 验证器不接受方括号字段名直接写进 rules 数组,得转成点号路径,比如 addresses.0.city。更关键的是:只要涉及数组,就必须在规则里声明该字段是数组类型,否则 .* 通配符不生效。
使用场景:用户提交多个联系人,每个都有 name 和 phone,你要统一验证所有 phone 是否符合格式。
正确规则:[‘addresses.*.name’ => ‘required|string’, ‘addresses’ => ‘array’] —— 必须有 addresses => array 这一项错误写法:’addresses[0][name]’ 或漏掉 addresses => array,会导致验证跳过或报错 Array to string conversion如果嵌套层级深(如 orders.0.items.1.price),验证规则也照点号展开,但注意 PHP 数组键名不能含点,所以实际数据结构仍是合法多维数组
批量创建嵌套模型时,别直接用 create(),先 validate 再 map
create() 只适合单层数据;对嵌套结构(如订单+订单项),硬塞会触发 MassAssignmentException 或静默丢弃子字段。必须拆解:先验证顶层,再对每个子数组单独实例化、填充、保存。
性能影响:一次请求创建 10 个子记录,用事务包住可避免部分失败导致数据不一致;不用 insert() 批量插入,因为 Eloquent 模型事件、强制类型转换、creating 观察器都依赖单实例流程。
不要:Order::create($request->all()) —— items 字段会被忽略应该:$order = Order::create($request->only([‘user_id’, ‘total’])); $request->items->each(fn($i) => $order->items()->create($i));注意 $request->items 是集合还是数组?如果是数组,用 collect($request->items)->each(…) 更稳
前端传 JSON 时,Laravel 默认不解析嵌套字段
很多前端用 fetch + JSON.stringify() 发送复杂结构,但 Laravel 的 request() 在非 JSON 请求头下不会自动解包。即使你写了 addresses: [{ city: ‘Beijing’ }],服务端收到的仍是原始字符串,request(‘addresses’) 是字符串而非数组。
兼容性影响:Postman 测试时容易误设 header,本地开发没问题,上线 Nginx 后因请求体截断或编码问题导致嵌套字段为空。
前端必须加 headers: { ‘Content-Type’: ‘application/json’ }后端无需额外配置,Laravel 自动识别并解析 JSON body 成 PHP 数组验证规则写法不变(仍用点号),但要注意:JSON 中 key 名必须和规则完全一致,大小写敏感,比如 userProfile ≠ user_profile事情说清了就结束。最常卡住的地方不是语法,而是前后端字段名约定没对齐,或者忘了给数组字段加 xxx => array 这条基础规则。

评论(0)