如何用Eloquent更新含点号键的JSON列?问题排查与问询
如何在Laravel Eloquent中更新键含点号的JSON字段值
可行的实现方法
方法1:直接修改模型属性后保存
这是最直观的方式,避开批量赋值的填充检查:
$model = Something::find(1005); $state = $model->state; // 自动解析为数组 $state['2.95'] = 8.7; $model->state = $state; $model->save();
方法2:使用原生JSON函数(推荐)
利用数据库的JSON操作函数(以MySQL为例),通过DB::raw()执行:
Something::find(1005)->update([ 'state' => DB::raw("JSON_SET(state, '$."2.95"', 8.7)") ]);
注意JSON路径中带特殊字符的键需要用双引号包裹,确保数据库能正确识别目标键。
方法3:临时解除填充保护
通过unguarded方法临时绕过isFillable的检查,适合批量操作场景:
Something::unguarded(function () { Something::find(1005)->update(['state->2.95' => 8.7]); });
注意:此方法会暂时关闭模型的批量赋值保护,使用时需确保传入的字段安全。
问题原因分析
你定位到的GuardsAttributes::isFillable方法确实是核心问题:
- 当模型的
$fillable数组不为空时,只有明确列在$fillable中的字段才允许批量赋值 - 即使
$fillable为空,方法也会拒绝包含点号的键(! str_contains($key, '.')) - Eloquent的JSON字段点语法(
state->2.95)会被识别为带点号的键,触发填充限制,导致更新被静默忽略
内容的提问来源于stack exchange,提问作者SGA
相关产品推荐
相关产品推荐

