Notice
Recent Posts
Recent Comments
Link
«   2026/05   »
1 2
3 4 5 6 7 8 9
10 11 12 13 14 15 16
17 18 19 20 21 22 23
24 25 26 27 28 29 30
31
Archives
Today
Total
관리 메뉴

co-cherry

에러 핸들링과 안전성 본문

React

에러 핸들링과 안전성

co-cherry 2026. 4. 26. 16:32

API 에러 분류 

HTTP 상태 코드 (HTTP Status Code)

HTTP 요청의 성공/실패 여부를 서버에서 알려주는 코드 

API 호출 시, HTTP Status Code로 API 처리 결과를 받고 HTTP Response Body로 응답 값을 받음 

  • 정상 호출: 200 반환, 각 API 별 지정된 포맷의 결과값을 받음 
  • 비정상 호출: 400/500 반환, 각 API 서버별 에러 코드와 에러 메세지 값을 받음 

2XX 성공 상태 코드 

  • 200 OK 가장 일반적인 성공 응답, GET/PUT/PATCH 요청 성공, 응답 본문에 데이터가 포함 
  • 201 Created 리소스 생성 성공(POST), Location 헤더에 생성된 리소스 URL 포함 
  • 202 Accepted 요청 접수됨(처리는 아직 완료 아님), 비동기 작업에서 사용 
  • 204 No Content 성공했으나 응답할 본문이 없음, DELETE 성공 또는 PUT 업데이트 성공

4XX 클라이언트 에러 : 예측 가능 에러 (Expected)

개발자가 미리 예상하고 대비할 수 있는 에러

개발자가 구체적인 안내 가능, 프론트에서 사전 검증으로 예방 가능 

  • 400 Bad Request 잘못된 요청(문법 오류, 필수값 누락 등)
  • 401 Unauthorized 인증 안 됨(로그인 필요), 토큰 없음, 토큰 만료, 잘못된 비밀번호 
  • 403 Forbidden 인증은 됐으나 권한이 없음 
  • 404 Not Found 리소스가 존재하지 않음
  • 409 Conflict 리소스 상태 충돌
  • 422 Unprocessable Entity 요청 형식은 맞으나 비즈니스 로직 검증 실패 
  • 429 Too Many Requests Rate Limit 초과(요청이 너무 많음)

5XX 서버 에러 : 예측 불가능 에러 (Unexpected)

런타임에 갑자기 발생해 미리 대비하기 어려운 에러 

일반적인 안내만 가능, 자동 재시도 필요, 프론트에서 예방 불가능 

  • 500 Internal Server Error 가장 일반적인 서버 에러, 서버에서 예상치 못한 오류 발생
  • 502 Bad Gateway 게이트웨이/프록시 서버가 잘못된 응답 받음 
  • 503 Service Unavailable 서버가 일시적으로 요청 처리 불가
  • 504 Gateway Timeout 게이트웨이 서버가 서버 응답을 시간 내 못 받음 

이처럼 예측 가능한 에러는 구체적인 안내를 통해 해결하고 예측 불가능한 에러는 일반적 메세지를 표시 후, 재시도를 유도한다. 

export function handleApiError(error: AxiosError) {
  // 1. 예측 가능 에러
  if (error.response?.status === 401) {
    clearAuth();
    router.push('/login');
    return;
  }
  
  if (error.response?.status === 422) {
    showValidationErrors(error.response.data.errors);
    return;
  }
  
  // 2. 예측 불가능 에러
  if (error.response?.status >= 500) {
    Sentry.captureException(error);
    showToast('서버 오류가 발생했습니다. 잠시 후 다시 시도해주세요');
    return;
  }
}

 

https://sanghaklee.tistory.com/61

 

REST API 관점에서 바라보는 HTTP 상태 코드(HTTP status code)

REST API 관점에서 바라보는 HTTP 상태 코드(HTTP status code) TOC Introduction HTTP 와 REST HTTP Status Code 2XX Success 4.1. 200 OK 4.2. 201 Created 4.3. 202 Accepted 4.4. 204 No Content 4XX Client errors 5.1. 400 Bad Request 5.2. 401 Unauthori

sanghaklee.tistory.com

https://naver.github.io/naver-openapi-guide/errorcode.html

 

네이버 오픈 API 에러 코드 목록

네이버 오픈 API 에러 코드 목록 API를 호출하면 HTTP Status Code로 API 처리 결과를 받고 HTTP Response Body로 응답 값을 받습니다. 응답 값은 OpenAPI에 따라 XML또는 JSON형식이 될 수 있습니다. 따라서 API 응

naver.github.io

 

ErrorBoundary 설계 패턴 

Error Boundary

React 컴포넌트 트리에서 발생한 JavaScript 에러를 포착하는 컴포넌트

에러 발생 시, 대체 UI(Fallback UI)를 보여주기 위한 컴포넌트 

 

