等待异步任务完成

时间:2022-09-02 02:20:13

I'm interacting with a third-party JavaScript library where some function calls are asynchronous. Instead of working the asynchronous logic into my application, I preferred to write synchronous wrappers to those async calls. I know, I know, it's terrible design, but this is a demo project with very high chance of being rewritten entirely. I need something to show the team the concept, not really having to worry performance, yet.

我正在与一个第三方JavaScript库进行交互,其中一些函数调用是异步的。与其将异步逻辑应用到我的应用程序中,我更喜欢将同步包装器写入那些异步调用。我知道,我知道,这是一个糟糕的设计,但这是一个演示项目,很有可能被完全重写。我需要一些东西向团队展示这个概念,而不是担心性能。

Here's what I wanna do:

我想做的是:

function sync_call(input) {
    var value;

    // Assume the async call always succeed
    async_call(input, function(result) {value = result;} );

    return value;
}

I tried the jQuery's deferred and promise but it seems to be aiming at the async design pattern. I want to use the synchronous pattern in my code.

我尝试了jQuery的deferred and promise,但它似乎是针对异步设计模式的。我想在代码中使用同步模式。

2 个解决方案

#1


27  

This will never work, because the JS VM has moved on from that async_call and returned the value, which you haven't set yet.

这将永远不会工作,因为JS VM已经从异步调用转移到返回值,而您还没有设置这个值。

Don't try to fight what is natural and built-in the language behaviour. You should use a callback technique or a promise.

不要试图与语言行为中自然和固有的东西作斗争。您应该使用回调技术或承诺。

function f(input, callback) {
    var value;

    // Assume the async call always succeed
    async_call(input, function(result) { callback(result) };

}

The other option is to use a promise, have a look at Q. This way you return a promise, and then you attach a then listener to it, which is basically the same as a callback. When the promise resolves, the then will trigger.

另一种选择是使用一个承诺,看一下q,这样你返回一个承诺,然后你给它附加一个监听器,这基本上和回调是一样的。当承诺解决时,它就会触发。

#2


0  

How about calling a function from within your callback instead of returning a value in sync_call()?

在回调中调用一个函数而不是在sync_call()中返回一个值,怎么样?

function sync_call(input) {
    var value;

    // Assume the async call always succeed
    async_call(input, function(result) {
        value = result;
        use_value(value);
    } );
}

#1


27  

This will never work, because the JS VM has moved on from that async_call and returned the value, which you haven't set yet.

这将永远不会工作,因为JS VM已经从异步调用转移到返回值,而您还没有设置这个值。

Don't try to fight what is natural and built-in the language behaviour. You should use a callback technique or a promise.

不要试图与语言行为中自然和固有的东西作斗争。您应该使用回调技术或承诺。

function f(input, callback) {
    var value;

    // Assume the async call always succeed
    async_call(input, function(result) { callback(result) };

}

The other option is to use a promise, have a look at Q. This way you return a promise, and then you attach a then listener to it, which is basically the same as a callback. When the promise resolves, the then will trigger.

另一种选择是使用一个承诺,看一下q,这样你返回一个承诺,然后你给它附加一个监听器,这基本上和回调是一样的。当承诺解决时,它就会触发。

#2


0  

How about calling a function from within your callback instead of returning a value in sync_call()?

在回调中调用一个函数而不是在sync_call()中返回一个值,怎么样?

function sync_call(input) {
    var value;

    // Assume the async call always succeed
    async_call(input, function(result) {
        value = result;
        use_value(value);
    } );
}