18

Why do we do this

router.get('/data', async (ctx, next) => {
  ctx.body = dummyjson.parse(data);
  await next();
});

router.get('/data/:x', async (ctx, next) => {
  const newData = dataRepeat.replace('%(x)', ctx.params.x);
  ctx.body = dummyjson.parse(newData);
  await next();
});

What is the use of await next()

It would work just fine without that. Similar thing was expected with koa 1. yield next was added at the end of the router.

relidon
  • 2,142
  • 4
  • 21
  • 37
  • 1
    [This answer](http://stackoverflow.com/questions/10695629/what-is-the-parameter-next-used-for-in-express) is for Express, not Koa but its basically the same reasoning. – Saad Mar 02 '17 at 09:49
  • You need to read on how Koa utilized Generators and Iterators to achieve this - Cascading in Koa. as explained by @Sebastian Hildebrandt, Koa does this by yielding downstream and then flowing the control back upstream – Abhay Shiro Nov 27 '20 at 17:41

2 Answers2

24

I'll try to explain it using a very simple example:

const Koa = require('koa');
const app = new Koa();

// middleware
app.use(async function (ctx, next) {
    console.log(1)
    await next();
    console.log(3)
});

// response
app.use(ctx => {
    console.log(2)
});

app.listen(3000);

If you call localhost:3000 in your browser, the following will happen in your app:

  • The first app.use that you fired here was the middleware. So the request flow goes into that one first, logs 1to the console.
  • Then, when you see this await next(), it downstreams to the next use.
  • Here we just log 2 to the console. When this is finished (and no further await next is seen in the second use) the flow goes back to the first one which actually waited till the second one was finished.
  • Here we then continue with logging 3 to the console.

Hope this makes it a little more clear.

cmur2
  • 2,614
  • 1
  • 20
  • 23
Sebastian Hildebrandt
  • 2,661
  • 1
  • 14
  • 20
  • Just to clarify, if you **didn't** use `await`, `console.log(3)` would be executed _synchronously_, so it would be unpredictable... So it might run before `console.log(2)`, or it might run after... It just depends how long `console.log(2)` takes to run. – Jack_Hu Sep 11 '21 at 17:43
3

No, It is not necessary. It is depend on your requirement. you use next() function when you call next middleware.

Check your router module and its version. I have use koa-router module and its version is 7.2.0 for routing. It self handle await next.

'use strict';

const Koa = require('koa'),
    router = require('koa-router'),
    app = new Koa();

let pubRouter = new router();
let securedRouter = new router();

let mapper = require('./mapper'),

// assign router to corresponding function
mapper(pubRouter, securedRouter);

app .use(logger(config.app.log))    
.use(bodyParser())
.use(pubRouter.routes()).use(pubRouter.allowedMethods())
    .use(jwt({
        secret: publicKey,
        algorithms: ['RS256']
    }))
    .use(async(ctx, next) => {
        console.log('\n\n\n\n\n', ctx.state.user);
        await next();
    })
    .use(securedRouter.routes()).use(securedRouter.allowedMethods())
    .use(async(ctx, next) => {
        ctx.body = 'Invalid URL!!!';
    });

app.listen(port, () => console.log(`Server listening on port: ${port}`));
Rishabh
  • 185
  • 1
  • 13