1. 직접 구현 (Class Component)

ErrorBoundary 클래스를 직접 구현하는 방법 

  • getDerivedStateFromError() 에러가 발생한 후, UI 렌더링에 사용(Fallback UI 렌더링용)
  • componentDidCatch() commit 단계에서 호출, 에러 정보 기록에 사용 
class ErrorBoundary extends React.Component {
  constructor(props) {
    super(props);
    this.state = { hasError: false };
  }

  static getDerivedStateFromError(error) {
    // 다음 렌더링에서 폴백 UI를 보여주도록 상태 업데이트
    return { hasError: true };
  }

  componentDidCatch(error, errorInfo) {
    // 에러 로깅 (Sentry 등)
    console.error('Error caught:', error, errorInfo);
  }

  render() {
    if (this.state.hasError) {
      return <h1>문제가 발생했습니다.</h1>;
    }

    return this.props.children;
  }
}

 

구현 후, 컴포넌트를 감싸는 방식으로 애플리케이션에서 에러 바운더리 사용 가능

MyComponent나 하위 컴포넌트 중 어떤 컴포넌트가 렌더링 중 에러를 발생시킨다면, 에러 바운더리가 이를 잡아내 기록한 뒤 대체 UI를 렌더링한다. 

<ErrorBoundary>
  <MyComponent />
</ErrorBoundary>

 

2. react-error-boundary 라이브러리 사용 

https://www.npmjs.com/package/react-error-boundary?activeTab=readme

 

제공하는 라이브러리를 사용하는 방법 

pnpm install react-error-boundary

 

라이브러리를 사용하면 별도의 클래스 생성 없이, import를 통해 라이브러리를 호출해 에러 발생 시, fallback UI를 호출할 수 있다.

import { ErrorBoundary } from 'react-error-boundary';

<ErrorBoundary fallback={<div>에러가 발생했습니다</div>}>
  <MyComponent />
</ErrorBoundary>

 

라이브러리에서는 추가적으로 아래와 같은 기능이 있다. 

resetErrorBoundary() 사용 예시

  • FallbackComponent 에러 UI 정의(error, resetErrorBoundary 자동 전달)
    • resetErrorBoundary() 호출 시, 에러 상태 초기화 및 자식 컴포넌트 재 렌더링(다시 시도의 역할)
  • onReset 다시 시도 클릭 시, 캐시/상태 초기화
  • onError 에러 발생 시, Sentry 같은 모니터링 도구에 자동 전송
  • resetKeys 배열 안 값 변경되면 에러 상태 자동 리셋 
import { ErrorBoundary } from 'react-error-boundary';

// 1. FallbackComponent: 에러 UI
function ErrorFallback({ error, resetErrorBoundary }) {
  return (
    <div>
      <h2>문제가 발생했습니다</h2>
      <p>{error.message}</p>
      <button onClick={resetErrorBoundary}>다시 시도</button>
    </div>
  );
}

function App() {
  const [userId, setUserId] = useState(1);
  
  return (
    <ErrorBoundary
      // 1. FallbackComponent: 에러 발생 시 보여줄 컴포넌트
      FallbackComponent={ErrorFallback}
      
      // 2. onReset: 리셋 버튼 클릭 시 실행할 추가 로직
      onReset={() => {
        queryClient.clear(); // 캐시 초기화
      }}
      
      // 3. onError: 에러 발생 시 로깅 (Sentry 전송)
      onError={(error, errorInfo) => {
        Sentry.captureException(error);
      }}
      
      // 4. resetKeys: userId 변경 시 에러 자동 리셋
      resetKeys={[userId]}
    >
      <UserProfile userId={userId} />
    </ErrorBoundary>
  );
}

 

https://velog.io/@wjdals189/React%EC%9D%98-Error-Boundary-%EA%B7%B8%EB%A6%AC%EA%B3%A0-react-error-boundary-%EB%9D%BC%EC%9D%B4%EB%B8%8C%EB%9F%AC%EB%A6%AC

 

React의 Error Boundary 그리고 react-error-boundary 라이브러리

Error Boundary란 무엇이고 어디서 어떻게 쓰여지는지 궁금해서 찾아보며 이해하는 글에러 경계는 컴포넌트 트리가 깨지는 대신 자식 컴포넌트 트리에서 에러를 잡아내고, 이러한 에러의 로그를 남

velog.io

 

 

Error Boundary가 잡을 수 있는 에러와 없는 에러

 

잡을 수 있는 에러 

  • 렌더링 중 발생한 에러 
  • 생명주기 메서드 내 에러
  • 하위 컴포넌트의 constructor 에러

잡을 수 없는 에러 

  • 이벤트 핸들러 (onClick, onChange 등)
  • 비동기 코드 (setTimeout, Promise, async/await)
  • 서버 사이드 렌더링
  • Error Boundary 자체에서 발생한 에러

