Laravel 6更新函数报错SQLSTATE[42S22]:where子句'id'列不存在
解决Laravel更新操作中"Unknown column 'id' in 'where clause'"的错误
这个报错的原因很明确:你的apps表主键是appId,但Laravel的Eloquent模型默认会把id作为主键字段来使用,所以当框架尝试执行查询或更新时,会自动生成包含id的where条件,而你的表里没有这个字段,就触发了错误。
咱们一步步来解决这个问题:
1. 给App模型指定正确的主键
打开你的App模型文件(通常在app/Models/App.php),添加以下配置代码:
<?php namespace App\Models; use Illuminate\Database\Eloquent\Model; class App extends Model { // 指定表的主键字段为appId protected $primaryKey = 'appId'; // 如果你的appId不是自增整数类型(比如字符串),必须加上这一行 public $incrementing = false; // 其他模型原有代码... }
这一步告诉Laravel,以后操作App模型时,要用appId作为主键来查询和更新数据。
2. 修正控制器里的update方法
你当前的控制器代码存在两个明显问题:
- 使用了路由模型绑定
App $app,但模型未指定主键,导致框架尝试用id查找记录,最终$app为空 - 硬编码了
appId=1,这不是通用的更新逻辑,无法针对指定记录操作
方案一:使用路由模型绑定(推荐)
首先确保你的路由定义是这样的(示例在routes/web.php中):
Route::put('/apps/{app}', [YourControllerName::class, 'update']);
因为已经在模型里指定了主键,Laravel会自动用appId匹配路由里的{app}参数,找到对应的模型实例。
然后修改控制器方法:
public function update(Request $request, App $app) { // 验证请求数据 $validatedData = $request->validate([ 'domain' => ['required', 'string','min:2', 'max:255'], ]); // 直接更新模型 $app->update($validatedData); // 也可以分步更新(效果相同): // $app->domain = $validatedData['domain']; // $app->save(); return Redirect::back()->with('success', __('sentence.User updated successfully')); }
方案二:手动通过appId查询(无需路由模型绑定)
如果你的路由是直接传递appId参数,比如:
Route::put('/apps/{appId}', [YourControllerName::class, 'update']);
那控制器方法可以改成这样:
public function update(Request $request, $appId) { $validatedData = $request->validate([ 'domain' => ['required', 'string','min:2', 'max:255'], ]); // 通过appId查找记录,找不到则自动抛出404错误 $app = App::where('appId', $appId)->firstOrFail(); $app->update($validatedData); return Redirect::back()->with('success', __('sentence.User updated successfully')); }
为什么原来的代码会报错?
你原来的代码中,App $app路由模型绑定会尝试用id去查询数据库,但你的表没有id列,所以$app是null值。后续你虽然写了App::where('appId','=','1')->first()->update(...),但前面的$app = ...覆盖了这个操作,而且框架处理null模型的update时,会自动生成where id is null的SQL语句,这就是报错的根源。
内容的提问来源于stack exchange,提问作者Volka Dimitrev
相关产品推荐
相关产品推荐

