【问题标题】:Problem with updating MongoDB document with mongoose使用 mongoose 更新 MongoDB 文档的问题
【发布时间】:2019-02-28 18:49:52
【问题描述】:

我在更新文档时遇到问题。当我用 findByIdAndUpdate 更新文档时,它会更新,但这不是我想要的,因为我真的不想删除密码和其他人。我真的不知道为什么密码、userCreated 和 userModified 会被删除,因为 findByIdAndUpdate 使用 $set。

请求正文:

{
    "userProfile": {
        "username": "test",
        "email": "test2",
        "firstName": "Test3",
        "lastName": "Test4"
    }
}

原始文件:

{
        "_id" : ObjectId("5c77b064cecb8c2eacaacdb4"),
        "userProfile" : {
                "firstName" : "John",
                "lastName" : "Doe",
                "userCreated" : "1551347812064",
                "userModified" : "1551347812064",
                "username" : "johndoe",
                "email" : "john.doe@gmail.com",
                "password" : "$2a$10$qkRYXk4fgFWJ3dVaYDMQM.4TzLIKUz8axf/lJU8HihvQIC6fVj7Jm"
        },
        "userSheets" : [ ],
        "userTemplates" : [ ],
        "__v" : 0
}

我想要什么:

{
        "_id" : ObjectId("5c77b064cecb8c2eacaacdb4"),
        "userProfile" : {
                "firstName" : "UpdatedName",
                "lastName" : "UpdatedLastname",
                "userCreated" : "1551347812064",
                "userModified" : "1551347812064",
                "username" : "updatedUsername",
                "email" : "updated.email@gmail.com",
                "password" : "$2a$10$qkRYXk4fgFWJ3dVaYDMQM.4TzLIKUz8axf/lJU8HihvQIC6fVj7Jm"
        },
        "userSheets" : [ ],
        "userTemplates" : [ ],
        "__v" : 0
}

我得到了什么:

{
        "_id" : ObjectId("5c77b064cecb8c2eacaacdb4"),
        "userProfile" : {
                "firstName" : "UpdatedName",
                "lastName" : "UpdatedLastname",
                "username" : "updatedUsername",
                "email" : "updated.email@gmail.com"
        },
        "userSheets" : [ ],
        "userTemplates" : [ ],
        "__v" : 0
}

我不知道这里发生了什么,但在 userProfile 中只保留了我应要求提供的密钥。

这是我在 mongoose 中使用的两个文件和代码:

user.js

module.exports.updateUser = function(id, updatedUser, callback) {
    var options = {
        new: true
    };
    User.findByIdAndUpdate(id, updatedUser, options, (err, userAll) => {
        if(err) throw err;
        const user = {
            success: true,
            userProfile: userAll.userProfile
        };
        callback(null, user);
    });
}

users.js

router.route('/profile')
    // Send user account
    .get(passport.authenticate('jwt', {session: false}), (req, res) => {
        res.json({user: req.user});
    })
    // Updates user account
    .put(passport.authenticate('jwt', {session: false}), (req, res) => {
        const username = req.body.userProfile.username;
        const email = req.body.userProfile.email;
        const id = req.user._id;

        User.areUsernameAndEmailAvailable(username, email, id, (err, isAvailable) => {
            if(err) throw err;
            if(isAvailable.success) {
                // If username and email are available, if updates user profile
                const updatedUser = req.body;
                User.updateUser(id, updatedUser, (err, updatedUserAndSuccess) => {
                    if(err) throw err;
                    res.json(updatedUserAndSuccess);
                });
            } else {
                res.json(isAvailable);
            }
        });
    })

架构:

const UserSchema = Schema({
    userProfile: {
        username: { type: String, require: true },
        email: { type: String, require: true },
        firstName: { type: String, default: '' },
        lastName: { type: String, default: '' },
        userCreated: { type: String, default: Date.now() },
        userModified: { type: String, default: Date.now() },
        password: { type: String, require: true }
    },
    userSheets: [
        {
            sheetName: { type: String },
            sheetDescription: { type: String, default: '' },
            sheetCreated: { type: Date, default: Date.now() },
            sheetModified: { type: String, default: Date.now() },
            status: { type: String, default: 'Not started yet' },
            statusChanged: { type: Date, default: Date.now() },
            sheetContent: {
                itemType: { type: String },
                itemRow: { type: Number },
                itemColumn: { type: Number },
                itemContent: { type: String, default: '' },
                itemDatatype: { type: String },
            }
        }
    ],
    userTemplates: [
        {
            templateName: { type: String },
            templateDescription: { type: String, default: '' },
            templateCreated: { type: Date, default: Date.now() },
            templateModified: { type: Date, default: Date.now() },
            templateContent: [
                {
                    templateItemType: { type: String },
                    templateItemRow: { type: Number },
                    templateItemColumn: { type: Number },
                    templateItemContent: { type: String },
                    templateItemDatatype: { type: String },
                }
            ]
        }
    ]
});

节点:10.15.0 MongoDB:4.0.5 猫鼬:5.4.2 快递:4.16.4

【问题讨论】:

    标签: node.js mongodb express mongoose


    【解决方案1】:

    您正在替换整个 userProfile 对象,您只需要更新您想要的键。

    考虑一下这是不是你的身体

    body = {
        "userProfile": {
            "username": "test",
            "email": "test2",
            "firstName": "Test3",
            "lastName": "Test4"
        }
    }
    

    你应该传递这样的东西

    User.findByIdAndUpdate(id, body.updatedUser)
    

    【讨论】:

    • 所以你的意思是更新前的更新对象应该是这样的: updatedUser = { "userProfile": { "username": "Test", "email": "Test2", "firstName": "Test3", "lastName": "Test4" } } - 当我遇到问题时,我传递的是完全相同的对象。
    • 你应该只通过这些项目 { "username": "test", "email": "test2", "firstName": "Test3", "lastName": "Test4" }
    猜你喜欢
    • 1970-01-01
    • 2022-07-12
    • 2017-01-06
    • 2015-10-04
    • 2016-10-15
    • 2017-05-29
    • 1970-01-01
    • 2017-09-22
    • 1970-01-01
    相关资源
    最近更新 更多