📢 어렵고 정석적인 개념 설명보다는 저같은 초보자도 이해하기 쉽게 정리하는 것을 원칙으로 포스팅하고 있습니다. 😄

[JavaScript] 자바스크립트 엔진 동작 원리 (이벤트 루프)

What

자바스크립트를 공부한다고 해서 단순히 타입과 메서드를 공부하는 게 전부는 아니다. 사실 이것보다 중요한 것은 자바스크립트가 어떻게 동작하는지를 이해하는 것이다. 우리가 작성한 코드가 자바스크립트 입장에서 어떻게 읽어내는지, 그냥 위에서 아래로 읽기만 하는 건지 등을 공부하는 게 자바스크립트 학습의 가장 기본 중에 기본이라고 할 수 있다.

 

지금까지 자바스크립트를 그저 내가 친 코드나 읽어주는 엔진 나부랭이(?) 정도로만 생각했다면, 이 글에서만큼은 스스로가 자바스크립트 엔진 혹은 한 줄의 JS 코드가 되었다고 생각하고 어떻게 동작하는지 이해해 보자.

 

How

위 그림은 자바스크립트의 동작 원리 이해에 조금이나마 도움이 되고자 한 번 그려봤다. 그림에서 주목할 만한 점은 메모리 힙, 콜 스택, 콜백 큐, Web APIs 이렇게 4개의 공간이 자바스크립트 엔진이 코드를 읽고 실행하는 데 거쳐가는 곳이라는 점이다. 즉, 소화기관이라고 생각했을 때 엔진이 코드를 먹으면 콜 스택과 콜백 큐, Web APIs를 거쳐 최종적으로 메모리에 저장된다고 이해하면 쉽다.

 

메모리 힙 (Memory Heap)

메모리 힙은 자바스크립트 엔진이 최종적으로 변수와 함수 등을 저장하는 공간이다.

우리가 작성한 코드가 화면에 나타나는 것도 바로 이 메모리 힙에 저장됐기 때문이라고 할 수 있다.

 

콜 스택 (Call Stack) ≒ 실행 컨텍스트

콜 스택은 메모리 힙에 저장되기 직전 코드가 실행되는 공간이라고 할 수 있다. 특히, 싱글 스레드라는 특징을 갖는데 싱글 스레드란 한 번에 코드 1개를 실행할 수 있음을 뜻한다. 또한, 가장 나중에 쌓인 게 제일 먼저 실행되는 LIFO 성격도 가지고 있다. 

 

콜백 큐 (Callback Queue)

자바스크립트는 일반적으로 동기식 언어지만, setTimeout()과 같은 비동기식 함수를 자주 사용하기도 한다. 비동기식 함수가 Web APIs에서 실행이 되고 콜 스택으로 들어가기 전 대기하는 공간이 바로 콜백 큐이다.

 

실행이 모두 끝난 비동기식 함수는 콜백 큐에서 콜 스택에 자리가 날 때까지 기다리게 되는데, 콜백 큐에 자리가 났을 때 콜백 큐에서 대기 중인 코드를 넘겨주는 과정이 바로 '이벤트 루프'이다.

이벤트 루프는 콜백 큐와 콜 스택을 항상 지켜보는 관제탑 역할을 하며, 자바스크립트 엔진이 동기식과 비동기식 함수를 모두 사용할 수 있게끔 해주는 장치이기도 하다.

 

Web APIs

자바스크립트는 동기식과 비동기식이 존재한다. 일반적으로는 동기식이 원칙이지만, setTimeout()처럼 비동기식 함수가 가끔 호출되기도 한다. 자바스크립트 엔진은 비동기식을 동기식과 같은 과정으로 처리하지 않는다.

콜 스택에서 비동기식을 발견하는 순간 Web APIs로 보내버리고, 이곳에서 비동기식 함수를 실행한다. 실행이 끝나면 다시 콜백 큐에서 대기 후 이벤트 루프에 의해 다시 콜 스택으로 넘어간다.

 

자바스크립트 엔진 동작 과정

1. 자바스크립트 엔진이 한 줄의 동기식 코드를 발견했다.
2. 콜 스택에서 코드가 실행된다.
3. 메모리에 저장된다.
4. 자바스크립트 엔진이 비동기식 함수를 발견했다.
5. 콜 스택에서 Web APIs로 이동한다.
6. Web APIs에서 실행이 끝나면(setTimeout()으로 치면 n초가 지났을 때) 콜백 큐에서 대기한다.
7. 콜 스택에 자리가 나면 이벤트 루프에 의해 콜백 큐에서 콜 스택으로 이동 후 실행된다.