| 항목 | 내용 |
|---|---|
| 발생 환경 | NextAuth.js 세션에 커스텀 필드 추가 필요 |
| 증상 | session.user.role 등 접근 시 TypeScript 에러 |
| 영향 범위 | 인증된 사용자 정보 활용 전체 |
문제:
// TypeScript 에러: Property 'role' does not exist on type 'User'
const { role } = session.user;
| 방안 | 장점 | 단점 |
|---|---|---|
| A. Type Assertion | 빠른 적용 | 타입 안정성 낮음, 매번 캐스팅 필요 |
| B. Module Augmentation | 전역 타입 확장, 한 번 설정 | 설정 방법 학습 필요 |
| C. 커스텀 타입 래퍼 | 유연한 구조 | 기존 훅 사용 불가 |
선택: B안 (Module Augmentation)
// src/types/next-auth.d.ts
import { DefaultSession, DefaultUser } from 'next-auth';
import { UserRole, UserStatus } from '@/generated/prisma';
declare module 'next-auth' {
interface Session {
user: {
id: number;
loginId: string;
role: UserRole;
status: UserStatus;
} & DefaultSession['user'];
}
interface User extends DefaultUser {
id: number;
loginId: string;
role: UserRole;
status: UserStatus;
}
}
declare module 'next-auth/jwt' {
interface JWT {
id: number;
loginId: string;
role: UserRole;
status: UserStatus;
}
}
NextAuth 설정:
// src/app/api/auth/[...nextauth]/route.ts
export const authOptions: NextAuthOptions = {
callbacks: {
async jwt({ token, user }) {
if (user) {
token.id = user.id;
token.loginId = user.loginId;
token.role = user.role;
token.status = user.status;
}
return token;
},
async session({ session, token }) {
session.user.id = token.id;
session.user.loginId = token.loginId;
session.user.role = token.role;
session.user.status = token.status;
return session;
},
},
};
| 관점 | 이유 |
|---|---|
| 타입 안정성 | 전역 타입 확장으로 어디서나 타입 추론 |
| 유지보수 | 한 파일에서 타입 관리 |
| 공식 권장 | NextAuth.js 공식 문서 권장 방식 |