¿Cómo hago que una función espere hasta que todas las solicitudes de jQuery Ajax se realicen dentro de otra función?
En resumen, necesito esperar a que se realicen todas las solicitudes de Ajax antes de ejecutar la siguiente. ¿Pero cómo?
javascript
jquery
ajax
jamietelin
fuente
fuente
Respuestas:
jQuery ahora define una función when para este propósito.
Acepta cualquier cantidad de objetos diferidos como argumentos y ejecuta una función cuando todos se resuelven.
Eso significa que, si desea iniciar (por ejemplo) cuatro solicitudes de ajax, luego realizar una acción cuando terminen, podría hacer algo como esto:
En mi opinión, crea una sintaxis limpia y clara, y evita la participación de variables globales como ajaxStart y ajaxStop, que podrían tener efectos secundarios no deseados a medida que se desarrolla su página.
Si no sabe de antemano cuántos argumentos de ajax necesita esperar (es decir, si desea usar un número variable de argumentos), aún puede hacerse, pero es un poco más complicado. Consulte Pasar en una matriz de diferidos a $ .when () (y tal vez jQuery. Al solucionar problemas con un número variable de argumentos ).
Si necesita un control más profundo sobre los modos de falla de los scripts ajax, etc., puede guardar el objeto devuelto por
.when()
: es un objeto jQuery Promise que abarca todas las consultas ajax originales. Puede invocarlo.then()
o.fail()
agregarlo para agregar controladores detallados de éxito / falla.fuente
$.when
devuelve unPromise
objeto que tiene métodos más útiles, no solo.done
. Por ejemplo, con el.then(onSuccess, onFailure)
método podría reaccionar cuando ambas solicitudes tengan éxito o al menos una de ellas falle.fail
caso. A diferenciadone
,fail
dispara inmediatamente en el primer fallo e ignora los aplazamientos restantes.onFailure
se puede adjuntar una función. Como señalé en un comentario a la pregunta del OP: podría querer indicar con mayor precisión lo que quería decir con "hecho". "Ryan Mohr" también tuvo un muy buen punto con respecto al hecho de que sefail
comporta de manera diferentedone
, yaPromises
que creo que hay que leer más sobre html5rocks.com/en/tutorials/es6/promisesSi desea saber cuándo
ajax
finalizan todas las solicitudes en su documento, no importa cuántas existan, simplemente use el evento $ .ajaxStop de esta manera:Actualización:
si desea seguir con la
ES
sintaxis, puede usar Promise.all paraajax
métodos conocidos :Un punto interesante aquí es que funciona con
Promises
y con$.ajax
solicitudes.Aquí está la demostración de jsFiddle .
Actualización 2:
Sin embargo, una versión más reciente que utiliza la sintaxis async / await :
fuente
He encontrado una buena respuesta por gnarf mi mismo que es exactamente lo que estaba buscando :)
jQuery ajaxQueue
Luego puede agregar una solicitud ajax a la cola de esta manera:
fuente
Usa el
ajaxStop
evento.Por ejemplo, supongamos que tiene un mensaje de carga ... mientras recupera 100 solicitudes ajax y desea ocultar ese mensaje una vez cargado.
Del documento jQuery :
Tenga en cuenta que esperará a que se realicen todas las solicitudes de ajax en esa página.
fuente
NOTA: Las respuestas anteriores utilizan una funcionalidad que no existía en el momento en que se escribió esta respuesta. Recomiendo usar en
jQuery.when()
lugar de estos enfoques, pero estoy dejando la respuesta con fines históricos.-
Probablemente podría sobrevivir con un simple semáforo de conteo, aunque la forma en que lo implemente dependerá de su código. Un ejemplo simple sería algo así como ...
Si desea que esto funcione como {async: false} pero no desea bloquear el navegador, puede lograr lo mismo con una cola jQuery.
fuente
.get()
. De esa manera al menos no duplicas ese código. ¡No solo eso, sino que declarando afunction(){}
cada vez asigna memoria cada vez! Más bien una mala práctica si pudieras llamar a una función estáticamente definida.JavaScript está basado en eventos, por lo que nunca debe esperar , en lugar de establecer ganchos / devoluciones de llamada
Probablemente solo pueda usar los métodos de éxito / completo de jquery.ajax
O podría usar .ajaxComplete :
aunque debe publicar un pseudocódigo de cómo se llama (s) su (s) solicitud (es) ajax para ser más precisos ...
fuente
Una pequeña solución es algo como esto:
La esperanza puede ser útil ...
fuente
jQuery le permite especificar si desea que la solicitud ajax sea asíncrona o no. Simplemente puede hacer que las solicitudes ajax sean síncronas y luego el resto del código no se ejecutará hasta que regresen.
Por ejemplo:
fuente
Si necesitas algo simple; devolución de llamada una vez y hecho
fuente
También podría usar async.js .
Creo que es mejor que $ .when porque puedes combinar todo tipo de llamadas asincrónicas que no admiten promesas listas para usar, como tiempos de espera, llamadas SqlLite, etc., y no solo solicitudes ajax.
fuente
Sobre la base de la respuesta @BBonifield, escribí una función de utilidad para que la lógica del semáforo no se extienda en todas las llamadas ajax.
untilAjax
es la función de utilidad que invoca una función de devolución de llamada cuando se completan todas las llamadas ajax.ajaxObjs
es una matriz de objetos de configuración ajax[http://api.jquery.com/jQuery.ajax/]
.fn
es la función de devolución de llamadaEjemplo:
doSomething
usos de funcionesuntilAjax
.fuente
Le recomiendo usar $ .when () si está comenzando desde cero.
Aunque esta pregunta tiene más de un millón de respuestas, todavía no encontré nada útil para mi caso. Supongamos que tiene que lidiar con una base de código existente, que ya realiza algunas llamadas ajax y no quiere introducir la complejidad de las promesas y / o rehacer todo.
Podemos tomar ventaja de jQuery
.data
,.on
y.trigger
las funciones que han sido una parte de jQuery desde siempre.Codepen
Lo bueno de mi solución es:
es obvio de qué depende exactamente la devolución de llamada
a la función
triggerNowOrOnLoaded
no le importa si los datos ya se han cargado o si todavía estamos esperando por elloses muy fácil conectarlo a un código existente
fuente
Estoy usando la verificación de tamaño cuando se completa toda la carga ajax
fuente
Para ampliar la respuesta de Alex, tengo un ejemplo con argumentos y promesas variables. Quería cargar imágenes a través de ajax y mostrarlas en la página después de que se hayan cargado todas.
Para hacer eso, utilicé lo siguiente:
Actualizado para funcionar para urls individuales o múltiples: https://jsfiddle.net/euypj5w9/
fuente
Como se mencionó en otras respuestas, puede usar
ajaxStop()
para esperar hasta que se completen todas las solicitudes de ajax.Si desea hacerlo para una
ajax()
solicitud específica, lo mejor que puede hacer es utilizar elcomplete()
método dentro de la solicitud ajax determinada:Pero, ¿ si necesita esperar solo unas pocas y ciertas solicitudes de ajax? Use las maravillosas promesas de JavaScript para esperar hasta que estos ajax que desea esperar estén listos. Hice un ejemplo breve, fácil y legible para mostrarle cómo funciona promesas con ajax.
Por favor, eche un vistazo al siguiente ejemplo . Solía
setTimeout
aclarar el ejemplo.fuente
Encontré manera simple, usando
shift()
fuente
Mi solución es la siguiente
Funcionó bastante bien. He intentado muchas formas diferentes de hacerlo, pero descubrí que es la más simple y reutilizable. Espero eso ayude
fuente
Mira mi solución:
1.Inserte esta función (y variable) en su archivo javascript:
2. Construya una matriz con sus solicitudes, como esta:
3.Cree la función de devolución de llamada:
4. Llame a la función runFunctionQueue con parámetros:
fuente
$.when
no funciona para mí, encallback(x)
lugar dereturn x
funcionar como se describe aquí: https://stackoverflow.com/a/13455253/10357604fuente
Intenta de esta manera. haga un bucle dentro de la función de script java para esperar hasta que finalice la llamada ajax.
fuente
setTimeout()
NOtake a sleep
. En este caso, simplemente bloquea todas las pestañas hasta que sedone
haga realidad.done
eso nunca será cierto mientras el ciclo while todavía se esté ejecutando. Si el ciclo while se está ejecutando, el ciclo de eventos no puede continuar y, por lo tanto, nunca ejecutará la devolución de llamada para el éxito de ajax.