【发布时间】:2019-04-14 10:37:33
【问题描述】:
我将 sequelize.js 与 node.js 和 postgres 一起使用。 我从一个示例中得到了 2 个简单的表作为各种“POC”。 我将 ID 更改为 UUID,但在插入第二个表时遇到问题(使用 UUID FK)。
我正在使用邮递员对其进行测试。 我正在使用 UUID 创建待办事项行,没有任何问题, 然后我试图创建一个 todo 项目,它有一个 todo id 作为外键 它似乎无法识别该 ID!
我在 postgres 中尝试了一个手动脚本,它成功了。 我可能在代码方面遗漏了一些东西,但我不知道是什么。
这是邮递员返回给我的错误 -
{
"name": "SequelizeDatabaseError",
"parent": {
"name": "error",
"length": 96,
"severity": "ERROR",
"code": "22P02",
"file": "uuid.c",
"line": "137",
"routine": "string_to_uuid",
"sql": "INSERT INTO \"TodoItems\" (\"id\",\"content\",\"complete\",\"createdAt\",\"updatedAt\",\"todoId\") VALUES ($1,$2,$3,$4,$5,$6) RETURNING *;"
},
"original": {
"name": "error",
"length": 96,
"severity": "ERROR",
"code": "22P02",
"file": "uuid.c",
"line": "137",
"routine": "string_to_uuid",
"sql": "INSERT INTO \"TodoItems\" (\"id\",\"content\",\"complete\",\"createdAt\",\"updatedAt\",\"todoId\") VALUES ($1,$2,$3,$4,$5,$6) RETURNING *;"
},
"sql": "INSERT INTO \"TodoItems\" (\"id\",\"content\",\"complete\",\"createdAt\",\"updatedAt\",\"todoId\") VALUES ($1,$2,$3,$4,$5,$6) RETURNING *;"
}
这里是相关的js文件-
todoItems.js 控制器 -
const TodoItem = require('../dal/models').TodoItem;
const uuid = require('uuid/v4');
module.exports = {
create(req, res) {
return TodoItem
.create({
content: req.body.content,
todoId: req.params.todoId,
})
.then(todoItem => res.status(201).send(todoItem))
.catch(error => res.status(400).send(error));
},
update(req, res) {
return TodoItem
.find({
where: {
id: req.params.todoItemId,
todoId: req.params.todoId,
},
})
.then(todoItem => {
if (!todoItem) {
return res.status(404).send({
message: 'TodoItem Not Found',
});
}
return todoItem
.update({
content: req.body.content || todoItem.content,
complete: req.body.complete || todoItem.complete,
})
.then(updatedTodoItem => res.status(200).send(updatedTodoItem))
.catch(error => res.status(400).send(error));
})
.catch(error => res.status(400).send(error));
},
destroy(req, res) {
return TodoItem
.find({
where: {
id: req.params.todoItemId,
todoId: req.params.todoId,
},
})
.then(todoItem => {
if (!todoItem) {
return res.status(404).send({
message: 'TodoItem Not Found',
});
}
return todoItem
.destroy()
.then(() => res.status(204).send())
.catch(error => res.status(400).send(error));
})
.catch(error => res.status(400).send(error));
},
};
todos.js 控制器-
const Todo = require('../dal/models').Todo;
const TodoItem = require('../dal/models').TodoItem;
module.exports = {
create(req, res) {
return Todo
.create({
title: req.body.title,
})
.then((todo) => res.status(201).send(todo))
.catch((error) => res.status(400).send(error));
},
list(req, res) {
return Todo
.findAll({
include: [{
model: TodoItem,
as: 'todoItems',
}],
order: [
['createdAt', 'DESC'],
[{ model: TodoItem, as: 'todoItems' }, 'createdAt', 'ASC'],
],
})
.then((todos) => res.status(200).send(todos))
.catch((error) => res.status(400).send(error));
},
retrieve(req, res) {
return Todo
.findByPk(req.params.todoId, {
include: [{
model: TodoItem,
as: 'todoItems',
}],
})
.then((todo) => {
if (!todo) {
return res.status(404).send({
message: 'Todo Not Found',
});
}
return res.status(200).send(todo);
})
.catch((error) => res.status(400).send(error));
},
update(req, res) {
return Todo
.findByPk(req.params.todoId, {
include: [{
model: TodoItem,
as: 'todoItems',
}],
})
.then(todo => {
if (!todo) {
return res.status(404).send({
message: 'Todo Not Found',
});
}
return todo
.update({
title: req.body.title || todo.title,
})
.then(() => res.status(200).send(todo))
.catch((error) => res.status(400).send(error));
})
.catch((error) => res.status(400).send(error));
},
destroy(req, res) {
return Todo
.findByPk(req.params.todoId)
.then(todo => {
if (!todo) {
return res.status(400).send({
message: 'Todo Not Found',
});
}
return todo
.destroy()
.then(() => res.status(204).send())
.catch((error) => res.status(400).send(error));
})
.catch((error) => res.status(400).send(error));
},
};
todo 表创建迁移 -
module.exports = {
up: (queryInterface, Sequelize) =>
queryInterface.createTable('Todos', {
id: {
allowNull: false,
primaryKey: true,
type: Sequelize.UUID,
},
title: {
type: Sequelize.STRING,
allowNull: false,
},
createdAt: {
allowNull: false,
type: Sequelize.DATE,
},
updatedAt: {
allowNull: false,
type: Sequelize.DATE,
},
}),
down: (queryInterface /* , Sequelize */) => queryInterface.dropTable('Todos'),
};
todo-item 表创建迁移 -
module.exports = {
up: (queryInterface, Sequelize) =>
queryInterface.createTable('TodoItems', {
id: {
allowNull: false,
primaryKey: true,
type: Sequelize.UUID,
},
content: {
type: Sequelize.STRING,
allowNull: false,
},
complete: {
type: Sequelize.BOOLEAN,
defaultValue: false,
},
createdAt: {
allowNull: false,
type: Sequelize.DATE,
},
updatedAt: {
allowNull: false,
type: Sequelize.DATE,
},
todoId: {
type: Sequelize.UUID,
onDelete: 'CASCADE',
references: {
model: 'Todos',
key: 'id',
as: 'todoId',
},
},
}),
down: (queryInterface /* , Sequelize */) =>
queryInterface.dropTable('TodoItems'),
};
待办事项模型 -
const uuid = require('uuid/v4');
'use strict';
module.exports = (sequelize, DataTypes) => {
const Todo = sequelize.define('Todo', {
title: {
type: DataTypes.STRING,
allowNull: false,
}
});
Todo.associate = (models) => {
Todo.hasMany(models.TodoItem, {
foreignKey: 'todoId',
as: 'todoItems',
});
};
Todo.beforeCreate((item, _ ) => {
return item.id = uuid();
});
return Todo;
};
待办事项模型 -
const uuid = require('uuid/v4');
'use strict';
module.exports = (sequelize, DataTypes) => {
const TodoItem = sequelize.define('TodoItem', {
content: {
type: DataTypes.STRING,
allowNull: false,
},
complete: {
type: DataTypes.BOOLEAN,
defaultValue: false,
}
});
TodoItem.associate = (models) => {
TodoItem.belongsTo(models.Todo, {
foreignKey: 'todoId',
onDelete: 'CASCADE',
});
};
TodoItem.beforeCreate((item, _ ) => {
return item.id = uuid();
});
return TodoItem;
};
【问题讨论】:
标签: node.js postgresql orm sequelize.js