Core Web Vitals: 웹 성능 측정 및 개선
현대적인 웹 앱을 구축했지만 사용자들이 느리다고 불평합니다. 검색 순위도 영향을 받을 수 있습니다. Core Web Vitals(CWV)는 구글이 사용자 경험을 측정하는 지표로, Largest Contentful Paint(LCP), Interaction to Next Paint(INP), Cumulative Layout Shift(CLS)가 있습니다. 이 가이드는 이를 정확하게 측정하고 효과적으로 개선하는 방법을 보여줍니다.
Core Web Vitals란?
Core Web Vitals는 사용자 경험의 핵심 측면을 수치화하는 세 가지 지표입니다:
- LCP는 로딩 성능을 측정합니다. 가장 큰 콘텐츠 요소(이미지, 텍스트 블록, 비디오)가 보이는 시점을 표시합니다. 목표는 2.5초 이하입니다.
- INP는 반응성을 측정합니다. 모든 상호작용(클릭, 탭, 키 누름)의 지연 시간을 포착하고 최악(또는 거의 최악)의 지연을 보고합니다. 목표는 200밀리초 이하입니다.
- CLS는 시각적 안정성을 측정합니다. 로딩 중 예기치 않은 레이아웃 이동을 수치화합니다. 목표는 0.1 이하입니다.
이 지표는 필드 측정(실제 사용자)과 랩 측정(통제된 환경)으로 이루어집니다. 둘 다 중요합니다.
Core Web Vitals 측정 방법
문제를 진단하려면 필드 데이터와 랩 데이터가 모두 필요합니다.
필드 데이터(실사용자 모니터링)
필드 데이터는 다양한 기기와 네트워크에서 실제 사용자 경험을 반영합니다. 다음 소스를 사용하세요:
- Chrome User Experience Report (CrUX): 수백만 사이트의 실제 사용자 지표 공개 데이터셋입니다. PageSpeed Insights 또는 CrUX API를 통해 액세스할 수 있습니다.
- Google Search Console: Core Web Vitals 보고서는 CrUX 데이터를 기반으로 주의가 필요한 URL 그룹을 보여줍니다.
- Web Vitals JavaScript 라이브러리: 사이트에
web-vitals라이브러리를 추가하고 측정값을 분석 엔드포인트로 전송하세요.
import {onLCP, onINP, onCLS} from 'web-vitals';
function sendToAnalytics(metric) {
const body = JSON.stringify(metric);
navigator.sendBeacon('/analytics', body);
}
onLCP(sendToAnalytics);
onINP(sendToAnalytics);
onCLS(sendToAnalytics);
랩 데이터(합성 테스트)
랩 도구는 통제된 환경에서 로딩을 시뮬레이션하므로 디버깅 및 CI 통합에 적합합니다.
- Lighthouse: Chrome DevTools에 내장되어 있으며 CLI로도 사용 가능하고 PageSpeed Insights에 통합되어 있습니다. 랩 지표와 개선 기회를 보고합니다.
- WebPageTest: 사용자 정의 네트워크 조건과 필름스트립을 사용한 고급 테스트.
- Chrome DevTools Performance 패널: INP에 영향을 미치는 긴 작업을 포함한 런타임 성능을 기록하고 분석합니다.
모범 사례: 랩 데이터로 수정 사항을 식별하고, 필드 데이터로 영향을 검증하세요.
Largest Contentful Paint (LCP) 개선
LCP는 일반적으로 히어로 이미지나 큰 텍스트 블록이 지배합니다. 다음을 최적화하세요:
- LCP 리소스 최적화: 이미지를 압축하고(WebP/AVIF 사용),
srcset으로 반응형 크기를 제공하며, 중요한 경우 LCP 이미지를 미리 로드하세요. - 렌더링 차단 리소스 제거: 중요한 CSS를 인라인으로 처리하고, 중요하지 않은 CSS와 JavaScript를 지연시키세요.
- 서버 응답 시간(TTFB) 개선: CDN을 사용하고, 캐싱을 활성화하며, 백엔드 쿼리를 최적화하세요.
- 클라이언트 측 렌더링 감소: SPA의 경우 초기 뷰에 서버 측 렌더링(SSR) 또는 정적 생성을 고려하세요.
예시: LCP 이미지 미리 로드:
<link rel="preload" as="image" href="/hero.avif" imagesrcset="/hero-480.avif 480w, /hero-800.avif 800w" imagesizes="(max-width: 600px) 480px, 800px">
Interaction to Next Paint (INP) 개선
INP는 사용자 상호작용과 다음 페인트 사이의 지연을 측정합니다. 긴 작업과 무거운 JavaScript가 흔한 원인입니다.
- 긴 작업 분할:
setTimeout,requestIdleCallback또는 스케줄러 API를 사용하여 메인 스레드에 양보하세요. - 이벤트 핸들러 최적화: 비용이 큰 핸들러를 디바운스하거나 스로틀하고, 레이아웃 스래싱을 피하세요.
- JavaScript 실행 시간 감소: 코드 분할, 트리 셰이킹, 중요하지 않은 스크립트 지연.
- CPU 집약적 작업에 웹 워커 사용.
예시: 메인 스레드에 양보:
async function yieldToMain() {
if ('scheduler' in window && 'yield' in scheduler) {
return scheduler.yield();
}
return new Promise(resolve => setTimeout(resolve, 0));
}
async function handleClick() {
// ... do some work
await yieldToMain();
// ... continue
}
Cumulative Layout Shift (CLS) 개선
CLS는 요소가 예기치 않게 이동할 때 발생합니다. 다음 방법으로 방지하세요:
- 이미지와 비디오에 항상 width 및 height 속성 포함하거나 CSS
aspect-ratio를 사용하세요. - 동적 콘텐츠(광고, 임베드, iframe)를 위한 공간 확보: min-height 또는 플레이스홀더 사용.
- 사용자 상호작용에 의해 트리거되지 않는 한 기존 콘텐츠 위에 콘텐츠 삽입 피하기.
font-display: optional사용 또는 폰트 미리 로드로 FOIT/FOUT 이동 방지.
예시: 광고를 위한 공간 확보:
<div>
<!-- ad loads here -->
</div>
지속적 개선을 위한 도구 및 워크플로
성능은 일회성 수정이 아닙니다. 측정을 워크플로에 통합하세요:
- 예산 설정: Lighthouse CI를 사용하여 풀 리퀘스트에서 임계값을 적용하세요.
- 필드 데이터 모니터링: CrUX 또는 자체 RUM으로 대시보드를 설정하세요.
- 수정 우선순위 지정: '좋음' 임계값과 가장 큰 격차가 있는 지표에 집중하세요.
- 실제 기기에서 테스트: 중급 모바일 기기를 에뮬레이트하여 문제를 포착하세요.
빠른 확인을 위해 PageSpeed Insights로 페이지를 실행하세요. 랩 데이터와 필드 데이터를 결합합니다.
FAQ
Core Web Vitals의 현재 임계값은 무엇인가요?
LCP: 좋음 ≤2.5초, 개선 필요 ≤4초, 나쁨 >4초. INP: 좋음 ≤200ms, 개선 필요 ≤500ms, 나쁨 >500ms. CLS: 좋음 ≤0.1, 개선 필요 ≤0.25, 나쁨 >0.25.
CrUX 데이터는 얼마나 자주 업데이트되나요?
CrUX 데이터는 매일 업데이트되지만 데이터셋은 롤링 28일 기간을 반영합니다. Search Console은 주기적으로 업데이트됩니다.
디자인을 변경하지 않고 Core Web Vitals를 개선할 수 있나요?
네. 많은 개선은 기술적입니다: 이미지 최적화, 스크립트 지연, 동적 콘텐츠를 위한 공간 확보, 메인 스레드 작업 감소.
사이트 성능을 분석할 준비가 되셨나요? Nginx 로그 분석기를 사용하여 TTFB와 LCP에 영향을 미치는 느린 서버 응답을 식별하세요.