如何在Sequelize与PostgreSQL中查询数组对象属性?
在PostgreSQL + Sequelize中查询JSON数组字段中的匹配记录
你的subscriptionHistory是JSON数组类型,而非单个JSON对象,之前的写法未匹配数组结构,导致查询无效。以下是两种环境下的可行解决方案:
原生SQL解决方案
方法1:使用@>包含操作符(推荐,适用于jsonb类型)
@>操作符用于判断JSON对象/数组是否包含指定JSON值,针对数组字段,需将条件包装为数组形式:
SELECT * FROM vegiano_dev."subscription-tokens" WHERE "subscriptionHistory"::jsonb @> '[{"userSubscribedToo": "a4ufoAB"}]'::jsonb;
若字段本身已定义为jsonb类型,可省略::jsonb类型转换。
方法2:展开数组后匹配(灵活适配复杂过滤)
通过json_array_elements展开数组,再匹配目标字段,适合需要同时过滤数组元素其他属性的场景:
SELECT DISTINCT st.* FROM vegiano_dev."subscription-tokens" st CROSS JOIN json_array_elements(st."subscriptionHistory") AS sh WHERE sh->>'userSubscribedToo' = 'a4ufoAB';
Sequelize解决方案
方法1:利用Op.contains操作符(jsonb字段适用)
确保模型中subscriptionHistory字段定义为DataTypes.JSONB,使用Sequelize的Op.contains实现包含匹配:
const { Op } = require('sequelize'); const totalEarnings = await SubscriptionToken.count({ where: { subscriptionHistory: { [Op.contains]: [{ userSubscribedToo: user.id }] } } });
方法2:通过literal编写原生SQL片段(兼容json/jsonb)
如果字段是json类型,或需要更灵活的SQL逻辑,可使用literal注入原生查询,同时注意参数绑定避免SQL注入:
const { Op } = require('sequelize'); const totalEarnings = await SubscriptionToken.count({ where: sequelize.literal(`"subscriptionHistory"::jsonb @> :match`), replacements: { match: JSON.stringify([{ userSubscribedToo: user.id }]) } });
内容的提问来源于stack exchange,提问作者Oliver Dixon
相关产品推荐
相关产品推荐

