无法使用async,nodejs和mongodb更改javascript对象属性

时间:2014-01-05 19:38:41

标签: javascript node.js mongodb

我有以下代码:

exports.home = function(Comment,User,Activity){
    return function(req, res){  
        var get_url = req.url.split(/\?/)[1];
        if (!req.user)
        {
            res.writeHead(302, {
              'Location': '/'
            });
            res.end();
            return;
        }

        var posts_id_array = req.user.posts_id_array;
        var stocks_array = req.user.watch_list;
        var subscribe_to_arr = req.user.subscribe_to;
        User.find({_id:{$ne:req.user._id, $nin:subscribe_to_arr}}).sort('-_id').limit(10).exec(function(err_user, users){
            Activity.find({$or:[{owner_id : {$in :subscribe_to_arr}},{owner_id:req.user._id}]}).sort('-time_stamp').limit(20).exec(function(err_post,activities){
                 if( err_post || !activities) {
                    res.render('home',{user:req.user,stocks:JSON.stringify(stocks_array)});
                 }
                 else 
                 {
                    var funcArr = [];
                    var hasPost = ["publish","comment","like"];
                    var notPost = ["add_stock","delete_stock"];
                    for(var i =0;i<activities.length;i++)
                    {
                        if(hasPost.indexOf(activities[i].type)!=-1){
                            var fobj = {
                                act: activities[i],
                                f:function(callback){
                                    var test = this.act;
                                    var comments = test.post.comments;
                                    Comment.find({_id:{$in:comments}},function(err,_comments){
                                        console.log("test.post.comments");
                                        //console.log(test.post.comments);
                                        console.log("comments ");
                                        console.log(_comments);
                                        console.log("type");
                                        console.log(typeof test);
                                        console.log("cloning obj");
                                    //  obj = JSON.parse(JSON.stringify(test)); // cloning obj
                                        console.log(test);
                                        console.log("setting value of comments");
                                        **console.log(test.post.comments = _comments);** //unable to  change test.post.comments
                                        console.log("after assignment");
                                        console.log(test.post.comments); // remain unchanged but work with obj.post.comments if I clone test as obj and use obj instead.
                                        callback(null,test);
                                    });
                                }
                            }
                            funcArr.push(fobj.f.bind(fobj));
                        }else{
                            var fobj = {
                                act: activities[i],
                                f :function(callback){
                                    callback(null,this.act);
                                }
                            }
                            funcArr.push(fobj.f.bind(fobj));
                        }
                    }

                    async.series(funcArr,function(err,resArr){
                        console.log("resArr");
                        console.log(resArr);
                        res.render('home',{user:req.user,posts:JSON.stringify(resArr),stocks:JSON.stringify(stocks_array), other_users:JSON.stringify(users)});
                    });
                 }
            });
        }) // end of User.find
    }// end of return function(req,res);
}

我想更新“test”对象的post.comments属性(参见**部分),但我无法这样做。但是,当我将“test”对象克隆为“obj”然后设置“obj.post.comments”时,它可以工作。为什么会这样?是因为我搞砸了一些范围问题吗?

感谢。

2 个答案:

答案 0 :(得分:1)

我自己解决了这个问题。事实证明,我在test.post.comments中存储了mongodb的Schema.Types.ObjectId,经过一些搞乱我发现后无法覆盖。当我将测试对象的克隆创建为“obj”时,obj.post.comments中的Schema.Types.ObjectId对象存储在允许修改的不同位置。我的猜想是test.post.comments指向mongodb本身内的Schema.Types.ObjectId,因此无法覆盖。当我创建测试对象的副本时,问题就解决了。

答案 1 :(得分:0)

var test = this.act.concat();

请改用它。 因为js中的数组替换实际上并不复制数组,而是引用原始地址。

例如

var test = ['A','B','C','D'];
var copied = test;
test[0] = 0;
copied[1] = 0;

console.log(test) //0,0,'C','D'
console.log(copied) //0,0,'C','D'

为避免此问题,您可以使用.concat()复制数组 如果你不添加任何东西,它将被用作复制。

var test = ['A','B','C','D'];
var copied = test.concat();
test[0] = 0;
copied[1] = 0;

console.log(test) //0,'B','C','D'
console.log(copied) //'A',0,'C','D'