Reputation: 975
I'm new to KoaJS. Playing a bit now. I'm trying to redirect all request to a particular URL using a middle-ware. This seems to product ERR_TOO_MANY_REDIRECTS
in Chrome. I tried a lot to debug. Can't get what is wrong.
index.js
// App
const Koa = require('koa')
const app = new Koa()
// Parser
const bodyParser = require('koa-body')
app.use(bodyParser())
// Session
const session = require('koa-session')
app.keys = ['asdfasdf@#$ASDf1#$@5rasdf']
app.use(session(app))
// THIS MIDDLEWARE
app.use(async (ctx, next) => {
ctx.session.user = '121' // This is all playground. No production stuff.
const s = ctx.session.user
if (s != '1213') {
ctx.redirect('/login')
}
await next()
})
// Router
const common = require('./routes')
app.use(common.routes())
// Server
app.listen(3000, () => { console.log('Listening on http://localhost:3000') })
routes.js
const Router = require('koa-router')
const router = new Router()
// const User = require('./user')
router.get('/', async ctx => {
ctx.body = 'Home Page'
})
router.get('/login', async ctx => {
ctx.body = 'Login Page'
})
module.exports = router
Upvotes: 1
Views: 3135
Reputation: 203514
Consider your middleware:
app.use(async (ctx, next) => {
ctx.session.user = '121' // This is all playground. No production stuff.
const s = ctx.session.user
if (s != '1213') {
ctx.redirect('/login')
}
await next()
})
Because s != '1213'
always evaluates to "true", ctx.redirect('/login')
is executed for every request.
This will do two things:
Location
header to /login
, telling the browser to location to redirect toConsidering that this happens for every request, you end up in a loop: a request to /
is redirected to /login
, which itself is redirected to /login
, which is also redirected to /login
, ad infinitum. At some point, the browser gives up and issues a ERR_TOO_MANY_REDIRECTS
error.
FWIW, after calling ctx.redirect()
, you typically end the request, for instance like this:
if (s != '1213') {
return ctx.redirect('/login')
}
In your case, you don't end the request, which means that it will be passed to the router.
To answer your comment, I assume you used this:
if (s != '1213') {
ctx.url = '/login';
}
You change the URL that the router will check to see which handler it should call. Sort of like an internal redirect, or a "rewrite": a request to /
is handled internally as if it were a request for /login
.
This is not something that you want though, because it may confuse the browser. The correct way is to issue a proper redirect, using ctx.redirect()
, which will make the browser change the URL in the location bar and issue a new request.
Upvotes: 2