Interaction to Next Paint (INP) 문제 찾기 및 수정: 단계별 가이드

RUM 데이터, Chrome DevTools 및 LoAF API를 사용하여 Interaction to Next Paint 문제를 식별하고 수정하는 방법을 알아보세요.

Arjen Karel Core Web Vitals Consultant
Arjen Karel - linkedin
Last update: 2026-03-04

Interaction to Next Paint (INP) 문제 찾기 및 수정

이 페이지는 당사의 Interaction to Next Paint (INP) 시리즈의 일부입니다. INP는 사용자 상호 작용과 다음 시각적 업데이트 사이의 지연을 추적하여 웹사이트의 응답성을 측정합니다. 좋은 INP 점수는 200밀리초 미만이며, 500밀리초를 초과하는 점수는 나쁨으로 평가됩니다. INP가 처음이라면 전체 개요를 위해 INP 허브 페이지에서 시작하세요.

2025 Web Almanac에 따르면 모바일 오리진의 23%가 여전히 INP에 실패합니다. 귀하의 사이트가 그 중 하나라면, 프로세스는 다음과 같습니다: Search Console에서 문제를 확인하고, Real User Monitoring (RUM) 데이터로 근본 원인을 진단하며, 로컬에서 복제하고, 각 INP 단계에 대상 수정 사항을 적용하세요.

INP 팁: 대부분의 경우 사용자가 페이지 로딩의 시작 단계 동안 페이지와 상호 작용할 때 INP가 훨씬 더 나빠질 것입니다. 그렇기 때문에 INP를 디버깅할 때, 모든 상호 작용과 페이지 로딩 상태를 기록하는 것이 좋습니다!

1단계: Search Console에서 INP 확인

첫 번째 단계는 실제로 INP 문제가 있는지 확인하는 것입니다. 코드 변경을 수행하기 전에 Google Search Console에서 문제를 확인하여 가정이 아닌 실제 필드 데이터를 바탕으로 작업해야 합니다.

Google Search Console에 로그인하세요. 왼쪽 메뉴에서 Core Web Vitals를 클릭하고 모바일 또는 데스크톱을 선택하세요 (: 대부분의 경우 INP 문제는 모바일에서 먼저 나타나므로 모바일로 시작하세요).

여기에 현재 사이트에 있는 모든 Core Web Vitals 관련 문제에 대한 개요가 표시됩니다. 이러한 문제 중 하나가 INP와 관련된 경우 문제가 있음을 확인한 것입니다.

2단계: Interaction to Next Paint 문제 식별

Google Search Console은 URL 그룹 외에는 Interaction to Next Paint 문제의 원인을 파악할 수 있는 어떠한 정보도 제공하지 않습니다. 그래서 대부분의 경우 개발자들은 맹목적으로 뛰어듭니다. 그들은 사용하지 않는 JavaScript를 제거하고 (항상 좋은 아이디어입니다) 메인 스레드를 분할하기 시작하지만 (이 역시 좋은 아이디어입니다), 그것만으로는 INP가 완전히 수정되는 경우가 거의 없습니다.

그렇기 때문에 INP를 개선할 때, 정확히 무슨 일이 일어나고 있는지 알아야 합니다. 다음 네 가지 중요한 질문에 대한 답이 필요합니다:

어떤 요소와 상호 작용할 때 나쁜 INP 점수가 발생합니까? 보통 나쁜 INP 점수는 단일 요소가 아니라 여러 문제의 조합으로 발생합니다. 우리는 가장 나쁜 것부터 시작하여 하나씩 해결해 나가야 합니다.
이러한 상호 작용은 언제 발생합니까? 페이지 로드의 시작 단계 동안 발생합니까, 아니면 메인 페이지가 완전히 로드된 후에도 발생합니까?
이러한 상호 작용은 어디에서 발생합니까? 모든 페이지에서 발생합니까, 아니면 선택된 몇 개의 페이지에서만 발생합니까?
이러한 상호 작용을 어떻게 복제할 수 있습니까? 이미 눈치채셨겠지만, INP 문제를 복제하는 것은 어렵습니다. 그렇기 때문에 나쁜 INP 점수를 가진 기기 특성을 모방하여 성공을 위한 환경을 설정해야 합니다.

