When to use next() and return next() in Node.js
Scenario: Consider the following is the part of code from a node web app.
app.get('/users/:id?', function(req, res, next){
var id = req.params.id;
if (id) {
// do something
} else {
next(); //or return next();
}
});
Issue: I am checking which one to go with just next()
or return next()
. Above sample code works exactly the same for both & did not show any difference in execution.
Question: Can some one put light on this, when to use next()
and when to use return next()
and some important difference?
Solution 1:
As @Laurent Perrin's answer:
If you don't do it, you risk triggering the callback a second time later, which usually has devastating results
I give an example here if you write middleware like this:
app.use((req, res, next) => {
console.log('This is a middleware')
next()
console.log('This is first-half middleware')
})
app.use((req, res, next) => {
console.log('This is second middleware')
next()
})
app.use((req, res, next) => {
console.log('This is third middleware')
next()
})
You will find out that the output in console is:
This is a middleware
This is second middleware
This is third middleware
This is first-half middleware
That is, it runs the code below next() after all middleware function finished.
However, if you use return next()
, it will jump out the callback immediately and the code below return next()
in the callback will be unreachable.
Solution 2:
Some people always write return next()
is to ensure that the execution stops after triggering the callback.
If you don't do it, you risk triggering the callback a second time later, which usually has devastating results. Your code is fine as it is, but I would rewrite it as:
app.get('/users/:id?', function(req, res, next){
var id = req.params.id;
if(!id)
return next();
// do something
});
It saves me an indentation level, and when I read the code again later, I'm sure there is no way next
is called twice.
Solution 3:
next()
is part of connect middleware. Callbacks for router flow doesn't care if you return anything from your functions, so return next()
and next(); return;
is basically the same.
In case you want to stop the flow of functions you can use next(err)
like the following
app.get('/user/:id?',
function(req, res, next) {
console.log('function one');
if ( !req.params.id )
next('No ID'); // This will return error
else
next(); // This will continue to function 2
},
function(req, res) {
console.log('function two');
}
);
Pretty much next()
is used for extending the middleware of your requests.
Solution 4:
The difference between next() and return next() is very simple as another programming principle. Some lines of code are explain below:
app.use((req, res, next) => {
console.log('Calling first middleware');
next();
console.log('Calling after the next() function');
});
app.use((req, res, next) => {
console.log('Calling second middleware');
return next(); // It returns the function block immediately and call next() function so the return next(); and next(); return; are the same
console.log('After calling return next()');
});
Output is
Calling first middleware
Calling after the next() function
Calling second middleware