Laravel updateOrCreate函数按需赋值:创建/更新时分别设置用户ID
解决Laravel updateOrCreate中创建/更新时分别设置不同字段的问题
嘿,这个需求在Laravel开发里挺常见的,你当前的代码确实会不管创建还是更新都同时设置user_id和user_modified_id,不符合你想要的「创建时赋值user_id,更新只更user_modified_id」的逻辑。我给你几个不同层级的解决方案,你可以根据项目情况选最优的:
方案1:直观的分情况处理(适合新手或简单场景)
直接先查询记录是否存在,存在则只更新user_modified_id,不存在则创建并设置user_id和初始的user_modified_id:
$variable = Variable::where([ 'name' => $name, 'landing_id' => $landing_id, 'version_id' => $version_id, 'page_id' => $page_id ])->first(); if ($variable) { // 记录存在,仅更新修改人ID $variable->update(['user_modified_id' => Auth::user()->id]); } else { // 记录不存在,创建时设置创建人和修改人ID $variable = Variable::create([ 'name' => $name, 'landing_id' => $landing_id, 'version_id' => $version_id, 'page_id' => $page_id, 'user_id' => Auth::user()->id, 'user_modified_id' => Auth::user()->id // 刚创建时修改人就是创建人,可选保留 ]); }
方案2:利用updateOrCreate的返回值优化(简洁高效)
updateOrCreate会返回模型实例,并且Laravel模型自带wasRecentlyCreated属性,可以判断该实例是否是刚刚创建的。我们可以先执行更新逻辑,再针对创建的情况补充设置user_id:
$variable = Variable::updateOrCreate( // 查询条件 ['name' => $name, 'landing_id' => $landing_id, 'version_id' => $version_id, 'page_id' => $page_id], // 更新时要设置的字段(创建时也会默认用这些,但我们后续会补充user_id) ['user_modified_id' => Auth::user()->id] ); // 如果是刚创建的记录,补充设置创建人ID if ($variable->wasRecentlyCreated) { $variable->user_id = Auth::user()->id; $variable->save(); }
方案3:模型事件统一处理(优雅复用,适合多模型场景)
如果你的项目里多个模型都需要「创建人、修改人」的逻辑,推荐把这个逻辑放到模型的事件里,让控制器代码更简洁:
首先在Variable模型里注册事件:
namespace App\Models; use Illuminate\Database\Eloquent\Model; use Illuminate\Support\Facades\Auth; class Variable extends Model { protected static function booted() { // 创建时设置创建人和修改人 static::creating(function ($variable) { $variable->user_id = Auth::user()->id; $variable->user_modified_id = Auth::user()->id; }); // 更新时仅设置修改人,同时禁止修改创建人(可选) static::updating(function ($variable) { $variable->user_modified_id = Auth::user()->id; // 防止意外修改创建人ID,直接移除该字段的更新 unset($variable->user_id); }); } }
然后控制器里的代码就可以简化成:
$variable = Variable::updateOrCreate( ['name' => $name, 'landing_id' => $landing_id, 'version_id' => $version_id, 'page_id' => $page_id], [] // 不需要传用户相关字段,模型事件会自动处理 );
方案选择建议
- 如果只是单个模型的简单需求,方案2的代码最简洁,效率也不错(只比方案1多一次save,但逻辑更紧凑);
- 如果是多模型都需要类似逻辑,方案3的模型事件方式最优雅,能统一管理业务逻辑;
- 方案1最直观,适合刚接触Laravel的开发者理解。
内容的提问来源于stack exchange,提问作者user3819000
相关产品推荐
相关产品推荐