RUM 추적 설정

이 모든 질문에 대답하려면 실제 사용자를 추적하고 Interaction to Next Paint에서 발생할 수 있는 모든 문제를 기록하기 시작해야 합니다. RUM 추적을 활성화하는 방법에는 여러 가지가 있습니다. 첫 번째는 Web Vitals 라이브러리를 사용하고 결과를 자체 분석 백엔드로 보내는 것입니다. 이 방법의 장점은 저렴하고 유연하다는 것입니다. 단점은 많은 추가 작업이 필요할 수 있다는 것입니다.

Core Web Vitals 데이터를 자체 백엔드로 보내는 것에 대한 좋은 대안은 시중에 있는 많은 RUM 도구 중 하나를 사용하는 것입니다. 당사는 이러한 사용 사례를 위해 CoreDash를 개발했습니다. CoreDash는 저렴하고 빠르며 효과적인 RUM 도구로 제 역할을 다합니다. 물론 시중에는 많은 RUM 솔루션이 있으며 그들 또한 제 역할을 할 것입니다(다만 가격이 더 높습니다).

높은 INP를 유발하는 요소별 느린 상호 작용 찾기

가장 나쁜 INP 점수를 유발하는 가장 느린 상호 작용을 찾는 것부터 시작하세요. CoreDash에서 "INP metric by Elements"로 페이지를 나열하면 가장 느린 상호 작용을 얻을 수 있습니다. 첫 번째 줄을 클릭하여 이러한 상호 작용으로 지표를 필터링하세요.

나쁜 INP 상호 작용이 발생하는 시기 찾기

다음으로, 로드 상태별로 필터링된 URL을 정렬하세요. 이것은 INP의 근본 원인에 대한 더 많은 통찰력을 줄 것입니다. 이 경우 DOM 콘텐츠가 로드되었을 때 높은 INP가 발생합니다. 이는 스크립트는 구문 분석되었지만 비동기 스크립트와 페이지의 하위 리소스는 아직 로드되지 않았음을 의미합니다. 이 경우 INP는 페이지 로드가 완전히 끝나지 않은 상태에서의 조기 클릭으로 인해 발생합니다.

영향력이 가장 큰 로드 상태를 클릭하여 다른 필터를 계속 생성하세요.

높은 INP 점수의 원인이 되는 URL 찾기

마지막으로, 가장 느린 상호 작용이 있는 요소와 올바른 로드 상태로 필터링한 후, INP가 최악인 URL을 살펴볼 것입니다. 이 경우 이것은 특정 페이지 세트에서 분명하게 발생합니다.

기기 특성 찾기

느린 상호 작용, 로드 상태 및 높은 Interaction to Next Paint를 유발하는 URL을 식별했다면, 어떤 유형의 방문자가 최악의 INP 점수를 유발하는지 살펴볼 것입니다. 우리는 기기 메모리, 대역폭, 화면 크기 및 기타 하드웨어 특성을 살펴볼 것입니다. 이러한 특성을 식별하면 문제를 복제하고 기록하는 단계로 넘어갈 수 있습니다.

INP 진단을 위해 Long Animation Frames (LoAF) API 사용하기

Long Animation Frames API (LoAF)는 어떤 스크립트와 함수가 느린 상호 작용을 유발하는지 정확히 알려줍니다. 이전의 Long Tasks API와 달리, LoAF는 스크립트 URL, 함수 이름 및 프레임별 타이밍 분석을 제공합니다. 이는 CoreDash와 같은 도구의 RUM 데이터와 결합될 때 특히 유용합니다.

이 관찰자는 50ms보다 긴 프레임에 대한 LoAF 항목을 수집하여 스크립트 기여도, 지속 시간 및 차단 시간을 캡처합니다:

