Laravel中如何获取关联软删除表的联合查询数据?
解决方案
问题原因
withTrashed()是User模型的专属查询作用域,只会自动给users表添加包含软删除记录的条件,无法作用于join关联的posts表。你之前的尝试无效的原因:
->whereNotNull('posts.deleted_at')仅筛选已删除的Post,不是你要的「包含已删除+未删除」的所有Post;- 在join闭包里调用
withTrashed()无效,因为闭包里是基础查询构造器实例,不是Post模型实例,触发不了Post的软删除作用域。
可行解决方法
方法1:手动兼容posts表的软删除条件
直接在查询中明确允许posts表的deleted_at字段为null或非null,以此包含所有状态的Post:
User::join('posts', 'posts.user_id', '=', 'users.id') ->withTrashed() ->where(function ($query) { $query->whereNull('posts.deleted_at') ->orWhereNotNull('posts.deleted_at'); }) ->get();
如果你的Post模型全局软删除作用域没有意外影响join查询,也可以简化为(效果等价):
User::join('posts', 'posts.user_id', '=', 'users.id') ->withTrashed() ->get();
方法2:用Post模型的withTrashed()构造子查询join
通过Post模型的withTrashed()获取包含所有状态的Post查询,再将其作为子查询进行join:
$allPosts = Post::withTrashed()->select('*'); User::withTrashed() ->joinSub($allPosts, 'posts', function ($join) { $join->on('posts.user_id', '=', 'users.id'); }) ->get();
方法3:改用关联预加载(推荐,符合Laravel ORM设计)
如果业务不需要强制用join的SQL结构,而是要获取用户及其所有(含已删除)的帖子,用模型关联预加载更简洁:
User::withTrashed() ->with(['posts' => function ($query) { $query->withTrashed(); }]) ->get();
内容的提问来源于stack exchange,提问作者vbnewbie
相关产品推荐
相关产品推荐

