Asynchronous Programming In Javascript - Advanced Event Loop
Event Loop에는 여러 queue와 다양한 task queue가 존재한다.
1] (Regular) Task Queue
브라우저마다 다른 다양한 task queue를 가진다.
setTimeout, setInterval 같은 timer를 위한 queue
HTTP requests를 위한 queue
user event handlers를 위한 queue 등등...
task의 type이 같으면 같은 task queue로 가게 되고, 브라우저가 어떤 task queue를 실행할지 정하지만, 같은 task queue 내의 task는 도착한 순서대로 실행된다.
(HTTP requests를 위한 queue에 2개가 들어올 경우 나중에 도착한 task가 먼저 도착한 task보다 먼저 실행될 수 없다.)
2] Rendering Pipeline
브라우저는 변경사항이 있을 때마다 페이지를 그리는 것이 아니라,
rendering pipeline이 있어 매 16 ms마다(크롬에서 실험 시 6 ms at 24.04.23.) 페이지를 그리게 된다.
단, task가 진행중일 경우 rendering pipeline은 실행되지 않는다.
따라서 regular tasks 사이에서만 실행될 수 있으며, 한 task가 16 ms보다 크면, rendering pipeline은 대기하게 되고,
사용자는 애니메이션이나 페이지의 상호작용에 있어서 렉을 경험하게 된다.
해결 방법
한 개의 long task의 경우 작은 여러 tasks로 나누어 실행한다.
1개의 long task 예시
여러 개의 작은 tasks
배치 사이즈를 정해서 분할해서 적용한다.
3] Microtask Queue
브라우저에는 regular task와 다른 MicroTask가 있다.
Microtask의 규칙
Javascript는 call stack이 빌 때마다 microtask queue를 regular task queue보다 먼저 확인한다.
(특히 rendering pipeline이 실행이 되기 전에 regular task가 끝날 때마다 확인한다.)
microtask queue에 여러 microtask가 있으면, 모든 microtask를 끝낸 후 rendering pipeline을 실행한다.
microtask가 실행중일 때 microtask를 추가하면, 새로운 microtask 또한 rendering pipeline이 실행되기 전에 실행한다.
사용법
(1) Promise
Promise가 fulfilled 되거나 rejected 된 후 then이나 catch 메서드를 사용하면 then이나 catch 메서드 안의 코드는 microtask queue에 들어간다.
(2) queueMicrotask(callback)
queueMicrotask라는 함수를 사용해서 callback 메서드를 microtask queue에 넣을 수 있다.
Example
다음과 같이 코드를 작성하면, setTimeout(regular task queue)이 먼저 실행되는 것이 아니라, Promise(microtask)의 코드가 먼저 실행되는 것을 볼 수 있다.
4] Animation Frame Queue
애니메이션에 관련된 queue이다.
Animation queue의 규칙
(1) animation queue에 있는 tasks는 브라우저가 페이지를 그릴 때(rendering pipeline이 실행될 때) 전부 실행된다
(2) 단, animation queue의 task가 실행 중일 때 추가로 task가 들어오면, 추가된 task는 다음에 실행된다.
사용법
(1) requestAnimationFrame(callback)
requestAnimationFrame를 사용해서 넣는다.