如何使用 MongoDB 中的值更新 Javascript class 的成员变量?

How can I update a member variable of a Javascript class with a value from MongoDB?

我有一份工作 class,在 Javascript 中定义如下:

var Job = function() {};
module.exports = Job;

然后我使用它的原型定义了一个成员函数。这工作正常,直到我尝试使用数据库中的值来设置成员变量:

// Create from an existing job ID
Job.prototype.createFromID = function( inID, callback ) {

    // Start by making sure we're invalid 
    this.id = "";

    // Connect to database
    var db = MongoClient.connect('mongodb://localhost:27017/nodepurple', function( err, db ) {
        if (err) { return false; }

        // Find the job document we're interested in
        db.collection('jobs').find({ jobID: inID }).limit( 1 ).toArray( function( err, theJobs ) {
            if (theJobs.length == 1) {
                this.id = theJobs[0].jobID;

                // Close the database
                db.close();

                callback( (this.id != ""), this );
            }
        }); // Find
    }); // Connect
}

这个函数的目的是:

这行不通。我想我明白为什么它不起作用,当这些 MongoDB 回调 return 时,我假设我不再处于正确的上下文中来完成这项工作,但我很难看到如何解决这个问题。

那么,我如何获取值 MongoDB 返回给我的 jobID 并使用它来填充我正在处理的特定作业实例中的 "id" 成员变量?

是的,你是对的,在回调中 this 不再引用 Job 对象。要解决这个问题,您有几个选择。

1) 保留对 Job 对象的引用以在回调中使用以设置 id

Job.prototype.createFromID = function( inID, callback ) {

    this.id = "";
    var self = this;

    var db = MongoClient.connect('mongodb://localhost:27017/nodepurple', function( err, db ) {
        if (err) { 
            return false; 
        }
        db.collection('jobs').find({ jobID: inID }).limit( 1 ).toArray( function( err, theJobs ) {
            if (theJobs.length == 1) {
                self.id = theJobs[0].jobID;
                db.close();
                callback( (self.id != ""), self );
            }
        }); 
    }); 
}

2) 绑定Job对象到回调函数

Job.prototype.createFromID = function( inID, callback ) {

    this.id = "";
    var mongoCallback2 = function(err, theJobs) {
        if (theJobs.length == 1) {
            this.id = theJobs[0].jobID;
            db.close();
            callback((this.id != ""), this);
        }
    }
    var mongoCallback1 = function(err, db) {
        if (err) { return false; }
        db.collection('jobs').find({jobID: inID}).limit(1).toArray(mongoCallback2.bind(this)); 
    }); 

    var db = MongoClient.connect('mongodb://localhost:27017/nodepurple', mongoCallback1.bind(this));
}

3) 使用箭头函数。箭头函数不改变上下文。

Job.prototype.createFromID = function( inID, callback ) {

    this.id = "";

    var db = MongoClient.connect('mongodb://localhost:27017/nodepurple', (err, db) => {
        if (err) { 
            return false; 
        }
        db.collection('jobs').find({jobID: inID}).limit( 1 ).toArray((err, theJobs) => {
            if (theJobs.length == 1) {
                self.id = theJobs[0].jobID;
                db.close();
                callback((this.id != ""), this);
            }
        }); 
    }); 
}

并非所有浏览器或所有浏览器版本都支持箭头函数,但有一些工具可以将您的代码转换为适用于更广泛的浏览器和浏览器版本。