2012-09-10 28 views
8

Creación de mi primer proyecto "serio" Node.js (usando Express).Patrón de llamadas asíncronas a API en Node.js

Necesito usar varias llamadas a varias API REST, recopilar todos los resultados, darles masajes y devolverle un JSON completo al cliente (HTML5 + AJAX).

  1. API Call A
  2. API Call B
  3. llamada a la API A de nuevo (con los resultados de B)
  4. resultados proceso desde el 3 llamadas en una JSON
  5. response.send (resultado)

Estoy seguro/esperando que haya un patrón fácil, una solución o un módulo que no busqué en Google correctamente :) También agradecería una opinión o n dónde colocar tales operaciones (bajo 'rutas'? ¿Archivos separados? etc.)

¡Gracias por su tiempo!

+0

esto es sólo una cuestión general de programación asíncrona. No creo que sea adecuado para stackoverflow porque hay muchas, muchas formas diferentes de abordarlo (fibras, librerías asincrónicas, manejo de eventos).Deberías simplemente usar promesas con la biblioteca de Q terriblemente nombrada pero muy útil. Esta es una respuesta obstinada, así que la dejo como un comentario. Espero ver esta pregunta cerrada AHORA. –

+5

@AndyRay Es bueno que todavía no pueda cerrar las preguntas. – Tomalak

+0

@AndyRay No hay norma para no hacer preguntas generales. Estoy buscando las mejores herramientas, ya que estoy aprendiendo mi camino sobre cómo nodo correcto. Si tiene una respuesta, déjela como una sola. Me alegraría saber más sobre cada una de las soluciones que ofreció, y es posible que obtenga algunos puntos. El cierre de una pregunta porque ya conoce la respuesta a ella late el propósito de todo este sitio :) –

Respuesta

8

El módulo async encaja en este tipo de trabajo. Específicamente, puede usar la función async.waterfall.

Ejemplo:

async.waterfall([ 
    function(callback){ 
     callback(null, 'one', 'two'); 
    }, 
    function(arg1, arg2, callback){ 
     callback(null, 'three'); 
    }, 
    function(arg1, callback){ 
     // arg1 now equals 'three' 
     callback(null, 'done'); 
    } 
], function (err, result) { 
    // result now equals 'done'  
}); 

Editar, si usted tiene algunas dependencias no triviales entre los puestos de trabajo, entonces puede usar async.auto. Determinará el mejor orden para ejecutar funciones en función de sus requisitos.

+0

+1 Estaba escribiendo la misma respuesta (me ganaste). Lo único que falta es una indicación de cómo obtener todos los resultados de 1, 2 y 3 en el paso 4. – Tomalak

+0

Parece lo que estaba buscando. Sin embargo, una pregunta: ¿podría combinar .waterfall con .parallel? Es decir. Paralelo a todas las llamadas y cascada de las que dependen el uno del otro? Tengo más de 3 llamadas, con algunas dependencias interesantes ... –

+3

@TravelingTechGuy entonces puede usar [async.auto] (https://github.com/caolan/async#auto) – qiao

2

Hay muchas bibliotecas de flujo de control. Utilicé Q en mis proyectos anteriores, lo cual no me molesta, sin embargo, es probable que investigue el uso de la biblioteca asíncrona de caolan para mi próximo proyecto.

https://github.com/caolan/async

De lo que usted ha descrito anteriormente, usted probablemente querrá buscar en el uso de la función paralela

https://github.com/caolan/async#parallel

El problema que usted describe se pueden transferir muy fácilmente hasta el paralelo ejemplo en los documentos

EDITAR: Me olvidé de que las llamadas API dependieran. Siempre que necesite pasar valores a lo largo de la cadena y controlar el orden, necesitará usar el método de cascada (vea la respuesta de qiao). Si hay un caso en el que las llamadas son independientes, usaría el método paralelo. Un ejemplo del método paralelo está por debajo

async.parallel({ 
    google: function(callback){ 
     http.get("http://www.google.com", function(res){ 
     console.log("google done"); 
     callback(null, res.statusCode); 
     }) 
    }, 
    yahoo: function(callback){ 
     http.get("http://www.yahoo.com", function(res){ 
     console.log("yahoo done"); 
     callback(null, res.statusCode); 
     })  
    } 
    }, 
    function(err, results) { 
    if(!err){ 
     console.log("all done"); 
     console.log(results.google); 
     console.log(results.yahoo); 
    }else{ 
     console.log(err); 
    } 
    } 
); 

Lo que esto hace es hace todas sus peticiones en paralelo y le da una devolución de llamada cuando se puede hacer todo. Aquí es donde debes masajear tus datos.

Lista de bibliotecas de control de flujo:

https://github.com/joyent/node/wiki/Modules#wiki-async-flow

+1

'paralelo()' no funcionará porque a) no ejecutará los pasos en una secuencia definida y b) no hay manera de pasar a lo largo de un resultado de una función a la siguiente. – Tomalak

+0

Gracias, lo perdí. Editado mi respuesta – wdavo

+0

No se trata solo de la orden. También se trata de pasar los resultados de un paso a otro. 'parallel()' simplemente no es correcto para eso. – Tomalak

Cuestiones relacionadas