Next.js Discord

Discord Forum

How to handle server side logins?

Answered
Minskin posted this in #help-forum
Open in Discord
Avatar
MinskinOP
Hey guys im kind of new to nextjs, and want to recreate an old project i did with vuejs in nextjs to learn it.

My current goal is to recreate the login functionality, with vuejs this was simple, because everything was shipped to the client anyways. Now with nextjs im a bit confused, because to catch the form submit i need to use a client side component, but do i also send the request from the client direclty to my backend (Ktor), or do i loop it through the nextjs server first, to save the cookies and stuff on the nextjs serve. And if so, how can i do that?
Answered by nehalist
seems like you've mixed up the route handler with the lib config; route handlers need to be exported as GET and POST. see https://nehalist.io/authentication-for-nextjs-with-nextauth-part-1/#basic-configuration at route handler section.
View full answer

46 Replies

Avatar
MinskinOP
Is it still ok to use axios for reaching out to my backend which handles my auth?
Avatar
MinskinOP
Maybe im on the wrong here but i what i wanto to achieve is kind of:


Frontend (handeled by my nextjs server)
Next js server -> Kotlin Backend
Avatar
there's a lot to unpack here. the easiest approach to adding auth to your next app is nextauth. I've recently published a beginner-friendly post on how to add it on my blog, https://nehalist.io/authentication-for-nextjs-with-nextauth-part-1/

if you still want to handle everything by yourself (which I'd highly advise against, since auth is a very complex topic), you can take a look at https://tanstack.com/query/v4/docs/framework/react/reference/useQuery which will handle requests for you in a very convinient way. you're still going to need axios, but useQuery will make things significantly easier.
one possible approach would be to submit your form to a server action (https://nextjs.org/docs/app/building-your-application/data-fetching/server-actions-and-mutations), do your login logic there and return a proper response (like cookies etc). but again, I would not do that at all
Avatar
MinskinOP
Yes, but this looks like my auth would directly be sitting in my nextJS application, and i have a separate backend which already handels all of my logic.
Avatar
what do you mean by handles all your logic?
Avatar
MinskinOP
User database, sending emails etc. protecting routes ...
Avatar
Avatar
MinskinOP
this looks good 👍
Avatar
glad to hear that 🙂
Avatar
MinskinOP
In the docs it is using the pages router: pages/api/auth/[...nextauth].js
How would this change when i use the app directory?
Avatar
src/app/api/auth/[...nextauth]/route.ts (or without the src dir if you don't use that); the entire setup process is on my blog in case
Avatar
MinskinOP
thanks for the help :)
Avatar
glad I could help! 🙂
Avatar
MinskinOP
From what i see, when i want to use the useSession function, i need to wrap my pages inside a SessionProvider, but this makes them a client component?
Is there another way to do this_
Avatar
I've mentioned this in my post; wrapping components within client components doesn't hurt your seo. or what other issue do you have with client components?
Avatar
MinskinOP
No this was just a general question
Avatar
MinskinOP
i have the feeling that my config is not really doing what it should do
Image
This is my current layout
import CredentialsProvider from "next-auth/providers/credentials";
import { baseURL } from "@/app/api/api";
import { NextAuthOptions } from "next-auth";
import NextAuth from "next-auth"


export const authOptions: NextAuthOptions = ({
  providers: [
    CredentialsProvider({
      name: 'Credentials',
      // The credentials is used to generate a suitable form on the sign in page.
      // You can specify whatever fields you are expecting to be submitted.
      // e.g. domain, username, password, 2FA token, etc.
      credentials: {
        email: { label: "Email", type: "text", placeholder: "jsmith" },
        password: {  label: "Password", type: "password" }
      },
  
      async authorize(credentials, req) {
        const {email, password} = credentials as any
  
        const res = await fetch(`${baseURL}/auth/login`, {
          method: "POST",
          headers: {
            "Content-Type": "application/json"
          },
          body: JSON.stringify(email, password)
        }) 
  
        const user = (await res.json()).user;
  
        if (res.ok && user)
          return user
        return null
      }
    })
  ],
  session: {
    strategy: "jwt"
  },
  pages: {
    signIn: "/auth/login"
  }
})

export default NextAuth(authOptions);
And this is my config
but when i use the signIn() method to get redirect to the login page, the issue i get is /api/auth/error
Avatar
anything in the console regarding the error?
Avatar
MinskinOP
i only get a 404 because that page doesnt exist
Problem is, i get redirected instantly, so the console gets cleared afterwards
Avatar
i mean your terminal, not browser console
Avatar
MinskinOP
looks fine aswell
Avatar
additionally, you can set "preserve log" in browser consoles to keep the log
Avatar
MinskinOP
Image
Avatar
your signIn page says "/auth/login", but you put your next route handler under "/api/auth/login"
doesn't seem right
Avatar
MinskinOP
its 2 different folders
├── api
│ ├── api.ts
│ └── auth
│ └── [...nextauth].ts
├── auth
│ ├── login
│ │ └── page.tsx
│ └── register
│ └── page.tsx
├── favicon.ico
├── globals.css
├── layout.tsx
├── page.tsx
└── providers.tsx
i can also access the page by going to /auth/login
Avatar
what do you see when you open /api/auth/signin (AND commenting out the pages section in your config)?
Avatar
MinskinOP
404
Avatar
just to be sure: your api directory is within the app directory?
Avatar
MinskinOP
yes
app/api/auth/[...nextauth].ts
Avatar
seems like you've mixed up the route handler with the lib config; route handlers need to be exported as GET and POST. see https://nehalist.io/authentication-for-nextjs-with-nextauth-part-1/#basic-configuration at route handler section.
Answer
Avatar
MinskinOP
ah i see
Yes redirect is working now
thanks