// INP 기여도를 위해 Long Animation Frames 관찰
const observer = new PerformanceObserver((list) => {
  for (const entry of list.getEntries()) {
    // 50ms보다 긴 프레임만 기록
    if (entry.duration > 50) {
      console.log('Long Animation Frame:', {
        duration: entry.duration,
        blockingDuration: entry.blockingDuration,
        renderStart: entry.renderStart,
        styleAndLayoutStart: entry.styleAndLayoutStart,
        scripts: entry.scripts.map(script => ({
          sourceURL: script.sourceURL,
          sourceFunctionName: script.sourceFunctionName,
          invokerType: script.invokerType,
          invoker: script.invoker,
          duration: script.duration
        }))
      });
    }
  }
});

observer.observe({ type: 'long-animation-frame', buffered: true });

LoAF API는 어떤 스크립트가 INP의 각 단계에 기여하는지 보여줍니다. scripts 배열은 정확한 소스 파일과 함수 이름을 알려주며, renderStartstyleAndLayoutStart는 처리 시간과 프레젠테이션 지연을 분리하는 데 도움을 줍니다. LoAF는 현재 Chromium 전용(Chrome 123+)이므로, Firefox 및 Safari 디버깅의 경우 Performance 패널 추적 및 RUM 데이터에 의존하세요. async 대 defer JavaScript 로딩이 이러한 타이밍에 미치는 영향에 대한 자세한 내용은 당사의 전용 가이드를 참조하세요.

3단계: 높은 INP 점수를 유발하는 상호 작용 복제 및 디버깅

이 데이터를 확보했으므로 근본 원인을 수정하기 시작할 수 있습니다.

성공을 위한 설정: INP 실패 환경 복제

다음으로 해야 할 일은 실패하는 INP를 재현해 보는 것입니다. INP가 실패할 수 있는 상황을 모방하여 이 작업을 수행합니다.

Chrome Performance 패널 사용: Chrome 개발자 도구를 열고(Ctrl+Shift+I) Performance 패널을 선택하세요. 상단 표시줄에서 CPU 스로틀링을 선택하고 (일반 모바일 기기를 에뮬레이트하기 위해 4배 감속으로 스로틀링), 네트워크 스로틀링을 선택하며 (평균 모바일 기기를 모방하기 위해 빠른 3G 사전 설정을 선택), 평균 모바일 기기를 모방하기 위해 하드웨어 동시성을 4 또는 8로 설정할 수 있습니다.

더 적은 메모리로 Chrome을 로드하려면(네트워크 및 CPU 설정을 낮추는 것만으로도 종종 충분하지만) Docker 컨테이너에서 Chrome을 시작하고 더 적은 메모리를 할당하세요.

페이지 재로드, 상호 작용 및 Core Web Vitals 시각화 도구로 INP 확인

이제 조건을 시뮬레이션하고 INP 점수가 RUM 데이터에서 보고된 것과 일치하는지 확인하세요.

페이지를 재로드하고 적절한 시간 올바른 요소 클릭하세요.

성능 추적을 사용한 INP 디버깅

이것이 바로 이전 단계에서 준비해 온 순간입니다. 특정 상호 작용이 나쁜 Interaction to Next Paint 점수를 유발하는 이유를 알아낼 때입니다.

Chrome 개발자 콘솔(Ctrl+Shift+I)을 열고 Performance 패널로 이동하여 이번에는 원형 화살표 아이콘을 클릭하여 페이지를 다시 로드하고 기록을 시작하세요(또는 Ctrl+Shift+E 단축키를 사용하세요). 기록이 실행되는 동안 나쁜 INP를 유발하는 요소와 상호 작용하세요. 몇 초 후, 기록을 중지하고 타임라인을 검사합니다. "Interactions" 트랙에서 상호 작용 이벤트를 찾은 다음, "Main" 트랙에서 해당 작업을 검사하여 각 단계 동안 정확히 어떤 코드가 실행되고 있는지 확인하세요.

성능 추적 읽기

Chrome Performance 패널에서 상호 작용은 "Interactions" 트랙에 색상 막대로 나타납니다. 이를 클릭하여 전체 INP 지속 시간과 그 세부 정보를 확인하세요. 아래의 "Main" 트랙에서는 상호 작용 동안 실행된 개별 작업을 볼 수 있습니다. 다음 사항에 주의하세요:

  • 이벤트 핸들러 이전의 작업: 입력 지연에 기여합니다
  • 이벤트 핸들러 자체: 이것은 처리 시간입니다
  • 핸들러가 완료된 후의 렌더링 작업: 이것은 프레젠테이션 지연입니다

