React · 2026-03-15

React에서 웹 폰트 최적화와 로딩 전략

React 프로젝트에서 폰트 로딩으로 인한 렌더 지연과 레이아웃 이동을 줄이기 위한 font-display 설정, 서브셋, 프리로드 및 캐싱 전략을 정리

작성일 : 2026-03-15 ㆍ 작성자 : 관리자
post
목차

왜 웹 폰트 최적화가 중요한가

웹 폰트는 디자인 일관성에 필수적이지만, 잘못 다루면 초기 렌더링 지연과 FOUT(Flash of Unstyled Text), FOIT(Flash of Invisible Text), 그리고 CLS(Cumulative Layout Shift)를 초래한다. React 환경에서는 클라이언트 렌더링 특성상 폰트 로딩이 사용자 경험에 더 큰 영향을 미치므로 의도적인 로딩 전략이 필요하다. 이 글은 초보자도 이해할 수 있도록 단계별로 접근 방법을 제시한다.

기본 개념 정리

font-display란

font-display는 브라우저가 웹 폰트를 로드할 때 대체 폰트를 보여줄지, 기다릴지, 또는 즉시 교체할지를 결정하는 CSS 규칙이다. 대표값으로는 swap, block, optional, fallback 등이 있으며 각각의 동작에 따라 FOUT/FOIT 현상과 UX가 달라진다.

핵심 목표

  • 초기 텍스트 가시성 확보
  • 레이아웃 이동 최소화
  • 네트워크 비용 절감 및 캐시 활용
  • 첫 번째 의미 있는 페인트(First Contentful Paint) 개선

font-display 설정과 권장 값

React에서 font-display를 적절히 설정하면 FOUT와 FOIT 사이에서 균형을 맞출 수 있다. 대부분의 상황에서는 font-display: swap이나 font-display: optional이 유용하다. swap은 대체 폰트를 즉시 보여주고, 웹 폰트가 도착하면 교체한다. optional은 네트워크 상태가 좋지 않을 때 아예 웹 폰트 적용을 포기해 성능을 우선시한다.

실무 권장 설정

  • 브랜딩 폰트(핵심 UI 텍스트): swap 또는 서버에서 미리 로드(preload)
  • 데코레이티브 폰트(헤더, 특수 효과): optional 또는 비동기 로드
  • 중요도가 낮은 아이콘 폰트: SVG/아이콘 컴포넌트로 대체

프리로드와 프리커넥트

폰트를 외부 CDN에서 가져오는 경우 preconnectpreload를 사용해 TCP/TLS 핸드셰이크와 자원 우선순위를 개선할 수 있다. HTML의 head에 미리 선언하면 브라우저가 폰트 요청을 조기에 시작한다.

<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link rel="preload" as="font" href="/fonts/myfont.woff2" type="font/woff2" crossorigin>

React SPA에서는 서버사이드 렌더링(SSR) 또는 프레임워크(Next.js)의 <Head> 컴포넌트에 해당 태그를 넣어 초기 HTML에 포함시키는 것이 효과적이다.

폰트 서브셋과 포맷 선택

폰트 파일 크기를 줄이는 것이 가장 직접적인 성능 개선 방법이다. 사용하지 않는 글리프를 제거한 서브셋을 사용하거나 언어별로 분리하면 전송 크기를 크게 낮출 수 있다. 또한 WOFF2는 현대 브라우저에서 가장 효율적이므로 우선 제공하고, 레거시용으로 WOFF/TTF를 폴백으로 남긴다.

CSS @font-face 예시

@font-face {
  font-family: 'MyBrand';
  src: url('/fonts/mybrand-subset.woff2') format('woff2');
  font-weight: 400 700;
  font-style: normal;
  font-display: swap;
}

React 환경별 적용 팁

Create React App / SPA

  • index.html head에 preload/preconnect 추가
  • critical 텍스트는 시스템 폰트로 우선 렌더링하고, 브랜드 폰트는 swap으로 교체

Next.js / SSR

  • 서버에서 폰트 링크를 head에 포함해 초기 HTML에 전달
  • 가능하면 폰트 파일을 정적 파일로 빌드에 포함시키고 CDN으로 서빙

비동기 로딩 기법

비동기 로딩은 렌더 차단을 피하는 또 다른 방법이다. JavaScript로 폰트를 로드하고 로딩 완료 시 클래스 토글로 적용하는 방식이 있다. 이때 Font Loading API나 fontfaceobserver 같은 경량 라이브러리를 활용하면 안정적이다.

import FontFaceObserver from 'fontfaceobserver'

const myFont = new FontFaceObserver('MyBrand')
myFont.load(null, 3000).then(() => {
  document.documentElement.classList.add('font-loaded')
})

측정과 검증

변경 후에는 반드시 성능 지표를 측정한다. FCP, LCP, CLS, 그리고 TTFB를 확인하고, Lighthouse와 웹페이지스피드 인사이트를 통해 폰트 관련 권장사항을 검토한다. 실제 사용자 환경(RUM)에서 폰트 로딩 실패와 지연을 모니터링하는 것도 중요하다.

자주 발생하는 실수

  • 모든 텍스트에 커스텀 폰트를 무조건 적용해 FOIT 유발
  • 폰트 파일을 압축하지 않거나 서브셋을 만들지 않음
  • preload를 남발해 브라우저 우선순위를 오히려 낮춤

요약

React에서의 웹 폰트 최적화는 단일 기술로 해결되는 문제가 아니다. font-display 설정, 서브셋과 포맷 선택, preload/preconnect, 비동기 로딩 그리고 측정을 조합해 적용해야 한다. 이렇게 하면 초기 렌더링과 사용자 경험을 동시에 개선할 수 있다. 단계적으로 적용하면서 각 변경의 영향을 계측하는 것이 핵심이다.

react webfont 최적화 font-display 설정 react 폰트 로딩 최적화 webfont 최적화 preload 폰트 웹 성능 서브셋 폰트 font loading 전략