我有以下 Sequelize 设置:
var sequelize = new Sequelize('...', '...', '...', {
host: '...',
port: '3306',
logging: true,
define: {
timestamps: true,
paranoid: true
}
});
var Period = sequelize.define('Period', {
name: { type: Sequelize.STRING, allowNull: false },
periodStart: { type: Sequelize.INTEGER },
periodEnd: { type: Sequelize.INTEGER }
});
var Material = sequelize.define('Material', {
name: { type: Sequelize.STRING, allowNull: false }
});
var Artefact = sequelize.define('Artefact', {
accession: { type: Sequelize.STRING, allowNull: false },
simpleName: { type: Sequelize.STRING },
dimensions: { type: Sequelize.STRING },
thumbnail: { type: Sequelize.TEXT },
storageDescriptor: { type: Sequelize.TEXT },
description: { type: Sequelize.TEXT }
});
Artefact.hasMany(Period);
Period.hasMany(Artefact);
Artefact.hasMany(Material);
Material.hasMany(Artefact);
Period.hasMany(Period, { as: 'children', foreignKey: 'parentId', useJunctionTable: false });
Period.belongsTo(Period, { as: 'parent', foreignKey: 'parentId' });
Material.hasMany(Material, { as: 'children', foreignKey: 'parentId', useJunctionTable: false });
Material.belongsTo(Material, { as: 'parent', foreignKey: 'parentId' });
sequelize.sync().success(function ()
{
console.log('sync OK');
Period.findAll({ include: [ Artefact ] }).success(function (periods)
{
console.log(JSON.stringify(periods, null, 4));
});
}
).error(function (err)
{
console.log('sync FAIL');
throw err;
});
该sync()
调用导致以下CREATE
语句:
CREATE TABLE IF NOT EXISTS `Periods` (`name` VARCHAR(255) NOT NULL, `periodStart` INTEGER, `periodEnd` INTEGER, `id` INTEGER NOT NULL auto_increment , `createdAt` DATETIME NOT NULL, `updatedAt` DATETIME NOT NULL, `deletedAt` DATETIME, `parentId` INTEGER, PRIMARY KEY (`id`)) ENGINE=InnoDB;
CREATE TABLE IF NOT EXISTS `Materials` (`name` VARCHAR(255) NOT NULL, `id` INTEGER NOT NULL auto_increment , `createdAt` DATETIME NOT NULL, `updatedAt` DATETIME NOT NULL, `deletedAt` DATETIME, `parentId` INTEGER, PRIMARY KEY (`id`)) ENGINE=InnoDB;
CREATE TABLE IF NOT EXISTS `Artefacts` (`accession` VARCHAR(255) NOT NULL, `simpleName` VARCHAR(255), `dimensions` VARCHAR(255), `thumbnail` TEXT, `storageDescriptor` TEXT, `description` TEXT, `id` INTEGER NOT NULL auto_increment , `createdAt` DATETIME NOT NULL, `updatedAt` DATETIME NOT NULL, `deletedAt` DATETIME, `categoryId` INTEGER, `findLocationId` INTEGER, `storeLocationId` INTEGER, PRIMARY KEY (`id`)) ENGINE=InnoDB;
CREATE TABLE IF NOT EXISTS `ArtefactsPeriods` (`PeriodId` INTEGER , `ArtefactId` INTEGER , `createdAt` DATETIME NOT NULL, `updatedAt` DATETIME NOT NULL, `deletedAt` DATETIME, PRIMARY KEY (`PeriodId`, `ArtefactId`)) ENGINE=InnoDB;
CREATE TABLE IF NOT EXISTS `ArtefactsMaterials` (`MaterialId` INTEGER , `ArtefactId` INTEGER , `createdAt` DATETIME NOT NULL, `updatedAt` DATETIME NOT NULL, `deletedAt` DATETIME, PRIMARY KEY (`MaterialId`, `ArtefactId`)) ENGINE=InnoDB;
这是我所期望的。但是,调用会Period.findAll(...)
导致以下 SQL 和异常:
Executing: SELECT `Periods`.*, `Artefacts`.`accession` AS `Artefacts.accession`, `Artefacts`.`simpleName` AS `Artefacts.simpleName`, `Artefacts`.`dimensions` AS `Artefacts.dimensions`, `Artefacts`.`thumbnail` AS `Artefacts.thumbnail`, `Artefacts`.`storageDescriptor` AS `Artefacts.storageDescriptor`, `Artefacts`.`description` AS `Artefacts.description`, `Artefacts`.`id` AS `Artefacts.id`, `Artefacts`.`createdAt` AS `Artefacts.createdAt`, `Artefacts`.`updatedAt` AS `Artefacts.updatedAt`, `Artefacts`.`deletedAt` AS `Artefacts.deletedAt`, `Artefacts`.`categoryId` AS `Artefacts.categoryId`, `Artefacts`.`findLocationId` AS `Artefacts.findLocationId`, `Artefacts`.`storeLocationId` AS `Artefacts.storeLocationId` FROM `Periods` LEFT OUTER JOIN `Artefacts` AS `Artefacts` ON `Periods`.`id` = `Artefacts`.`PeriodId`;
Error: ER_BAD_FIELD_ERROR: Unknown column 'Artefacts.PeriodId' in 'on clause'
at Query.Sequence._packetToError (/Users/ndjm8/Work/dev/sandbox/node_modules/mysql/lib/protocol/sequences/Sequence.js:32:14)
at Query.ErrorPacket (/Users/ndjm8/Work/dev/sandbox/node_modules/mysql/lib/protocol/sequences/Query.js:82:18)
at Protocol._parsePacket (/Users/ndjm8/Work/dev/sandbox/node_modules/mysql/lib/protocol/Protocol.js:172:24)
at Parser.write (/Users/ndjm8/Work/dev/sandbox/node_modules/mysql/lib/protocol/Parser.js:62:12)
at Protocol.write (/Users/ndjm8/Work/dev/sandbox/node_modules/mysql/lib/protocol/Protocol.js:37:16)
at Socket.ondata (stream.js:51:26)
at Socket.EventEmitter.emit (events.js:117:20)
at Socket.<anonymous> (_stream_readable.js:736:14)
at Socket.EventEmitter.emit (events.js:92:17)
at emitReadable_ (_stream_readable.js:408:10)
--------------------
at Query.Sequence (/Users/ndjm8/Work/dev/sandbox/node_modules/mysql/lib/protocol/sequences/Sequence.js:15:20)
at new Query (/Users/ndjm8/Work/dev/sandbox/node_modules/mysql/lib/protocol/sequences/Query.js:12:12)
at Function.Connection.createQuery (/Users/ndjm8/Work/dev/sandbox/node_modules/mysql/lib/Connection.js:48:10)
at Connection.query (/Users/ndjm8/Work/dev/sandbox/node_modules/mysql/lib/Connection.js:100:26)
at module.exports.Query.run (/Users/ndjm8/Work/dev/sandbox/node_modules/sequelize/lib/dialects/mysql/query.js:26:17)
at module.exports.execQueueItem (/Users/ndjm8/Work/dev/sandbox/node_modules/sequelize/lib/dialects/mysql/connector-manager.js:313:21)
at /Users/ndjm8/Work/dev/sandbox/node_modules/sequelize/lib/dialects/mysql/connector-manager.js:269:25
at adjustCallback (/Users/ndjm8/Work/dev/sandbox/node_modules/sequelize/node_modules/generic-pool/lib/generic-pool.js:187:7)
at dispense (/Users/ndjm8/Work/dev/sandbox/node_modules/sequelize/node_modules/generic-pool/lib/generic-pool.js:211:9)
at Object.me.acquire (/Users/ndjm8/Work/dev/sandbox/node_modules/sequelize/node_modules/generic-pool/lib/generic-pool.js:260:5)
看起来它并没有尝试使用ArtefactsPeriods
由于sync()
. 我对自己做错了什么感到茫然。Period
和的自引用关系Material
都按预期运行,只是多对多不起作用。