유저가 로그인을 하면 쿠키에 입장권을 저장시켜둠
쿠키는 GET/POST 요청시 자동으로 서버에 전송을 함
장 : 매번 서버에 요청할때마다 DB를 조회해서 엄격하게 체크 가능
단 : DB 부담 심해짐
해결법 : 유저가 많은 사이트 들은 Redis 같은 DB를 사용
장 : DB부담 적음, 유저가 많은 사이트들이 주로 사용함
단 : 유저의 JWT를 훔쳐가면 막을 수 있는 방법이 없음
로그인 방법중 하나임, 예를 들자면 소셜 로그인
유저의 A사이트의 사용 권한을 B사이트를 운영하는 운영자가 잠깐 빌리는것
페북 구글도 비슷한 방법으로 하면 된다
Github.com 로그인하면 우측상단 Settings -> Developer settings -> New OAuth app
어플리케이션 하나 만든다
import NextAuth from "next-auth";
import GithubProvider from "next-auth/providers/github";
export const authOptions = {
providers: [
GithubProvider({
clientId: 'Github에서 발급받은ID',
clientSecret: 'Github에서 발급받은Secret',
}),
],
secret : 'jwt생성시쓰는암호'
};
export default NextAuth(authOptions);
next.auth가 하라는대로 코드를 짜면 된다. jwt 암호는 그냥 원하는거 적자
넥스트는 signIn이라는 함수를 제공한다 이걸 사용하면 만들어져 있는 로그인 페이지에 들어갈 수 있다
'use client';
import { signIn } from 'next-auth/react'
export default function LoginBtn() {
return <button onClick={() => { signIn() }}>로그인</button>
}
'use client'
import { SessionProvider } from "next-auth/react"
export default function Layout({ children }){
return (
<SessionProvider>
{children}
</SessionProvider>
)
}
이렇게 컴포넌트를 만들어서 SessionProvider안에 넣는다 children으로 넣고
let session = useSession();
원하는 곳에 useSession()을 변수에 할당해서 출력하면 된다
보통은 서버 컴포넌트에서 유저정보 가져와서 보여주는게 낫다 왜냐하면 useSession은 랜더링이 끝나고 출력을 하기 때문에 조금 늦게 실행된다
export default function Page(){
let session = await getServerSession(authOptions)
if (session) {
console.log(session)
}
유저의 로그인 상태를 엄격하게 관리하고 싶으면 사용하자
- 첫 로그인시 자동으로 유저를 회원가입 시켜서 회원정보 보관
- 로그인시 자동으로 유저가 언제 로그인 했는지 세션 정보 db에 보관
- 서버에서 유저 정보가 없으면 db에서 가져옴 (jwt에서 가져오지 않음)
- 로그아웃시 유저 세션 정보는 db에서 삭제
npm install @next-auth/mongodb-adapter
export const authOptions = {
providers: [
GithubProvider({
clientId: 'Github에서발급받은ID',
clientSecret: 'Github에서발급받은Secret',
}),
],
secret : '어쩌구'
adapter : MongoDBAdapter(connectDB), //추가함
};
글 발행시 글쓴이에 대한 정보도 함께 저장하면 됨
let session = await getServerSession(요청, 응답, authOptions)
서버 기능 안에서 유저 정보를 이렇게 출력한다
출력을 확인한 후에
if (session) {
요청.body.author = session.user.email
}
요청이
맞으면 email을 author로 해달라고 할당을 하고 넣으면 된다
게시글 작성자에 관한 validation을 할때 session 변수에 정보를 담고 만약 작성자가 작성한글만 삭제 시키고 싶다면 그 정보의 유저 정보와 글의 유저 정보가 같을때 삭제 시키면 된다.
npm install bcrypt
import { connectDB } from "@/util/database";
import bcrypt from "bcrypt";
export default async function handler(요청, 응답) {
if (요청.method === "POST") {
// 숫자 10은 숫자별로 암호화 정도를 나타냄
const hash = await bcrypt.hash(요청.body.password, 10);
// body의 password 부분을 hash로 바꿔줌
요청.body.password = hash;
let db = (await connectDB).db('forum');
// user_cred 라는 컬렉션에 추가
await db.collection('user_cred').insertOne(요청.body);
응답.status(200).json('성공');
}
};
보관할 문자 같은것 (시크릿 코드) 같은거를 잠가놓자
예시
NEXTAUTH_SECRET='secretkey1234'
이렇게 적어놓고
secret: process.env.NEXTAUTH_SECRET
env에 적은 파일을 가져다 쓰면 된다 이러면 소스코드를 보더라도 시크릿 키를 알수가 없다