-
[Next.js] Section04 그런데 백엔드 개발자 API를 아직 못 만들었다.Next.js 2025. 2. 16. 23:34
시작하기에 앞서, Section04 강의를 모두 수강하고 정리를 완료 했으나, 메모장이 삭제가 되어 강의를 다시 수강하며 간략하게 내용을 정리 했습니다.
MSW세팅과 .env
백엔드 개발자가 아직 API를 완성하지 못한 경우, 프론트엔드 개발자는 MSW(Mock Service Work)를 이용하여 API 요청을 테스트할 수 있다.
MSW란?
백엔드 API가 없어도 프론트엔드 개발자가 API 요청을 보내고 응답을 받을 수 있도록 도와주는 라이브러리이다.
대신, 요청에 대한 응답을 직접 만들어줘야 하고, 실제 데이터베이스는 다루지 않고, 요청을 보내면 어떤 데이터가 올 것이다 이런식으로 코딩을 해놓는거다.
MSW 동작 방식 :
MSW 설정을 하면, API 요청이 실제 서버로 보내지는 것이 아닌, MSW가 요청을 가로채고 미리 정의된 응답을 반환을 해준다.
MSW 장점 :
에러 상황 테스트 가능 : 특정 API 요청에 대한 에러 응답을 설정하여 예외 처리 로직을 쉽게 테스트할 수 있다.
백엔드 의존도 감소 : API가 완성되기를 기다릴 필요 없이 독립적으로 개발을 진행할 수 있다.
(백엔드 개발자에 과하게 의존하게 되면 회사에서는 백엔드 개발자 없으면 아무것도 못하는 존재 아니냐는 멸시를 받을 수 있다.
그렇기 때문에, 이번 기회에 MSW 공부하면서 HTTP 요청 응답, 헤더 , 쿠키, 캐시 공부를하면 더 좋다.)Next.js 15 버전 이후 API 요청 시 기본 주소를 환경 변수에서 가져와야 한다 :
const baseUrl = process.env.NEXT_PUBLIC_BASE_URL;
fetch(`${baseUrl}/api/login`, {
method: 'POST',
body: JSON.stringify({ username, password }),
headers: {
'Content-Type': 'application/json',
},
});process.env와 NEXT_PUBLIC
- process.env는 환경 변수를 저장하는 객체로, 보안이 필요한 정보를 코드에 직접 노출되지 않도록 관리합니다.
- NEXT_PUBLIC_을 붙이면 브라우저에서도 접근 가능한 환경 변수가 됩니다.
- NEXT_PUBLIC_이 없는 변수는 서버 환경에서만 접근 가능하며, 보안이 필요한 데이터는 이를 이용하여 보호해야 합니다.
Next용 msw 컴포넌트
Next 환경에서 msw 사용 할려면, 프론트엔드의 설정이 필요하고, 특히 로그인 전후로 모두 msw가 필요하므로 API 요청을 원활하게 처리하기 위해서는 컴포넌트를 별도로 생성해주면 된다.
Next의 hot Reloading 기능을 사용하면 msw 잘 안돌아가는 문제가 있다. #69098
버그가 해결이 되기 전까지는
worker.use(…handlers);
(module as any).~ 이런식으로 사용을 하면 된다.
https://github.com/vercel/next.js/issues/69098
Module incorrectly persists between hot updates (HMR) in the browser · Issue #69098 · vercel/next.js
Link to the code that reproduces this issue mswjs/examples#101 To Reproduce Clone the repo, check out the PR's branch. pnpm install. cd examples/with-next. pnpm dev Open the application URL in the ...
github.com
서버 컴포넌트에서 Server Action 사용하기
서버 액션이란?
Next에서 서버 컴포넌트에서 서버 액션을 사용할 수 있다. 클라이언트 컴포넌트 내에서 useServer를 활용하면 서버 코드를 직접 작성할 수 있으며, 브라우저에서는 해당 코드가 노출되지 않아서, API키, 비밀값 이런것들을 안전한게 관리할 수 있다.
Next14가 출시 되면서, 서버 액션의 개념이 과거 PHP 코드와 유사하다고(php는 원래 html이랑 서버 코드랑 같이 섞여 있었다고 함.)웃음거리로 삼기도 했다.
서버 액션의 장점 :
기존 방식에서는 브라우저 -> 서버 -> 데이터베이스 순으로 요청이 전달 되었지만, 서버 액션을 사용하면 서버에서 바로 데이터베이스에 접근할 수 있어 한 단계가 줄어들게 된다. 프론트엔드 개발자가 지겁 데이터베이스에 접근하여 데이터를 가져올 수 있는 환경이 만들어졌다.
이상적이라고 할 수 없지만, 성능상 좀 더 빠르다는 점이 있을 수 있다.
redirect 사용시 주의 점 :
redirect는 절대로 try-catch 문 안에서 사용을 하면 안된다.
그래서 보통 await과 함께 try-catch를 사용하지만, redirect를 try-catch 안에 넣으면 올바르게 동작하지 않을 수 있어서, 변수를 하나 만들어서 빼줘야 한다.
const submit = async () => {
let shouldRedirect = false;
try {
shouldRedirect = true;
} catch (err) {
console.log(err);
}
if (shouldRedirect) {
redirect("/");
}
};Next15 Form 컴포넌트
Next15에서는 Form 컴포넌트가 새롭게 추가가 되었고, 이 컴포넌트는 크게 두가지 방식으로 사용할 수 있다.
1. Function Action Form :
Action 자리에 함수를 직접 넣어 사용, 주로 서버 액션을 처리하는 용도로 사용한다.
2. String Action Form :
Action 자리에 문자열을 넣어 사용하고, 주로 검색창과 같은 간단한 Form 제출에 사용이 된다.
함수를 넣으면 서버 액션을 실행하는 폼이 되고, 문자열을 넣으면 검색과 같은 클라이언트 측 동작을 실행하는 폼이 된다.
클라이언트 컴포넌트에서 서버 액션 사용하기
React DOM 관련 훅에는 두 가지 훅이 있다.
기존에는 useFormState, useFormStatus가 사용되었으나, React 19에서 변경이 되서 useActionState로 변경이 되었지만, 현재 Next15 버전에서는 useActionState를 지원하지 않는다.
미들웨어, 라우트 핸들러, catch-all 라우트
NextAuth(기존 Next-Auth) 주요기능
- 다양한 프로바이더 지원을 해준다.
- 아이디 / 비밀번호 로그인 지원
- 기능 : 로그인, 로그아웃, 현재 사용자 정보 불러오기
- 쿠키 기반 세션 관리 : 로그인 상태를 유지하고, 쿠키를 통해 인증 관리 가능
설치 명령어 : npm i next-auth@5
Next Middleware 활용
Next에서는 Middleware를 활용하여 페이지 접근 권한을 쉽게 관리할 수 있다.
Middleware 역활 :
- 특정 페이지에 대한 로그인 여부 확인
- 로그인하지 않은 사용자는 로그인 페이지로 리디렉션
export const config = {
matcher: ["/explore"] <- 로그인을 해야지 접근 가능한 페이지
};
API Route -> Rpute Handlers 변경
Next에서 기존 API Route가 Route Handler로 변경이 되었다.
Route Handlers 특징
- 브라우저에서 직접 접근할 수 있는 API 주소
- 기존 API Routes보다 더욱 직관적인 URL 방식이 적용이 됐다.
Next를 사용하면 별도의 백엔드 서버 없이도 모든 기능을 프론트엔드에서 처리할 수 있다.
프론트엔드에서도 직접 데이터베이스와 연결이 가능하기 때문이다.
NextAuth 로그인하기
NextAuth 최신 버전에서는 ${process.env.AUTH_URL} 대신 NEXT_PUBLIC_BASE_URL을 사용해야 한다.
환경 변수 설정 (.env)
NEXT_PUBLIC_BASE_URL=yourdomain
AUTH_SECRET=your-secret-key- NEXT_PUBLIC_BASE_URL : 애플리케이션의 기본 URL 설정하는 변수
- AUTH_SECRET : 쿠키 암호화에 사용되는 비밀 키 ( 키가 유출되면 다른 사용자가 본인인 것처럼 로그인할 수 있으몰 철저한 관리 필요)
React-Query SSR 설정
Infinite-Scrolling(무한 스크롤)
React Query 장점 :
- 데이터를 효율적으로 패칭 및 캐싱 가능
- 상태 관리가 간편
- 자동으로 데이터 동기화 지원
Reactu Query SSR 설정
무한 스크롤을 구현 하기 위해서는 ReactQuery 설정이 필요하고 3단계로 나눠 진행을 한다.
1. React Query 설정
2. 서버에서 데이터 받기
3. 클라이언트에서 React-Query로 데이터 패칭 및 무한 스크롤 적용
(데이터를 가져오는거는 주로 로그인 이후에 일어날거기 때문에 after 로그인에만 적용을 해주면 된다.)
Next15 바뀐점 fecth의 cacht 및 Request Memorization
Request Memorization : SSR 과정에서 동일한 fetch 요청이 여러번 실행되더라도 한 번만 요청을 보내고 값을 공유, 기본적으로 비활성화 할 수 없다.
Data Cache : 여러 사용자가 동일한 요청을 보낼 때 백엔드로 한 번만 요청을 보내고, 동일한 데이터를 공유한다.
기본적으로 cache: "no-store" 값이므로 캐싱이 비활성화 되어 있고, 활성화 하려면 cache: "fore-cache" 옵션을 "추가" 해야 한다.
RevaildateTag & RevaildatePath
Next15에서는 캐시 초기화 기능을 제공하는 두 가지 옵션이 추가 되었다.
- revalidateTag - 특정 데이터를 캐싱 후 특정 시점에 초기화할 때 사용
- revalidatePath - 특정 경로의 데이터를 강제 새로고침할 때 사용
이 두 기능은 서버 액션 및 라우트 핸들러에서만 사용 가능하므로, 제한사항을 기억을 해줘야 한다.
Revaildate, RevaildatePath 실행을 안하면 영원히 캐싱이 될 수 있으니 revaildate라는 옵션이 있어서, 시간을 적어줄 수 있다. 60초로
설정을 해 놓으면, 알안서 60초 뒤에 데이터 캐시가 없어진다.
데이터 캐시를 켜고 끌 수 있는 cache: "fore-cache" revaildate: 60 이것들도 같이 기억 하기
클라이언트 React-Query
TypeScript에서 interface는 객체의 구조를 정의할 때 주로 사용이 되고, 객체의 타입을 미리 정의함으로써 타입 안정성을 보장할 수 있다.
import 하는 과정에서 이름이 겹치는데, 이름을 변경할 때 import {Post as IPost} I를 붙이는 이유는 인터페이스라는 뜻이다.
React-Query를 쓰는 이유와 fresh,stale,inactive
React Query 핵심 개념
React Query는 데이터를 가져오고, 캐싱하며, 컴포넌트 간에 공유하는 라이브러리이고, 이를 통해 트래픽을 줄이고, 성능을 최적화할 수 있다.
React-Query의 주요 상태
- Fresh : 데이터가 신선한 상태
- Fetching : 데이터를 가져오는 중
- Inactive : 비활성화 된 상태
상태를 잘 이해를 하면 데이터를 어떻게 다뤄야 하는지를 효과적으로 결정할 수 있따.
React Query의 주요 기능
1) 데이터 공유 기능
React Query의 핵심은 데이터를 컴포넌트 간에 공유하는 것입니다.
- 데이터를 가져오는 것만큼 중요한 것이 공유하는 것
- React Query는 데이터를 패칭(fetching)하는 동시에 자동으로 캐싱
2) 캐싱 기능
**캐싱(Caching)**은 데이터를 미리 저장해두고, 필요할 때 빠르게 불러오는 기술입니다.
캐싱을 사용하는 이유
- 서버 트래픽 절감: 요청 횟수를 줄여 비용 절감
- 빠른 데이터 로딩: 3초 이상의 로딩 시간은 사용자 경험에 부정적 영향을 미침
- 임시 저장소 활용: 메모리나 DB 등에 데이터를 저장하여 재사용 가능
- 사용자 경험 향상: 데이터를 빠르게 표시하여 더 나은 UX 제공
Redux도 데이터를 가져와서 컴포넌트 간에 공유할 수 있지만 <캐싱>이 약하다.
클라이언트에서 데이터를 많이 처리하게 되면, 캐싱이 더 중요하게 되는데, 리덕스 툴킷, 리덕스 사가 이런 애들은 캐싱 기능이 약하기 때문에 리액트 쿼리가 더 필요하게 된다.
인피니티 스크롤링
React-Query에서 매우 쉽게 지원을 해준다.
인피티니 쿼리는 페이지별로 따로 관리를 하고, 2차원 배열 형태로 데이터를 저장하여, 새로운 페이지가 추가가 되면 기존 데이터에 추가를 한다.
prefetchInfiniteQuery 사용
prefetchInfiniteQuery는 미리 데이터를 가져와 캐싱하는 역할을 한다.
initialPageParam 설정
- initialPageParam은 처음 불러올 데이터의 커서 값
- 기본적으로 0으로 설정하여 첫 번째 데이터를 가져옴
<Fragment> 사용법
React에서 <>...</> 구문은 Fragment의 단축형 표현이다.
Fragment의 필요성
- prop을 넣을 경우 <Fragment>로 명시적으로 선언
- prop이 필요 없는 경우 <>...</>를 사용 가능
'Next.js' 카테고리의 다른 글
[Next.js] Section 06 : 백엔드 개발자가 퇴사했다 (2) 2025.03.03 [Next.js] Section05 백엔드 개발자가 드디어 API 문서를 주었다 (0) 2025.02.23 [Next.js] Section 03 본격 클론 시작 (0) 2025.02.02 [Next.js] Section2 기획자와 디자이너가 기획서를 던져주었다! (0) 2025.01.25 [Next.js] Section01 인트로 (1) 2025.01.16