자바스크립트가 어떻게 내부적으로 동작하고, 비동기 기반으로 작동하는지 또 원리는 무엇인지에 대해서 알아보려고 합니다.
자바스크립트가 어떠한 언어이고, 블로킹, 논 블로킹 중에 어떤 방식으로 프로그래밍을 실행하는지 알아볼까요?
그림은 블로킹 / 논 블로킹의 이미지입니다.
Blocking이란, 자신의 작업을 진행하다가 다른 주체의 작업이 시작되면 다른 작업이 끝날 때까지 기다렸다가 자신의 작업을 시작하는 것이고,
Non-Blocking은 다른 주체의 작업에 관련없이 자신의 작업을 하는 것을 뜻합니다.
자바스크립트는 싱글스레드이지만 논 블로킹으로 프로그래밍이 실행되는데요.
자바스크립트는 메인스레드 하나로 구성되어 있습니다.
이 말의 뜻은 한번에 하나의 작업만을 수행할 수 있음
을 의미합니다.
다른 작업이 끼어들거나 먼저 수행할 수 없으므로 비동기나 동시성은 본래 자바스크립트의 성질이 아닌거죠.
그럼 어떻게 동시성을 가진 함수들을 사용할 수 있었는가에 대해 알아보도록 합시다!
동작원리를 알기 전에! 자바스크립트 엔진이 무엇인지 왜 필요한지에 대해서 알아봅시다.
자바스크립트 엔진은 왜 필요할까요?
당연하게도 자바스크립트를 실행하기 위해서인데요!
자바스크립트 엔진은 자바스크립트 코드를 해석하고 실행하는 인터프리터입니다.
그리고, 자바스크립트 엔진을 내장한 웹브라우저는 자바스크립트가 실행될 수 있는 환경인 실행 환경이라고 할 수 있고, 영어로는 런타임이라고 합니다.
자스 엔진은 v8, rhino, spidermonkey
등 다양하게 있지만 이 중에서도 가장 대표적인 예는 구글에서 만든 v8
엔진이 있습니다.
C++
로 작성되었으며, 구글이 개발한 오픈소스이고, Google Chrome
, Electron
, Node.js
에서 사용합니다.
SpiderMonkey
: 파이어폭스
V8
: 크롬, Node.js
Webkit
: 사파리
Chakra
: 엣지
자바스크립트 엔진에는 메모리힙과 콜스텍이 있습니다.
Memory heap : 메모리 할당이 일어나는 곳, 우리가 선언한 변수들이 어디에 저장되어 있는지 기록하는 장치
Call stack : 코드 실행에 따라 호출 스택이 쌓이는 곳, 우리가 작성한 js 파일을 기계어로 바꿔서 컴퓨터가 실행할 수 있게 해줌
먼저 콜스텍이란 무엇인지 알아봅시다.
( 실행 컨텍스트라는 것이 무엇인지 알아야 하는데,
실행 컨텍스트 : 실행할 코드에 제공할 환경 정보들을 모아놓은 객체라고 생각하면 됩니다. )
콜스텍은 콜이 스택처럼 쌓입니다.
Call
이 쌓이는 것이고, call
은 function
을 호출하는 것입니다.
윗방향으로 쌓이게 되고, 아랫방향으로 실행됩니다.
콜스텍을 통해서 우리가 어떤 함수를 지금 실행하고 있구나
를 알게 됩니다.
왼쪽 코드가 어떻게 동작이 될 거 같나요?
제일 처음으로 모든 코드를 가지고 있는 전역 컨텍스트 anonymous
가 담깁니다.
그 다음에 first
가 호출이 됩니다.
여기서 콜 스텍은 호출이 될 때 담긴다고 생각하면 됩니다.
first
가 담기고 first
로 갔더니 second
가 호출이 되고
seond
로 갔더니 third
가 호출이 됩니다.
그리고 third로 갔더니 console.log(‘세번째’)
가 호출이 됩니다.
호출스텍에 다 쌓이고 나서 console.log(‘세번째’)
가 실행이 되고,
실행되면서 console.log(‘세번째’)
가 빠져나갑니다.
third()
가 빠져나가고 second()
로 왔더니 third()
가 빠지고 console.log(‘두번째’)
가 실행됩니다.
실행되면서 console.log(‘두번째’)
빠져나가고
second()
가 빠져나갑니다.
이렇게 콜스텍이 무엇인지, 어떻게 실행되는지 알아보았고 다음에는 비동기 처리는 어떻게 하는지 알아봅시다.
아까와는 다른 코드인데 어떻게 실행될 거 같나요?
console.log(‘시작’)
SetTimeout
은 바로 실행할 수 없기 때문에 대기실로 보냅니다 -> Web API
에게 비동기 작업을 위임합니다.Web API
는 자바스크립트 엔진이 아닙니다. Web API
는 브라우저에서 제공하는 api
로, dom
, ajax
, timeout
등이 있습니다. call stack
에서 실행된 비동기 함수는 Web API
를 호출합니다.console.log(‘끝’)
Web API
는 3초 후에 setTimeout
비동기 작업을 수행하고, 콜백 함수를 이벤트 루프를 통해서 콜백 큐에 넘겨주게 됩니다.Web API
에서 작업이 끝나면 이벤트 루프를 통해서 콜백함수를 콜백 큐에 밀어 넣습니다.콜스텍이 비어있을 때
, 콜백 큐에서 대기하고 있던 콜백함수를 콜스텍으로 넘겨줍니다.Web API
에게 위임합니다.Web API
는 해당 비동기 작업을 수행하고, 콜백 함수를 이벤트 루프를 통해서 태스트 큐에 넘겨주게 됩니다.마지막으로 정리를 해보자면,
참고 :
https://www.youtube.com/watch?v=v67LloZ1ieI
https://www.youtube.com/watch?v=QFHyPInNhbo
https://joshua1988.github.io/web-development/translation/javascript/how-js-works-inside-engine/
멋져여!