Mysql 续集JSON数据类型
我将模型定义为Mysql 续集JSON数据类型,mysql,json,node.js,sequelize.js,Mysql,Json,Node.js,Sequelize.js,我将模型定义为 module.exports = function (sequelize, DataTypes) { const MyModel = sequelize.define('MyModel', { data: { type: DataTypes.JSON, ... }, ... }); return MyModel; }; 我使用 MyModel.findAll().then(myModels => ...);
module.exports = function (sequelize, DataTypes) {
const MyModel = sequelize.define('MyModel', {
data: {
type: DataTypes.JSON,
...
},
...
});
return MyModel;
};
我使用
MyModel.findAll().then(myModels => ...);
但是,查询结果中的
data
字段是字符串,而不是JSON对象。如何修复它?MySQL不支持JSON数据类型
请看这里的文档
一种解决方法是在查询文本时使用文本和字符串化/解析它还不受支持。但你可以这样做:
module.exports = function (sequelize, DataTypes) {
const MyModel = sequelize.define('MyModel', {
data: {
type: Sequelize.TEXT,
get: function () {
return JSON.parse(this.getDataValue('value'));
},
set: function (value) {
this.setDataValue('value', JSON.stringify(value));
},
,
...
},
...
});
return MyModel;
};
module.exports = (sequelize, DataTypes) => {
const Store = sequelize.define(
"Store",
{
name: DataTypes.STRING,
isActive: DataTypes.BOOLEAN,
address: {
type: DataTypes.TEXT,
get: function() {
return JSON.parse(this.getDataValue("address"));
},
set: function(value) {
return this.setDataValue("address", JSON.stringify(value));
}
}
},
{}
);
Store.associate = function(models) {
// associations can be defined here
Store.hasMany(models.Order, {
foreignKey: "id",
targetKey: "storeId"
});
};
return Store;
};
我还在github上发现了这个包,如果你不想使用getter和setter,你可以尝试一下。Jalal的回答很好,但对我来说不起作用,除非我稍微调整一下。以下是对我有效的方法: 首先:创建一个迁移,将所需字段添加为类型
文本
。
示例-我想在存储
表中添加一个名为地址
的字段:
module.exports = {
up: (queryInterface, Sequelize) => {
return queryInterface.addColumn("Stores", "address", Sequelize.TEXT);
},
down: (queryInterface, Sequelize) => {
return queryInterface.removeColumn("Stores", "address");
}
};
下一步:
在模型中,将带有getter和setter的字段添加到字段和数据类型列表(对象)中:
address: {
type: DataTypes.TEXT,
get: function() {
return JSON.parse(this.getDataValue("address"));
},
set: function(value) {
return this.setDataValue("address", JSON.stringify(value));
}
},
因此,我的整个模型如下所示:
module.exports = function (sequelize, DataTypes) {
const MyModel = sequelize.define('MyModel', {
data: {
type: Sequelize.TEXT,
get: function () {
return JSON.parse(this.getDataValue('value'));
},
set: function (value) {
this.setDataValue('value', JSON.stringify(value));
},
,
...
},
...
});
return MyModel;
};
module.exports = (sequelize, DataTypes) => {
const Store = sequelize.define(
"Store",
{
name: DataTypes.STRING,
isActive: DataTypes.BOOLEAN,
address: {
type: DataTypes.TEXT,
get: function() {
return JSON.parse(this.getDataValue("address"));
},
set: function(value) {
return this.setDataValue("address", JSON.stringify(value));
}
}
},
{}
);
Store.associate = function(models) {
// associations can be defined here
Store.hasMany(models.Order, {
foreignKey: "id",
targetKey: "storeId"
});
};
return Store;
};
现在您可以像使用数据库中的JSON类型字段一样创建和检索记录
例如:const store=wait store.create({name:“Joe's corner store”,地址:{address1:“123 test street”,city:“Los Angeles”,state:“CA”})
一些注意事项:
在上面的代码块中
- 将
替换为要使用的字段名地址
- 用您的型号/表名替换
存储
- 我在setter上添加了
,否则它在尝试创建新记录时出错(就像Jalal所做的那样)return
- 最简单的解决方案是使用这个名为
创建数据库和架构:
var Sequelize=require('Sequelize'),
JsonField=require('sequelize-json'),
db,
用户;
db=新的续集('数据库','用户名','密码'{
方言:“sqlite”,
日志记录:false
});
User=db.define('User'{
用户名:Sequelize.STRING,
jsonField:jsonField(db,'User','jsonField')
});
注意JsonField的参数,传递Sequelize实例、模型名称和字段名称。有一点awkard,但是为了向模型实例添加适当的钩子,这是必需的
现在,您可以始终将该字段视为json对象:
User.create({
用户名:“Scott”,
杰森菲尔德:{
喜欢:[“运行”、“节点”]
}
})
.then(功能(用户){
user.jsonField.likes.push('tests');
返回user.save();
})
.then(功能(用户){
expect(user.jsonField.to.be.a('object');
expect(user.jsonField.likes).to.have.length(3);
});代码>无需使用getter和setter,因为sequelize现在支持JSON。请参阅使用JSON.parse(data)
@AkshayKumar,我认为这不是必需的。如果字段类型已经是JSON,它应该返回JSON而不是字符串。@MikkoP您使用的是哪一个数据库?@divsingh MySQL在标记中,所以我猜MySQLWorks与postgres中的预期一样。从Sequelize 4.18开始支持MySQL的JSON这应该是公认的答案,非常有效谢谢Jalal,另外,sequelize json模块是不需要的,它也在3-4年内没有得到支持,这适用于所有情况。需要注意的是,这个.getDataValue('value'),值应该是'data',或者不管您的字段名是什么。显然,在版本4.18中,sequelize添加了JSON支持。请记住,MySQL会将值截断为列的最大长度,而不会出现错误,这意味着存储的JSON可能会被破坏(触发解析错误)。set()
函数应在保存之前验证长度。请与您一起跳到顶部!