Prefetch
Prefetch (<link rel="prefetch">
)는 브라우저 측 최적화 기능으로 앱의 두 번째 라우팅이나 페이지들이 로드되기 전에 필요한 리소스들을 미리 받을 수 있게 해 준다. Prefetch는 아래의 예시와 같이 HTML에 선언적으로 사용하는 방법, HTTP 헤더를 이용하는 방법 (Link: </js/chat-widget.js>; rel=prefetch
), 서비스 워커를 이용하는 방법 혹은 웹팩의 특정 기능을 이용하여 구현할 수 있다.
Prefetch
뷰포트에 들어올 때와 상호작용이 발생할 때 모듈을 불러오는 이전의 예제에서. 버튼을 눌러 컴포넌트를 토글할 때 종종 딜레이가 발생했었다. 이는 사용자가 버튼을 눌렀을 때에도 해당 모듈을 아직 불러오는 중이기 때문에 발생하는 현상이다.
보통 사용자가 최초 페이지를 본 후에도 뒤이어 특정 리소스들을 요청하게 된다. 그 모듈들은 즉시 화면에 보여지지 않기 때문에 초기 번들에서 제외하여 앱의 로딩 타임을 최대한 감소시키고. 사용자에게 더 나은 UX를 제공한다.
컴포넌트나 리소스들은 앱 이용 중에 prefetch될 수 있는데. 이를 위해 import문에 Webpack 의 magic comment를 추가할 수 있다 (/* webpackPrefetch: true */
)
const EmojiPicker = import(/* webpackPrefetch: true */ './EmojiPicker')
앱을 번들하면 콘솔에 EmojiPicker
가 prefetch될 것이라는 메시지를 볼 수 있다.
Asset Size Chunks Chunk Names
emoji-picker.bundle.js 1.49 KiB emoji-picker [emitted] emoji-picker
vendors~emoji-picker.bundle.js 171 KiB vendors~emoji-picker [emitted] vendors~emoji-picker
main.bundle.js 1.34 MiB main [emitted] main
Entrypoint main = main.bundle.js
(prefetch: vendors~emoji-picker.bundle.js emoji-picker.bundle.js)
이 경우 번들 결과에서는 head
태그에 아래처럼 rel=prefetch
속성을 가진 link
태그를 작성하게 된다.
<link rel="prefetch" href="emoji-picker.bundle.js" as="script" />
<link rel="prefetch" href="vendors~emoji-picker.bundle.js" as="script" />
이렇게 처리된 모듈들은 사용자가 모듈을 요청하기 전에 브라우저가 알아서 요청하여 로드 처리한다. 브라우저 프로세스가 유휴 상태이며 네트워크 상태가 좋다고 판단되면 해당 모듈들을 순서대로 불러와 캐시해 둔다. 리소스를 캐시해뒀기 때문에 로딩 타임은 크게 줄어들며 버튼을 클릭했을 때 기다리는 시간 역시 짧아진다. prefetch하여 캐시된 모듈을 받아오기 때문이다.
prefetching이 로딩 타임을 줄이기 위한 좋은 방법이긴 하지만 너무 과도하게 사용하지는 않길 바란다. 사용자가 EmojiPicker
를 끝까지 사용하지 않을 경우 불필요하게 리소스를 로드하게 되어 불필요한 메모리를 사용하고 앱을 느리게 할 수 있다. 꼭 필요한 리소스에만 prefetch를 적용하도록 하자.
아래 글들을 읽어보면 도움이 될 것이다: