【问题标题】:Can't use "delete" operator on mongoose query results不能对 mongoose 查询结果使用“删除”运算符
【发布时间】:2018-06-20 05:00:11
【问题描述】:

我正在尝试在将数据发送回浏览器之前删除密钥。出于某种原因,可能是因为它是一个猫鼬对象,这不起作用:

delete myObject.property

如果我这样做 console.log(delete myObject.property) 我会得到 true 我理解这意味着该属性没有被删除。我怎样才能摆脱这把钥匙?

(更多背景:我知道我可以通过使用 mongoose 选择查询来关闭它,但我确实需要最初选择键。我也可以将其设置为 null,这很好,但我宁愿得到完全摆脱钥匙)

【问题讨论】:

  • 通常这意味着您尝试在数组上使用delete。如果你这样做了 -> 尝试使用 for-of 循环(for 用于浏览器)将所有相同的属性删除到元素数组中

标签: javascript node.js mongodb express mongoose


【解决方案1】:

正如 MikaS 所说,您需要先转换才能将 Mongoose 文档对象转换为普通对象:

const newObj = myObject.toObject();
delete newObj.property;

如果你这样做一次应该没问题。但是,如果您必须在所有返回此类文档的地方重复此逻辑,但省略了某些键或其他转换,您应该在您的架构上定义转换:

// specify the transform schema option
if (!schema.options.toObject) schema.options.toObject = {};
schema.options.toObject.transform = function (doc, ret, options) {
  // any kind of simple/complicated transformation logic here
  // remove the _id of every document before returning the result
  delete ret._id;
  return ret;
}

// without the transformation in the schema
doc.toObject(); // { _id: 'anId', name: 'Wreck-it Ralph' }

// with the transformation
doc.toObject(); // { name: 'Wreck-it Ralph' }

在文档中了解Document#toObject and transformations

【讨论】:

    【解决方案2】:

    先将Mongoose文档对象转化为普通的Javascript对象:

    const newObj = myObject.toObject();
    delete newObj.property;
    

    【讨论】:

      【解决方案3】:

      适用于某些版本:

      myObject.set('property_to_delete', undefined, {strict: false} );
      myObject.save();
      

      【讨论】:

        【解决方案4】:

        使用 lodash pickby 方法。 文档:https://lodash.com/docs/#pickBy

        【讨论】:

          【解决方案5】:

          delete 返回 true,除非该属性不可配置。 所以你的密钥确实被删除了。您仍然可以看到该密钥,因为它在 Mongoose 文档实例中被删除时在原型链中可用。

          尝试转换:

          let Schema = new mongoose.Schema({
            myProperty: String,
            myOtherProperty: String
          }, {
            toObject: {
              transform: function (doc, ret) {
                delete ret.myOtherProperty;
              }
            },
            toJSON: {
              transform: function (doc, ret) {
                delete ret.myOtherProperty;
              }
            }
          });
          

          【讨论】:

            【解决方案6】:

            我为自己找到了一个解决方案,我只需在 Schema 上创建一个小辅助方法来删除它可能存在的任何字段。

            示例用户架构(简化):

            const UserSchema = new Schema(
              {
                name: {
                  type: String,
                  required: true,
                  trim: true
                },
                email: {
                  type: String,
                  required: true,
                  trim: true,
                },
                password: {
                  type: String,
                  required: true,
                  trim: true
                },
              },
              {
                timestamps: true
              }
            );
            
            const User = mongoose.model("User", UserSchema);
            module.exports = User;
            

            出于安全原因,我喜欢在发送回客户端时从用户对象中删除密码盐。我可能会在我的UserSchema 中创建一个辅助方法,例如:

            UserSchema.methods.hidePasswordSalt = function() {
              let self = this;
              self = self.toObject();
              if (self.password) {
                delete self.password;
              }
              return self;
            };
            

            然后,在我的控制器等中,当我检索我的User 时,我调用该方法并发送结果:

            User.findOne({ _id: req.session.userId })
              .then(user => {
                user = user.hidePasswordSalt(); // removes password field
                return res.status(200).json(user);
              })
              .catch(error => {
                return res.status(403).json(error.errors);
              });
            

            【讨论】:

              猜你喜欢
              • 1970-01-01
              • 2021-05-12
              • 1970-01-01
              • 2021-08-11
              • 1970-01-01
              • 1970-01-01
              • 2015-10-31
              • 1970-01-01
              • 1970-01-01
              相关资源
              最近更新 更多