如何在PostgreSQL/Supabase查询中判断用户是否关注帖子作者
问题
我在Supabase(基于PostgreSQL)中有三张表,表结构如下:
posts( id_post INT, id_user INT NOT NULL, PRIMARY KEY(id_post), FOREIGN KEY(id_user) REFERENCES users(id_user) ); users( id_user INT, PRIMARY KEY(id_user), UNIQUE(pseudo_user), ); follows( id_following INT, id_follower INT, PRIMARY KEY(id_following , id_follower ), FOREIGN KEY(id_following ) REFERENCES users(id_user), FOREIGN KEY(id_follower ) REFERENCES users(id_user) );
当前使用的查询语句为:
supabase.from('posts').select('*, users(*)').execute();
返回结果示例:
[ { "id_post": 1, "users": {"id_user": 1} } ]
现在需要检查follows表中是否存在满足id_follower = 1且id_following = 帖子的id_user的行,并在返回的users对象中新增isFollowed字段:若存在则值为1,否则为0,期望返回结果如下:
[ { "id_post": 1, "users": {"id_user": 1, "isFollowed": 1} } ]
解决方案
你可以通过PostgreSQL的子查询或表连接结合Supabase的查询语法,实现需求中的isFollowed字段添加,以下是两种可行方式:
方式一:使用EXISTS子查询(推荐)
这种方式直接在select语句中判断关注关系,逻辑清晰且性能更优:
supabase .from('posts') .select(` *, users(id_user, isFollowed:(SELECT EXISTS(SELECT 1 FROM follows WHERE id_follower = 1 AND id_following = users.id_user))) `) .then(res => { // 将布尔值转为1/0格式 const result = res.data.map(post => ({ ...post, users: { ...post.users, isFollowed: post.users.isFollowed ? 1 : 0 } })); console.log(result); });
方式二:使用左连接
通过左连接follows表筛选关注关系,再处理结果格式:
supabase .from('posts') .select(` *, users(*, follows(id_follower)) `) .leftJoin('follows', () => supabase.raw(`users.id_user = follows.id_following AND follows.id_follower = 1`) ) .then(res => { const result = res.data.map(post => ({ ...post, users: { ...post.users, isFollowed: post.users.follows ? 1 : 0, follows: undefined // 移除多余的中间字段 } })); console.log(result); });
关键说明
- 替换代码中的
id_follower = 1为当前登录用户的实际ID; - 两种方式最终都会将
isFollowed字段转为1(已关注)或0(未关注)的格式,符合需求; EXISTS子查询的方式在数据量较大时性能更优,因为它找到匹配行后会立即停止查询。
内容的提问来源于stack exchange,提问作者ThomasF
相关产品推荐
相关产品推荐

