【问题标题】:How does the Sequelize POJO JSON.stringify magic work?Sequelize POJO JSON.stringify 魔术是如何工作的?
【发布时间】:2017-01-20 03:42:20
【问题描述】:

如果你做了一个

db.MyTable.findAll({}).function(response){
    console.log(response);
}

您将看到如下所示的输出(当然取决于您的表格的外观):

[ { dataValues:
     { id: 1,
       text: 'sdf',
       complete: false,
       createdAt: Thu Jan 19 2017 11:55:38 GMT-0500 (Eastern Standard Time),
       updatedAt: Thu Jan 19 2017 11:55:38 GMT-0500 (Eastern Standard Time) },
    _previousDataValues:
     { id: 1,
       text: 'sdf',
       complete: false,
       createdAt: Thu Jan 19 2017 11:55:38 GMT-0500 (Eastern Standard Time),
       updatedAt: Thu Jan 19 2017 11:55:38 GMT-0500 (Eastern Standard Time) },
    _changed: {},
    '$modelOptions':
     { timestamps: true,
       instanceMethods: {},
       classMethods: {},
       validate: {},
       freezeTableName: false,
       underscored: false,
       underscoredAll: false,
       paranoid: false,
       rejectOnEmpty: false,
       whereCollection: null,
       schema: null,
       schemaDelimiter: '',
       defaultScope: {},
       scopes: [],
       hooks: {},
       indexes: [],
       name: [Object],
       omitNul: false,
       sequelize: [Object],
       uniqueKeys: {},
       hasPrimaryKeys: true },
    '$options':
     { isNewRecord: false,
       '$schema': null,
       '$schemaDelimiter': '',
       raw: true,
       attributes: [Object] },
    hasPrimaryKeys: true,
    __eagerlyLoadedAssociations: [],
    isNewRecord: false } ]

可以这么说,它是一个大而复杂的对象,上面有一堆元数据。

但是,如果您尝试使用以下任一方法将那个大而复杂的对象转换为字符串:

console.log(JSON.stringify(dbTodo));

res.json(dbTodo);

您将只取回实际实体的信息(大型复杂对象的 dataValues 属性中的项目)。对于我这里的测试表,它看起来像这样:

[{
    "id":1,
    "text":"sdf",
    "complete":false,
    "createdAt":"2017-01-19T16:55:38.000Z",
    "updatedAt":"2017-01-19T16:55:38.000Z"
 }]

这明显更简单(而且正是我想要的)。

这种魔法是如何发生的? sequelize 是否正在创建自己的 JSON.stringify() 和 express'res.json 版本?

什么时候发生和什么时候不发生的规则是什么?

我搜索了sequelizedocs,但没有找到好的解释。

【问题讨论】:

    标签: node.js sequelize.js


    【解决方案1】:

    这种行为有两种表现形式。

    1. 缺少的属性是不可枚举的。由Object.defineProperty 定义的属性设置为enumerable: false(或者根本不为enumerable 设置提供值)是不可枚举的属性,并被JSON.stringify 忽略。您可以在Object.getOwnPropertyDescriptor(obj, propName) 的输出中检查属性的enumerable 设置。

    2. 对象具有(或在其原型链中具有)toJSON method

      如果一个被字符串化的对象有一个名为toJSON的属性,它的值是一个函数,那么toJSON()方法自定义JSON字符串化行为:而不是被序列化的对象,调用时toJSON()方法返回的值将被序列化。

      如果对象具有或继承了toJSON 方法,则该方法的返回值将成为字符串化的目标。您可以通过读取obj.toJSON 的值来检查某个对象obj 上是否存在一个。

    【讨论】:

    • 很好的答案!谢谢。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-11-13
    • 1970-01-01
    • 1970-01-01
    • 2021-09-26
    • 1970-01-01
    • 1970-01-01
    • 2015-08-22
    相关资源
    最近更新 更多