Sequelize查询:仅当Question.target=2时关联User模型
如何在Sequelize v3中实现条件关联查询私密问题的接收用户?
嘿,我来帮你搞定这个查询需求!你想要的是:查询所有问题时,只有当问题是私密类型(target=2)时,才通过中间表关联对应的接收用户,公开问题则不关联任何用户。针对Sequelize v3的版本,我们可以这样写查询语句:
正确的查询代码
// 假设你已经获取到sequelize实例和models对象 models.questions.findAll({ include: [ { model: models.users, through: 'QuestionRecipient', // 指定多对多的中间表 required: false, // 左外连接:确保公开问题也能被返回,即使没有关联用户 on: sequelize.and( // 保留多对多的默认关联条件 sequelize.where(sequelize.col('QuestionRecipient.userId'), '=', sequelize.col('users.id')), sequelize.where(sequelize.col('QuestionRecipient.questionId'), '=', sequelize.col('questions.id')), // 核心条件:仅当问题为私密类型时才建立关联 sequelize.where(sequelize.col('questions.target'), '=', 2) ) } ], // 可选:如果你需要额外过滤问题,比如只查已发布的,可以在这里加where条件 // where: { /* ... */ } })
代码解释
required: false:这是关键设置,代表使用左外连接(LEFT OUTER JOIN),这样即使没有关联用户的公开问题(target=1)也会被查询出来,不会被过滤掉。on子句的条件组合:我们把多对多关联的默认字段匹配条件,和questions.target = 2的自定义条件结合在一起,这样只有私密问题才会去关联中间表和用户表,公开问题则不会触发关联查询。- 查询结果表现:公开问题的
users属性会是一个空数组,私密问题的users属性则会包含所有指定的接收用户。
额外小提示:修复模型关联的写法
另外,我注意到你模型里的关联写法有点小问题,在Sequelize v3中,关联应该放在classMethods的associate函数里,这样才能确保模型加载完成后再建立关联,避免报错:
修复后的User模型
/** USER MODEL **/ module.exports = function(sequelize, DataTypes) { var User = sequelize.define('users', { firstName: { type: DataTypes.STRING(50), field: 'firstName' }, lastName: { type: DataTypes.STRING(200), field: 'lastName' }, email: { type: DataTypes.STRING(200), field: 'email' }, }, { classMethods: { associate: function(models) { User.belongsToMany(models.questions, { through: 'QuestionRecipient', foreignKey: 'userId' }); } } }); return User; // 别忘了返回模型实例! }
修复后的Question模型
/** QUESTION MODEL **/ module.exports = function(sequelize, DataTypes) { var Question = sequelize.define('questions', { content: { type: DataTypes.TEXT, field: 'content' }, target: { type: DataTypes.INTEGER, field: 'target', defaultValue: 1 // 1 = public / 2 = private } }, { classMethods: { associate: function(models) { Question.belongsToMany(models.users, { through: 'QuestionRecipient', foreignKey: 'questionId' }); } } }); return Question; // 别忘了返回模型实例! }
这样你的关联就能正常工作啦!
内容的提问来源于stack exchange,提问作者Amadou Beye
相关产品推荐
相关产品推荐

