태스크는 프로그램 초기 시작, 이벤트 콜백실행, 인터벌과 타임아웃 실행처럼 표준방식에 의해 예약된 아무 자바스크립트 코드다. 태스크는 모두 태스크큐에서 실행까지 대기한다.
💡 태스크가 태스크 큐에 추가되는 상황
마이크로태스크는 자신을 생성한 함수나 프로그램이 종료된 후에 실행되며, 자바스크립트 실행 스택이 비어있을때만 실행되는 짧은 함수이다. 그리고 사용자 에이전트가 스크립트의 실행 환경을 제어하는 이벤트 루프에 제어권을 넘기기 전에 실행된다. 즉, 자바스크립트 실행 스택이 비어있을 때 마이크로태스크 큐에 있는 모든 마이크로태스크들이 실행 된 후에야 이벤트 루프로 제어권이 넘어간다.
💡 이벤트 루프는 각 콜백함수를 태스크/마이크로태스크 큐에서 꺼내쓰는 것
둘 다 큐에 추가되는 JavaScript 코드로, 적절한 시점에 실행된다. 2개의 큐 모두 콜백함수가 들어간다는 점에서 동일하지만 어떤 함수를 실행하느냐에 따라 어디로 들어가는지가 달라진다. 또한 명칭은 큐 (Queue) 이지만 실제 우리가 아는 자료구조의 큐와는 다르다. 엄밀히 말하자면 우선순위 큐 (Priority Queue) 라고 할 수 있는데, 이벤트 루프가 2개의 큐에서 태스크를 꺼내는 조건이 “제일 오래된 태스크” 이기 때문이다. (동작방식을 확인하고 싶다면 HTML 스펙 을 보자)
💡 함수들이 큐에 들어가는 상황
콜백함수를 태스크 큐에 넣는 함수들
setTimeout, setInterval, setImmediate, requestAnimationFrame, I/O, UI 렌더링
콜백함수를 마이크로태스크 큐에 넣는 함수들
process.nextTick, Promise, Object.observe, MutationObserver
let callback = () => log("일반 타임아웃 콜백을 실행했습니다.");
let urgentCallback = () => log("*** 앗! 긴급 콜백을 실행했습니다!");
log("주 프로그램 시작");
setTimeout(callback, 0);
queueMicrotask(urgentCallback);
log("주 프로그램 종료");
결과
주 프로그램 시작
주 프로그램 종료
*** 앗! 긴급 콜백을 실행했습니다!
일반 타임아웃 콜백을 실행했습니다.
→ 주 프로그램의 실행을 맡은 태스크가 종료된 후, 태스크 큐에 올라간 타임아웃 콜백 태스크를 처리하기 전에 마이크로태스크 큐를 우선 처리한다. 태스크와 마이크로태스크 큐가 별도로 관리된다는 것, 그리고 마이크로태스크가 태스크보다 먼저 실행된다는 것을 기억하면 좋다.
출처 : https://developer.mozilla.org/ko/docs/Web/API/HTML_DOM_API/Microtask_guide
https://baeharam.netlify.app/posts/javascript/JS-Task%EC%99%80-Microtask%EC%9D%98-%EB%8F%99%EC%9E%91%EB%B0%A9%EC%8B%9D