next-auth: Infinite redirect with middleware and basePath

Question 💬

I have a NextJS app setup to run under the /admin basepath. Whenever I use the middleware, I am having problems with it sending me to the wrong url for the login page. If I try passing a custom sign in page to the options, it redirects me infinitely. Can anyone point me in the right direction? Is this even possible?

How to reproduce ☕️

I am running next-auth@4.3.1, next@12.1.0

_app.js

import { SessionProvider } from 'next-auth/react';
import '../styles/globals.css';

function App({ Component, pageProps: { session, ...pageProps } }) {
  return (
    <SessionProvider
      session={session}
      basePath="/admin/api/auth"
    >
      <Component {...pageProps} session={session} />
    </SessionProvider>
  );
}

export default App;

_middleware.js

Note that without the custom signin page, the app redirects me to /api/auth/signin which does not exists (I can see the page if I manually go to /admin/api/auth/signin) and with the custom signin page I get an infinite redirect error.

import withAuth from 'next-auth/middleware';

export default withAuth({
  pages: {
    signIn: '/admin/signin',
  },
});

next.config.js

/** @type {import('next').NextConfig} */

const nextConfig = {
  reactStrictMode: true,
  env: {
    COGNITO_CLIENT_ID: '<removed>',
    COGNITO_CLIENT_SECRET: '<removed>',
    COGNITO_ISSUER: '<removed>',
    COGNITO_DOMAIN: '<removed>',
    NEXTAUTH_URL: 'http://localhost:3000/admin/api/auth',
    NEXTAUTH_SECRET: '<removed>',
  },
  basePath: '/admin',
};

module.exports = nextConfig;

pages/signin.js

import { Button } from '@mantine/core';
import { signIn } from 'next-auth/react';

export default function SignIn({ providers }) {
  return (
    <Button onClick={() => signIn('cognito')}>
      Sign in with Cognito
    </Button>
  );
}

pages/api/auth

import NextAuth from 'next-auth/next';
import CognitoProvider from 'next-auth/providers/cognito';

export default NextAuth({
  providers: [
    CognitoProvider({
      clientId: process.env.COGNITO_CLIENT_ID,
      clientSecret: process.env.COGNITO_CLIENT_SECRET,
      issuer: process.env.COGNITO_ISSUER,
      domain: process.env.COGNITO_DOMAIN,
    }),
  ],
  secret: process.env.NEXTAUTH_SECRET,
  debug: true,
});

Contributing 🙌🏽

No, I am afraid I cannot help regarding this

About this issue

  • Original URL
  • State: closed
  • Created 2 years ago
  • Reactions: 3
  • Comments: 26 (4 by maintainers)

Commits related to this issue

Most upvoted comments

I have the same issue by just using export { default } from "next-auth/middleware" in my middleware.

@nicks6853 thanks for reaching out. So this should theoretically be possible. I was successfully able to recreate and reproduce your infinite refresh / forwarding problem.

I think I’ve boiled it down to packages/next-auth/src/next/middleware.ts:L65-L68 - this check isn’t being hit and so its not early returning. Therefore its continuing on until a few lines further down it appends another copy of the callbackUrl query param and redirect’s to the signInUrl over and over again…

Unfortunately I haven’t been abel to get any further tonight. I’ll take another look at this tomorrow 👍

Currently, on next@13.1.1 and next-auth@4.18.8, I am having this issue as well using only export { default } from "next-auth/middleware", it makes my app break, and it gets into a cycle of “localhost redirected you too many times” error.

Using the matcher config for example export const config = { matcher: ["/dashboard"] }, makes it semi work, I can go to / with no issue since it wasn’t defined but going to the /dashboard directory with a successful login brings me back to the sign-in page, upon inspecting the console I can see a lot of re-renders, it seems it redirects it infinitely even when on the sign-in page.

any update on this?

I’m explicitly using “JWT” as the session strategy but facing the same infinite redirection issue. Is there any known workaround for this issue? I’m on the brink of abandoning the middleware to try another approach.

I’m using an auth0 provider, My current versions are:

"next": "13.1.6",
"next-auth": "^4.19.2",

I have the same issue, i’m using latest next and next-auth modules and then just write export { default } from “next-auth/middleware” in my middleware file 😦

I faced the same issue. Overriding the session strategy to “jwt” in the authOptions solved the issue.

When can we expect this to work? I’ve stumbled on the same issue.

I have the same issue, i’m using latest next and next-auth modules and then just write export { default } from “next-auth/middleware” in my middleware file 😦

I faced the same issue. Overriding the session strategy to “jwt” in the authOptions solved the issue.

This solved my issue (I think I glanced over with the explicit mention that JWT needs to be enabled for this to work (I understood its just withAuth.

I have created a PR on the docs to be more explicit that this should be added.

Same as @AbrahamX3. Any workarounds so far?

@nicks6853 I just realized (thanks to @ThangHuuVu in #4366) that you also have to pass the callbackUrl as a param to the signin() function in the custom login page.

i.e.

pages/signin.js

import { Button } from '@mantine/core';
import { signIn } from 'next-auth/react';
import { useRouter } from 'next';

export default function SignIn({ providers }) {
  const { callbackUrl }  = useRouter().query
  return (
    <div className='max-w-2xl mx-auto'>
      <div className='flex items-center justify-center px-8 py-8 mt-4 rounded bg-content bg-base-200'>
        {Object.values(providers).map((provider) => (
          <div key={provider.name}>
            <button className='btn' onClick={() => signIn(provider.id, { callbackUrl })}>
              Sign in with {provider.name}
            </button>
          </div>
        ))}
      </div>
    </div>
  );
}

I wasn’t able to test it, but I see we weren’t doing that in your login example so maybe this will help 👍