¿Para qué se usa el parámetro “siguiente” en Express?

Supongamos que tiene un bloque simple de código como este:

app.get('/', function(req, res){ res.send('Hello World'); }); 

Esta función tiene dos parámetros, req y res , que representan los objetos de solicitud y respuesta, respectivamente.

Por otro lado, hay otras funciones con un tercer parámetro llamado next . Por ejemplo, echemos un vistazo al siguiente código:

 app.get('/users/:id?', function(req, res, next){ // Why do we need next? var id = req.params.id; if (id) { // do something } else { next(); // What is this doing? } }); 

No puedo entender cuál es el punto de next() o por qué se usa. En ese ejemplo, si la identificación no existe, ¿qué sigue haciendo en realidad?

Pasa el control a la siguiente ruta coincidente . En el ejemplo que das, por ejemplo, puedes buscar al usuario en la base de datos si se le dio una id y asignarla a req.user .

A continuación, puede tener una ruta como:

 app.get('/users', function(req, res) { // check for and maybe do something with req.user }); 

Dado que / users / 123 coincidirá primero con la ruta en su ejemplo, eso primero comprobará y encontrará al usuario 123 ; entonces /users pueden hacer algo con el resultado de eso.

El middleware de ruta (nota: el enlace es a la documentación 2.x, pero esto se ha probado ya que funciona en 3.x) es una herramienta más flexible y poderosa, sin embargo, en mi opinión, ya que no depende de un esquema de URI particular o orden de ruta Me inclinaría a modelar el ejemplo que se muestra así, asumiendo un modelo de Users con un findOne() asincrónico findOne() :

 function loadUser(req, res, next) { if (req.params.userId) { Users.findOne({ id: req.params.userId }, function(err, user) { if (err) { next(new Error("Couldn't find user: " + err)); return; } req.user = user; next(); }); } else { next(); } } // ... app.get('/user/:userId', loadUser, function(req, res) { // do something with req.user }); app.get('/users/:userId?', loadUser, function(req, res) { // if req.user was set, it's because userId was specified (and we found the user). }); // Pretend there's a "loadItem()" which operates similarly, but with itemId. app.get('/item/:itemId/addTo/:userId', loadItem, loadUser, function(req, res) { req.user.items.append(req.item.name); }); 

Ser capaz de controlar el flujo de esta manera es bastante útil. Es posible que desee que ciertas páginas solo estén disponibles para los usuarios con un indicador de administrador:

 /** * Only allows the page to be accessed if the user is an admin. * Requires use of `loadUser` middleware. */ function requireAdmin(req, res, next) { if (!req.user || !req.user.admin) { next(new Error("Permission denied.")); return; } next(); } app.get('/top/secret', loadUser, requireAdmin, function(req, res) { res.send('blahblahblah'); }); 

Espero que esto te haya dado algo de inspiración!

También tuve problemas para comprender el siguiente (), pero esto ayudó

 var app = require("express")(); app.get("/", function(httpRequest, httpResponse, next){ httpResponse.write("Hello"); next(); //remove this and see what happens }); app.get("/", function(httpRequest, httpResponse, next){ httpResponse.write(" World !!!"); httpResponse.end(); }); app.listen(8080); 

Antes de comprender el next , debe tener una pequeña idea del ciclo solicitud-respuesta en el nodo, aunque no mucho en detalle. Comienza cuando haces una solicitud HTTP para un recurso en particular y finaliza cuando le envías una respuesta al usuario, es decir, cuando encuentras algo como res.send (‘Hola mundo’);

echemos un vistazo a un ejemplo muy simple.

 app.get('/hello', function (req, res, next) { res.send('USER') }) 

Aquí no necesitamos next (), porque resp.send terminará el ciclo y devolverá el control al middleware de la ruta.

Ahora echemos un vistazo a otro ejemplo.

 app.get('/hello', function (req, res, next) { res.send("Hello World !!!!"); }); app.get('/hello', function (req, res, next) { res.send("Hello Planet !!!!"); }); 

Aquí tenemos 2 funciones de middleware para la misma ruta. Pero siempre recibirás la respuesta del primero. Porque eso se monta primero en la stack de middleware y res.send terminará el ciclo.

Pero, ¿y si no queremos que vuelva la respuesta “Hello World !!!!”? Para algunas condiciones, podemos querer el “¡Hola planeta!” respuesta. Modifiquemos el código anterior y veamos qué sucede.

 app.get('/hello', function (req, res, next) { if(some condition){ next(); return; } res.send("Hello World !!!!"); }); app.get('/hello', function (req, res, next) { res.send("Hello Planet !!!!"); }); 

¿Qué next haciendo aquí? Y sí, podrías tener gusses. Va a omitir la primera función de middleware si la condición es verdadera e invocar la siguiente función de middleware y tendrá el "Hello Planet !!!!" respuesta.

Entonces, pasa el control a la siguiente función en la stack de middleware.

¿Qué ocurre si la primera función de middleware no envía ninguna respuesta sino que ejecuta una lógica y luego obtiene la respuesta de la segunda función de middleware?

Algo como a continuación: –

 app.get('/hello', function (req, res, next) { // Your piece of logic next(); }); app.get('/hello', function (req, res, next) { res.send("Hello !!!!"); }); 

En este caso, necesita invocar ambas funciones de middleware. Entonces, la única manera de llegar a la segunda función de middleware es llamando a next ();

¿Qué pasa si no haces una llamada al siguiente? No espere que la segunda función de middleware se invoque automáticamente. Después de invocar la primera función, su solicitud quedará pendiente. La segunda función nunca será invocada y no obtendrá la respuesta.

A continuación se usa para pasar el control a la siguiente función de middleware. Si no, la solicitud se dejará pendiente o abierta.

Llamar a esta función invoca la siguiente función de middleware en la aplicación. La función next () no forma parte de la API Node.js o Express, pero es el tercer argumento que se pasa a la función de middleware. La función next () podría llamarse cualquier cosa, pero por convención siempre se llama “next”.