Sequelize hasMany 通过另一个表
Posted
技术标签:
【中文标题】Sequelize hasMany 通过另一个表【英文标题】:Sequelize hasMany through another table 【发布时间】:2015-05-23 19:26:32 【问题描述】:好的,所以我有以下三个models
模块:
var Module = sequelize.define('module',
id: DataTypes.INTEGER,
name: DataTypes.STRING,
description: DataTypes.STRING,
category_id: DataTypes.STRING,
module_type_id: DataTypes.STRING,
gives_score: DataTypes.INTEGER,
duration: DataTypes.STRING,
price: DataTypes.STRING
,
freezeTableName: true
)
能力:
Competence = sequelize.define('competence',
id: DataTypes.INTEGER,
name: DataTypes.STRING,
organization_id: DataTypes.INTEGER,
competence_type_id: DataTypes.INTEGER
,freezeTableName:true)
Module_has_competence:
Module_has_competence = sequelize.define('module_has_competence',
id: DataTypes.INTEGER,
module_id: DataTypes.INTEGER,
competence_id: DataTypes.INTEGER,
score: DataTypes.STRING
,
freezeTableName: true
)
如您所见,表之间的关系是n:m
所以现在我想找到Module
拥有的所有Competence
:
所以我创建了以下关系:
Module.hasMany(Competence, through: Module_has_competence, foreignKey: 'module_id');
但是当我尝试运行时:
retrieveById: function (quote_id, onSuccess, onError)
Module.find(include: [ all: true ],where: id: quote_id)
.success(onSuccess).error(onError);
它什么也不返回。但如果我删除关系,它只返回Module
谁能告诉我我做错了什么?
当我调试时
当我调试它时,它没有记录任何 sql,可悲的是它似乎只是忽略了 sql 调用?
【问题讨论】:
你能发布这些语句产生的 SQL 查询吗?那时您的数据库状态也会有所帮助 @DanRocha 请坚持住:D @DanRocha 遗憾的是它没有发布任何 sql:s 我所有其他功能都可以,但这个没有:s 您确定您正在访问该代码吗?也可以尝试使用 findAll 来测试 find 是否有问题 @dege 代码是可访问的,因为一旦我删除它收集模块的行 【参考方案1】:据我了解,您创建了多对多关系的表,并且当您查询“模块”时,您希望所有“能力”都与之关联。
虽然我无法让.hasMany()
工作,但产生的错误是:
Trace: [TypeError: Cannot call method 'replace' of undefined]
at null.<anonymous> (/Users/sjlu/Development/29165644/app.js:61:13)
at tryCatch1 (/Users/sjlu/Development/29165644/node_modules/sequelize/node_modules/bluebird/js/main/util.js:45:21)
at Promise._callHandler (/Users/sjlu/Development/29165644/node_modules/sequelize/node_modules/bluebird/js/main/promise.js:571:13)
at Promise._settlePromiseFromHandler (/Users/sjlu/Development/29165644/node_modules/sequelize/node_modules/bluebird/js/main/promise.js:581:18)
at Promise._settlePromiseAt (/Users/sjlu/Development/29165644/node_modules/sequelize/node_modules/bluebird/js/main/promise.js:713:18)
at Promise._settlePromiseAt (/Users/sjlu/Development/29165644/node_modules/sequelize/lib/promise.js:76:18)
at Promise._settlePromises (/Users/sjlu/Development/29165644/node_modules/sequelize/node_modules/bluebird/js/main/promise.js:854:14)
at Async._consumeFunctionBuffer (/Users/sjlu/Development/29165644/node_modules/sequelize/node_modules/bluebird/js/main/async.js:85:12)
at Async.consumeFunctionBuffer (/Users/sjlu/Development/29165644/node_modules/sequelize/node_modules/bluebird/js/main/async.js:40:14)
at process._tickCallback (node.js:442:13)
几乎无法调试此输出。
但是,我能够创建您的模型绑定并使用 .belongsToMany()
关联正确查询它
Competence.belongsToMany(Module,
through: Module_has_competence,
as: 'module',
foreignKey: 'module_id'
)
Module.belongsToMany(Competence,
through: Module_has_competence,
as: 'competence',
foreignKey: 'competence_id'
)
输出您正在寻找的查询
SELECT `module`.`id`,
`module`.`name`,
`module`.`description`,
`module`.`category_id`,
`module`.`module_type_id`,
`module`.`gives_score`,
`module`.`duration`,
`module`.`price`,
`module`.`createdat`,
`module`.`updatedat`,
`competence`.`id` AS `competence.id`,
`competence`.`name` AS `competence.name`,
`competence`.`organization_id` AS
`competence.organization_id`,
`competence`.`competence_type_id` AS
`competence.competence_type_id`,
`competence`.`createdat` AS
`competence.createdAt`,
`competence`.`updatedat` AS
`competence.updatedAt`,
`competence.module_has_competence`.`id` AS
`competence.module_has_competence.id`,
`competence.module_has_competence`.`module_id` AS
`competence.module_has_competence.module_id`,
`competence.module_has_competence`.`competence_id` AS
`competence.module_has_competence.competence_id`,
`competence.module_has_competence`.`score` AS
`competence.module_has_competence.score`,
`competence.module_has_competence`.`createdat` AS
`competence.module_has_competence.createdAt`,
`competence.module_has_competence`.`updatedat` AS
`competence.module_has_competence.updatedAt`
FROM `module` AS `module`
LEFT OUTER JOIN (`module_has_competence` AS
`competence.module_has_competence`
INNER JOIN `competence` AS `competence`
ON `competence`.`id` =
`competence.module_has_competence`.`module_id`)
ON `module`.`id` =
`competence.module_has_competence`.`competence_id`
WHERE `module`.`id` = 1;
据我了解,.hasMany
引用了 1:M 关系,它不需要连接表。
http://docs.sequelizejs.com/en/latest/docs/associations/#one-to-many-associations
这是我得出这个结论的要点:
https://gist.github.com/sjlu/fa5c2e0e267cd692418a
【讨论】:
【参考方案2】:史蒂文的回答对我不起作用,但切换了外键。
Competence.belongsToMany(Module,
through: Module_has_competence,
as: 'module',
foreignKey: 'competence_id'
);
Module.belongsToMany(Competence,
through: Module_has_competence,
as: 'competence',
foreignKey: 'module_id'
);
【讨论】:
以上是关于Sequelize hasMany 通过另一个表的主要内容,如果未能解决你的问题,请参考以下文章
sequelize/sequelize-typescript - 带有 HasMany 的 findAll 返回一个对象而不是数组