7.2
Server Actions
Server Actions은 리액트 버전19에서 정식 출시된 기능으로, 클라이언트 컴포넌트가 서버에서 실행되는 비동기 함수를 호출할 수 있게 해주는 기능입니다. 쉽게 말하면 클라이언트 컴포넌트에서 서버쪽 데이터를 가져오거나 데이터베이스에 쿼리를 보낼 수 있게 해주는 것이죠.
Server Actions을 사용하기 위해서는 'use server' 지시어를 사용하면 됩니다. 이 지시어를 비동기 함수의 맨 위에 작성하여 해당 함수를 서버 액션으로 정의할 수도 있고, 파일의 맨 위에 작성하여 해당 파일의 모든 export를 Server Actions로 정의할 수 있습니다.
Next.js에서는 서버 컴포넌트와 클라이언트 컴포넌트에서 Server Actions를 사용하여 form을 제출하거나 데이터 변경을 처리하는 데 사용할 수 있습니다. 'use server' 지시어와 함께 Server Actions가 정의되면 Next.js는 자동으로 해당 서버 함수에 대한 참조를 생성하고, 그 참조를 클라이언트 컴포넌트에 전달합니다. 그리고 클라이언트에서 해당 함수가 호출되면 리액트는 서버에 요청을 보내서 그 함수를 실행하고 결과를 반환하게 됩니다.
Server Actions은 서버 컴포넌트에서 생성하여 클라이언트 컴포넌트의 props로 전달할 수도 있고, 클라이언트 컴포넌트에서 import하여 사용할 수도 있습니다. 지금부터 각 방법에 대해서 살펴보도록 하겠습니다.
서버 컴포넌트에서는 인라인 함수 레벨 또는 모듈 레벨에서 'use server' 지시어를 사용하여 Server Actions를 정의할 수 있습니다. 아래 코드는 인라인 함수 레벨에서 Server Actions를 정의한 예시 코드입니다.
import Button from './Button';
function WritePost() {
async function createPostAction() {
// Server Actions 정의
'use server';
await db.posts.create();
}
return <Button onClick={createPostAction} />;
}
export default WritePost;
위와 같이 Server Actions를 정의하면, 리액트가 WritePost라는 서버 컴포넌트를 렌더링 할 때 createPostAction() 함수의 레퍼런스를 생성하고 그것을 Button이라는 클라이언트 컴포넌트로 전달하게 됩니다. 아래는 Button 컴포넌트의 코드를 나타낸 것인데, 여기서 onClick을 콘솔 로그로 출력해보면 레퍼런스가 들어있는 것을 볼 수 있습니다.
'use client';
function Button({ onClick }) {
console.log(onClick);
// {$$typeof: Symbol.for("react.server.reference"), $$id: 'createPostAction'}
return <button onClick={onClick}>게시글 작성</button>;
}
export default Button;
이 상태에서 사용자가 버튼을 클릭하면, 리액트는 createPostAction() 함수의 레퍼런스와 함께 해당 함수를 실행하도록 서버에 요청하게 됩니다. 이러한 흐름이 서버 컴포넌트에서 Server Actions이 작동하는 흐름이라고 보면 됩니다.
그렇다면 클라이언트 컴포넌트에서 Server Actions를 사용하려면 어떻게 해야 할까요? 클라이언트 컴포넌트에서는 'use server' 지시어를 사용하는 파일로부터 Server Actions를 가져올 수 있습니다.
먼저 아래 코드와 같이 'use server' 지시어를 사용하고 Server Actions가 정의된 별도의 파일을 작성합니다.
// actions.ts
'use server';
export async function createPostAction() {
await db.posts.create();
}
이후 아래 코드와 같이 정의한 Server Actions를 클라이언트 컴포넌트에서 import해서 사용하면 됩니다.
'use client';
import { createPostAction } from './actions';
function WritePost() {
console.log(createPostAction);
// {$$typeof: Symbol.for("react.server.reference"), $$id: 'createPostAction'}
return <button onClick={createPostAction}>게시글 작성</button>;
}
export default WritePost;
이렇게 하게 되면 번들러가 WritePost 클라이언트 컴포넌트를 빌드할 때, 번들 안에 createPostAction() 함수에 대한 레퍼런스를 생성합니다. 그리고 버튼이 클릭되면 리액트는 제공된 레퍼런스를 사용하여 createPostAction() 함수를 실행하기 위해 서버에 요청을 보내게 됩니다.
그리고 추가로 아래와 같이 Server Actions를 클라이언트 컴포넌트에 props로 전달해서 사용할 수도 있습니다.
<ClientComponent myAction={myAction} />
'use client';
function ClientComponent(props) {
const { myAction } = props;
return <form action={myAction}>{/* ... */}</form>
}
export default ClientComponent;
마지막 업데이트: 2025년 10월 24일 02시 25분
이 문서의 저작권은 이인제(소플)에 있습니다. 무단 전재와 무단 복제를 금합니다.