https://wikidocs.net/197630

 

04) 에러 바운더리와 컴포넌트 에러 처리

[TOC] ## React에서의 에러 바운더리 소개 어떤 애플리케이션에서든 에러를 우아하게 처리하는 것은 원활한 사용자 경험을 제공하기 위해 중요합니다. React는 컴포넌…

wikidocs.net

https://velog.io/@coddingyun/Error-Boundary%EC%97%90%EB%9F%AC-%EB%B0%94%EC%9A%B4%EB%8D%94%EB%A6%AC%EB%A1%9C-%EC%9A%B0%EC%95%84%ED%95%98%EA%B2%8C-%EC%97%90%EB%9F%AC-%EC%B2%98%EB%A6%AC%ED%95%98%EA%B8%B0

 

Error Boundary(에러 바운더리)로 우아하게 에러 처리하기

\*\*공식 문서(https://react-ko.dev/reference/react/Component> 기본적으로 애플리케이션이 렌더링 도중 에러를 발생시키면 React는 화면에서 해당 UI를 제거합니다. 이를 방지하기 위해 UI의 일부를 에러 경계(

velog.io

 

선언적 vs 명령적 처리 전략 비교 

명령적 에러 처리(Imperative)

에러 처리 과정을 단계별로 명시하는 방식

어떻게(How) 처리할지 직접 작성 

  • 특정 조건별로 다른 처리 가능
  • 코드가 길고 복잡하며 에러 처리 로직이 비즈니스 로직과 섞여 재사용성이 낮음 
// 1. 이벤트 핸들러 (Error Boundary가 못 잡음)
const handleSubmit = async () => {
  try {
    await submitForm();
  } catch (error) {
    showToast('제출 실패');
  }
};

// 2. 조건별 다른 처리가 필요할 때
try {
  await fetchData();
} catch (error) {
  if (error.code === 'AUTH_ERROR') {
    router.push('/login');
  } else if (error.code === 'NETWORK_ERROR') {
    showOfflineMode();
  }
}

 

선언적 에러 처리(Declarative)

 

에러 발생 시 무엇을(What) 보여줄지만 선언

처리 과정은 프레임워크/라이브러리가 담당 

  • 코드가 간결하고 읽기 쉽고 에러 처리 로직이 분리되어 재사용성이 높음
  • 세밀한 제어가 어렵고 ErrorBoundary가 못잡는 에러 존재 
// 1. 렌더링 중 에러
<ErrorBoundary FallbackComponent={ErrorUI}>
  <MyComponent />
</ErrorBoundary>

// 2. 비동기 데이터 로딩
<ErrorBoundary>
  <Suspense fallback={<Loading />}>
    <UserData />
  </Suspense>
</ErrorBoundary>

 

구분 명령적 처리 선언적 처리
방식 try-catch, if-else, 상태 관리 Error Boundary, Suspense
에러 처리 위치 컴포넌트 내부 컴포넌트 외부
코드 길이 길고 복잡함 짧고 간결함
가독성 비즈니스 로직과 섞임 분리되어 깔끔
재사용성 낮음 (매번 작성해야 함) 높음 (한 번만 설정)
제어 수준 세밀한 제어 가능 제한적
사용 예 이벤트 핸들러, 특수한 경우 렌더링 에러, 비동기 데이터 

 

따라서, 렌더링은 선언적 에러 처리를 이벤트는 명령적 에러 처리를 하는 것이 좋다. 

 

https://velog.io/@seyoung8239/Imperative-vs-Declarative-Programming

 

Imperative vs Declarative Programming

프로그래머스에서 과제형 테스트를 연습하다 다음과 같은 요구사항을 만났다."가급적 컴포넌트 형태로 추상화 하세요."해설에서는 이 요구사항이 DOM에 접근하는 부분을 최소화하고, 명령형 프

velog.io

https://tech.kakaopay.com/post/react-query-2/#:~:text=Error%20Boundary%EB%8A%94%20React%20Component%20%EB%82%B4%EB%B6%80%EC%97%90%EC%84%9C%20%EC%97%90%EB%9F%AC%EA%B0%80%20%EB%B0%9C%EC%83%9D%ED%95%9C,%EB%8C%80%EC%8B%A0%20%EB%AF%B8%EB%A6%AC%20%EC%A0%95%EC%9D%98%ED%95%B4%20%EB%91%94%20Fallback%20UI%EB%A5%BC%20%ED%99%94%EB%A9%B4%EC%97%90

 

React Query와 함께 Concurrent UI Pattern을 도입하는 방법 | 카카오페이 기술 블로그

카카오페이에서 React Query를 활용하여 Concurrent UI Pattern을 도입한 사례에 대해 소개합니다. 이 글은 연작 중 2편에 해당합니다. 1편: 카카오페이 프론트엔드 개발자들이 React Query를 선택한 이유, 2

tech.kakaopay.com