이러한 발견을 LoAF 데이터와 비교하여 추적에서 식별된 스크립트가 RUM 도구의 기여도 데이터와 일치하는지 확인하세요. 이 시점은 JavaScript 스크롤 핸들러가 문제에 기여하고 있는지 확인할 수 있는 좋은 기회이기도 합니다.

4단계: INP 문제 수정

어떤 상호 작용이 왜 느린지 알고 있습니다. 이제 그것을 수정할 시간입니다. Interaction to Next Paint는 3가지 단계로 나눌 수 있습니다: 입력 지연, 처리 시간, 그리고 프레젠테이션 지연.

각 단계에는 다른 접근 방식이 필요합니다. 여기에 요약이 있습니다. 전체 최적화 가이드를 보려면 링크를 따라가세요.

입력 지연 최소화:

입력 지연은 페이지와의 상호 작용 시점부터 이벤트 콜백이 실행되기 시작할 때까지의 시간입니다. 일부 입력 지연은 불가피하지만(브라우저는 콜백을 예약할 시간이 필요함), 이를 최소화할 수 있습니다:

  1. 긴 작업을 피하세요. 작업이 실행될 때마다 메인 스레드를 차단하고 이벤트 콜백을 대기 상태로 만듭니다. 이는 초기 클릭을 최적화할 때 특히 중요합니다(대부분의 스크립트가 그 시점에 실행되기 때문입니다). JavaScript 차단을 줄이는 전략에 대해서는 async 대 defer JavaScript 가이드를 참조하세요.
  2. 새로운 작업을 생성할 때 주의하세요. 예를 들어, setTimeout()을 통한 반복적인 작업이나 mouseover 이벤트에 대한 콜백과 같이 INP 이벤트 이전에 발생할 가능성이 있는 작업들입니다.
  3. 초기 상호 작용을 측정하고 평가하세요. 대화형 요소가 일찍 표시되고(예: 사이트 검색 요소) 나중에 로드되는 JavaScript에 의해 제어되는 경우, 해당 요소와의 상호 작용은 즉각적인 레이아웃 업데이트를 트리거하지 않습니다. 기능을 우선순위로 지정하거나 요소가 제대로 작동하기 전에 요소를 숨기거나 비활성화하세요.
  4. 웹 워커를 사용하여 브라우저의 메인 스레드 밖에서 JavaScript를 실행하세요. 웹 워커는 스크립트가 메인 스레드 밖에서 실행되도록 허용합니다. 이렇게 하면 메인 스레드가 차단되어 INP 입력 지연 문제가 발생하는 것을 방지할 수 있습니다.
  5. 브라우저 유휴 시간 동안 있으면 좋은 타사 스크립트를 로드하세요. 어떤 스크립트는 다른 스크립트보다 더 중요합니다. 이러한 스크립트의 우선순위를 정하고 덜 중요한 스크립트는 브라우저 유휴 시간에 로드하는 것이 좋습니다. 예를 들어, 채팅 스크립트가 있습니다. 실용적인 기술에 대해서는 JavaScript를 지연시키는 14가지 방법에 대한 가이드를 참조하세요.

처리 시간 최소화

처리 시간은 브라우저가 이벤트에 대한 모든 콜백 함수를 실행하는 데 필요한 시간입니다.
  1. 불필요한 코드를 제거하세요. 불필요한 코드는 여전히 실행 중인 오래된 코드이거나 특정 페이지에서는 필요하지 않지만 여전히 CPU 시간을 차지하는 새로운 코드입니다. 이는 INP를 즉시 개선할 수 있는 가장 쉬운 방법입니다.
  2. 다음 페인트 전에 실행할 필요가 없는 코드를 지연시키세요. 코드를 INP 전에 실행되어야 하는 필수 코드와 비필수 코드(예: 분석 데이터 전송)로 분할하고 requestIdleCallback() 메서드를 사용하여 페인트 이벤트 이후에 실행되도록 예약하세요.
  3. 페인트 전에 실행되어야 하는 코드를 최적화하세요. 코드를 확인하고 느리거나 비효율적인 부분을 다시 작성하세요.
  4. 즉각적인 피드백을 제공하세요. 복잡하거나 느려질 수 있는 작업의 경우, 메인 코드를 실행하기 전에 즉각적인 피드백을 제공하세요.

