3

我正在为Node.js的异步流程而苦苦挣扎。假设您有以下课程:

function myClass() {
  var property = 'something';
  var hasConnected = false;

  this.connect = function(params) {
    //Some logic that connects to db and in callback returns if the connection is successful
    connectToSomeDB('ConnectionString', function(connectionResult) {
      hasConnected = connectionResult
    })
  };

  this.get = function(params) {
    if(hasConnected) {
      DoGetOperation() //
    }
    else {
      //Another question. What should be done here. Call the connect again?
    }
  }
}

考虑到 Javascript 和 Node 结构,我当然相信我的设计存在一些重大问题,但我无法找到解决办法,因为connect 必须调用才能使任何操作正常工作。但是当我在操作后进行一些日志记录时:

brandNewObject = myClass();
brandNewObject.connect();
brandNewObject.get();

isConnected我观察到在获取全局变量之前调用了 get 函数。在不违背 Node 的异步结构的情况下,我能做些什么来完成这项工作?

理想情况下,我正在寻找的解决方案实际上是在内部处理“连接”而不是定义回调“外部类”

4

3 回答 3

1

你必须使用回调。

function myClass() {
  var property = 'something';
  var hasConnected = false;

  // added second parameter
  this.connect = function(params, callback) {
    //Some logic that connects to db and in callback returns if the connection is successful
    connectToSomeDB('ConnectionString', function(connectionResult) {
      hasConnected = connectionResult;
      // Now call the callback!
      callback();
    })
  };

  this.get = function(params) {
    if(hasConnected) {
      DoGetOperation() //
    }
    else {
      //Another question. What should be done here. Call the connect again?
    }
  }
}
brandNewObject = myClass();
brandNewObject.connect({}, function () {
  // this function gets called after a connection is established
  brandNewObject.get();
});
于 2013-01-16T10:08:04.197 回答
1

将回调参数添加到您的connect方法。

  this.connect = function(params, callback) {
    //Some logic that connects to db and in callback returns if the connection is successful
    connectToSomeDB('ConnectionString', function(connectionResult) {
      hasConnected = connectionResult;

      // Call the callback provided
      callback(params);
    })
  };

然后你可以这样称呼它:

brandNewObject = myClass();
brandNewObject.connect({}, function(/* optionally, "params" */) {
    brandNewObject.get();
});
于 2013-01-16T10:08:24.197 回答
1

对此有不同的解决方法。

一种简单的方法类似于您正在做的事情

this.get = function(params) {
    if (hasConnected) {
        DoGetOperation(params);
    } else {
        //here you can check the status of the connect. if it is still in 
        //progress do nothing. if the connection has failed for some reason
        //you can retry it. Otherwise send a response back indicating that the
        //operation is in progress.
    }
}

另一种方法可能是为您的 get 函数使用相同的异步回调机制,这会将您的方法签名更改为类似的内容。

this.deferredOperations = new Array();

this.get = function(params, callback) {
    if (hasConnected) {
       //using a callback as an optional parameter makes the least 
       //impact on your current function signature. 
       //If a callback is present send the data back through it, 
       //otherwise this function simply returns the value (acts synchronously).
       if (callback !== null) {
         callback(DoGetOperation(params));
       } else {
         return DoGetOperation(params);
       }
    } else {
       this.deferredOperations.push([params,callback]);
    }
}

//connect changes now
this.connect = function(params) {
//Some logic that connects to db and in callback returns if the connection is successful
connectToSomeDB('ConnectionString', function(connectionResult) {
  hasConnected = connectionResult;
  if (hasConnected && this.deferredOperations.length > 0) {
    for (var i=0; i < this.deferredOperations.length; i++) {
      var paramFunction = this.deferredOperations.pop();
      var params = paramFunction[0];
      var func = paramFunction[1];
      DoAsyncGetOperation(params, func); //Need to write a new function that accepts a callback
    }
  }
})
};

高温高压

于 2013-01-16T10:20:56.480 回答