如何处理许多异步回调的完成

时间:2022-05-20 19:07:20

I have a local WebSQL db that I need to sync with a remote MySQL server. To do so, I have split the process into multiple requests, so I can fire the callback in between every request to show the progress.

我有一个本地WebSQL数据库,我需要与远程MySQL服务器同步。为此,我将进程拆分为多个请求,因此我可以在每个请求之间触发回调以显示进度。

The problem is that I have serious race conditions here that I don't think I can solve with the callbacks, because the insert statements are within a $.each() function (aka for loop).

问题是我在这里有严重的竞争条件,我认为我不能用回调来解决,因为insert语句在$ .each()函数内(也就是循环)。

I have this asynchronous problem spread all over the database interface. I have been investigating how to use promises and Deferred in jQuery, but that doesn't seem to solve the problem. I just need to make this thing synchronous.

我有这个异步问题遍布数据库接口。我一直在研究如何在jQuery中使用promises和Deferred,但这似乎并没有解决问题。我只需要让这个东西同步。

evalua.webdb.sync = function(callback){ 
$.getJSON("index.php/get/sync_riesgo",function(data){
    evalua.webdb.db.transaction(function(tx){
        $(data.riesgos).each(function(index, value){
            tx.executeSql('INSERT INTO riesgos (idRiesgo, nombre) VALUES ("'+value.idRiesgo+'", "'+value.nombre+'")');
        });
        $(data.estancias).each(function(index, value){
            tx.executeSql('INSERT INTO estancias (idEstancia, nombre, dimensionMinima) VALUES ("'+value.idEstancia+'", "'+value.nombre+'", "'+value.dimensionMinima+'")');
        });
        $(data.riesgosestancias).each(function(index, value){
            tx.executeSql('INSERT INTO riesgosestancias (idRiesgoEstancia, idRiesgo, idEstancia, porcentaje, indispensable) VALUES ("'+value.idRiesgoEstancia+'", "'+value.idRiesgo+'", "'+value.idEstancia+'", "'+value.porcentaje+'", "'+value.indispensable+'")');
        });
    });
});
    callback("First one done");
$.getJSON("index.php/get/sync_operaciones",function(data){
    evalua.webdb.db.transaction(function(tx){
        $(data.companhias).each(function(index, value){
            tx.executeSql('INSERT INTO companhias (idCompanhia, nombre) VALUES ("'+value.idCompanhia+'", "'+value.nombre+'")');
        });
        $(data.operaciones).each(function(index, value){
            tx.executeSql('INSERT INTO operaciones (idOperacion, nombre, descripcion) VALUES ("'+value.idOperacion+'", "'+value.nombre+'", "'+value.descripcion+'")');
        });
    });
});
    callback("Second one done");
}

2 个解决方案

#1


1  

jQuery ajax has a setting to make ajax requests synchronous. Very easy to do

jQuery ajax有一个让ajax请求同步的设置。很容易做到

$.ajaxSetup({'async': false});

...or just use .ajax and set this individually with each request.

...或者只使用.ajax并根据每个请求单独设置。

If you want the requests as a whole to be asynchronous but fire in order, you have to create a queue of some kind: https://gist.github.com/3818056 -- doesn't use the Deferred API, though it probably could. You would use it as follows:

如果您希望整个请求是异步但按顺序触发,则必须创建某种类型的队列:https://gist.github.com/3818056 - 不使用Deferred API,尽管它可能可以。您可以按如下方式使用它:

var aq = new AjaxQueue();
aq.push({'type': 'get', 'dataType': 'json', 'url': 'index.php/get/sync_riesgo',
   'success': "you're really long function"});
aq.push({'type': 'get', 'dataType': 'json', 'url': 'index.php/get/sync_operaciones',
   'success': "you're really long function"});

Of course, this also requires the client to continue running until the continue running until the ajax queue is empty. If available, I would suggest doing:

当然,这也要求客户端继续运行,直到继续运行,直到ajax队列为空。如果可以的话,我建议你这样做:

$(window).on('beforeunload', function () {
   if (aq.q.length) {
      return "Still doing back end processing; please stay on page for a moment";
   }
});

#2


0  

I think I may have found a solution right here:

我想我可能在这里找到了解决方案:

HTML5 WebSQL: how to know when a db transaction finishes?

HTML5 WebSQL:如何知道db事务何时完成?

I still need to know how to make different INSERT statements, and to handle the promises one after another. But that's a smaller set of chained callbacks.

我仍然需要知道如何制作不同的INSERT语句,并一个接一个地处理这些承诺。但这是一组较小的链式回调。

#1


1  

jQuery ajax has a setting to make ajax requests synchronous. Very easy to do

jQuery ajax有一个让ajax请求同步的设置。很容易做到

$.ajaxSetup({'async': false});

...or just use .ajax and set this individually with each request.

...或者只使用.ajax并根据每个请求单独设置。

If you want the requests as a whole to be asynchronous but fire in order, you have to create a queue of some kind: https://gist.github.com/3818056 -- doesn't use the Deferred API, though it probably could. You would use it as follows:

如果您希望整个请求是异步但按顺序触发,则必须创建某种类型的队列:https://gist.github.com/3818056 - 不使用Deferred API,尽管它可能可以。您可以按如下方式使用它:

var aq = new AjaxQueue();
aq.push({'type': 'get', 'dataType': 'json', 'url': 'index.php/get/sync_riesgo',
   'success': "you're really long function"});
aq.push({'type': 'get', 'dataType': 'json', 'url': 'index.php/get/sync_operaciones',
   'success': "you're really long function"});

Of course, this also requires the client to continue running until the continue running until the ajax queue is empty. If available, I would suggest doing:

当然,这也要求客户端继续运行,直到继续运行,直到ajax队列为空。如果可以的话,我建议你这样做:

$(window).on('beforeunload', function () {
   if (aq.q.length) {
      return "Still doing back end processing; please stay on page for a moment";
   }
});

#2


0  

I think I may have found a solution right here:

我想我可能在这里找到了解决方案:

HTML5 WebSQL: how to know when a db transaction finishes?

HTML5 WebSQL:如何知道db事务何时完成?

I still need to know how to make different INSERT statements, and to handle the promises one after another. But that's a smaller set of chained callbacks.

我仍然需要知道如何制作不同的INSERT语句,并一个接一个地处理这些承诺。但这是一组较小的链式回调。