프레젠테이션 지연 최소화

프레젠테이션 지연은 브라우저가 상호 작용에 따른 시각적 업데이트를 렌더링하는 데 걸리는 시간을 나타냅니다. 페이지를 업데이트해야 할 때, 브라우저는 먼저 페이지의 영향을 받는 부분을 다시 렌더링한 다음 새로운 콘텐츠를 페인트하고 컴포지터(GPU 및 래스터)로 보냅니다.
  1. DOM을 작고 단순하게 유지하세요. 브라우저가 중첩되지 않은 적고 단순한 DOM 요소(HTML 노드)를 가진 페이지를 렌더링하는 것이 중첩된 DOM 노드가 많은 페이지를 렌더링하는 것보다 훨씬 쉽습니다. 과도한 DOM 크기 수정에 대해 자세히 알아보세요.
  2. content-visibility를 사용하여 화면 밖의 콘텐츠를 지연 렌더링하세요. content-visibility는 화면 밖 콘텐츠의 렌더링을 지연시키고 해당 콘텐츠를 적시에 렌더링함으로써 페이지의 보이는 부분의 렌더링 속도를 높입니다.

빠른 수정: scheduler.yield()로 메인 스레드에 yield

필수 작업과 비필수 작업 사이에서 메인 스레드에 yielding하는 것은 3가지 INP 단계를 동시에 개선합니다. scheduler.yield() API는 이를 수행할 수 있는 깔끔한 방법을 제공합니다. 다음은 아직 해당 API를 지원하지 않는 브라우저를 위한 fallback이 포함된 재사용 가능한 헬퍼 함수입니다:

async function yieldToMain() {
  if ('scheduler' in window && 'yield' in window.scheduler) {
    return await window.scheduler.yield();
  }
  return new Promise((resolve) => {
    setTimeout(resolve, 0);
  });
}

// 이벤트 핸들러에서의 사용법
async function handleButtonClick() {
  // 필수 작업: UI 업데이트
  updateVisualFeedback();

  // 브라우저가 페인트할 수 있도록 Yield
  await yieldToMain();

  // 비필수 작업: 분석, 로깅
  sendAnalyticsEvent('button_click');
  logInteraction();
}

각 INP 단계 자세히 살펴보기

각 단계에는 고유한 최적화 전략이 있습니다:

  • 입력 지연: 사용자 상호 작용과 이벤트 처리 시작 사이의 시간을 최소화하는 방법을 알아보세요. 입력 지연은 일반적으로 세 단계 중 가장 작지만, 메인 스레드가 스크립트 실행으로 바쁜 페이지 시작 중에 급증합니다.
  • </b>처리 시간: 상호 작용 중에 실행되는 이벤트 핸들러 코드를 최적화하세요. 대부분의 페이지에서 여기서 최적화 노력의 상당 부분이 결실을 맺습니다.
  • 프레젠테이션 지연: 이벤트 처리에 따르는 렌더링 및 페인팅 작업을 줄이세요. 큰 DOM이 있는 복잡한 페이지에서 이것은 종종 가장 큰 단계입니다.

세 가지 단계 모두에 걸친 추가 전략에 대해서는 JavaScript 스크롤을 버려 INP 개선하기JavaScript에 대한 async 대 defer 선택하기 가이드를 참조하세요.

보고서 말고 코드를 씁니다.

1~2 스프린트 동안 팀에 합류해서 모니터링까지 세팅해둡니다. 제가 빠진 뒤에도 지표가 계속 초록으로 유지되도록.

연락 주세요
Interaction to Next Paint (INP) 문제 찾기 및 수정: 단계별 가이드Core Web Vitals Interaction to Next Paint (INP) 문제 찾기 및 수정: 단계별 가이드