모던 자바스크립트 DeepDive 공부 내용 14차
이번 정리 목차는 38 ~ 39장이다.
38장 브라우저의 렌더링 과정
- 파싱: 프로그래밍 언어의 문법에 맞게 작성된 텍스트 문서를 읽어 들여 문자열을 토큰으로 분해하고 문법적 의미와 구조를 반영하여 파스트리를 생성하는 일련의 과정
- 렌더링: HTML, CSS, JS로 작성된 문서를 파싱하여 브라우저에 시각적 출력
- 브라우저는 HTML, CSS, JS, 이미지, 폰트파일 등 렌더링에 필요한 리소스를 요청하고 서버로부터 응답 받는다.
- 렌더링 엔진은 서버로부터 응답된 HTML, CSS를 파싱하여 DOM과 CSSOM을 생성하고 이를 결합하여 렌더 트리 생성
- JS엔진은 서버로부터 응답된 JS를 파싱하여 AST(추상적구문트리)를 생성하고 바이트코드로 변환하여 실행한다. 이때 JS는 DOM API를 통해 DOM이나 CSSOM 변경가능, 변경된 DOM, CSSOM은 다시 렌더 트리에 결합
- 렌더 트리를 기반으로 HTML요소의 레이아웃 계산하고 화면에 HTML요소 페인팅한다.
요청과 응답
- 브라우저의 핵심 기능은 필요한 리소스를 서버에 요청하고 서버로부터 응답 받아 브라우저에 시각적으로 렌더링 하는 것
HTTP1.1과 HTTP2.0
- HTTP는 브라우저와 서버가 통신하기 위한 프로토콜이다.
- HTTP1.1은 하나의 요청과 하나의 응답만 처리 가능
- HTTP2.0은 다중 요청/응답 가능, HTTP1.1에비해 페이지 속도가 50% 빠르다
HTML 파싱과 DOM 생성
- 렌더링 엔진은 HTML문서를 파싱하여 브라우저가 이해할 수 있는 자료구조인 DOM을 생성
- 브라우저가 서버에 HTML파일을 요청하고 서버로부터 HTML파일을 바이트 형태로 받는다.
- 지정된 인코딩 방식을 통해 문자열로 변환하고 문자열로 변환된 HTML파일을 읽어 토큰들로 분해
- 각 토큰들을 객체로 변환하여 노드 생성
- 이 노드들로 구성된 트리 자료구조인 DOM(Document Object Model) 생성
- 즉 DOM은 HTML 문서를 파싱한 결과물
CSS 파싱과 CSSOM 생성
- 렌더링 엔진은 HTML을 순차적으로 파싱하여 DOM을 생성해 나가다가 CSS를 로드하는 link태그나 style태그 만나면 DOM생성 일시중지하고 HTML과 동일한 파싱과정을 거치며 CSSOM을 생성한다. 이 후 중단된 지점부터 다시 HTML파싱하여 DOM생성 재개
렌더 트리 생성
- DOM과CSSOM을 결합한 것이 렌더 트리
- 렌더트리는 렌더링을 위한 트리구조의 자료구조다. 화면의 렌더링 되는 노드로만 구성
- 완성된 렌더트리는 HTML 레이아웃 계산에 사용되고 화면에 픽셀을 렌더링하는 페인팅 처리에 입력된다.
- JS에의한 노드추가/삭제, 뷰포트 크기변경, 레이아웃 변경이 일어나면 리렌더링 된다.
- 렌더링과정은 반복해서 실행될 수 있다. 가급적 리렌더링 빈번하지 않게 주의해야한다.
자바스크립트 파싱과 실행
- 렌더링 엔진은 HTML을 파싱하며 DOM생성해 나가다가 JS파일 로드하는 script 태그만나면 DOM생성 일시 중지하고 JS파일을 서버에 요청하고 JS엔진에 제어권을 넘긴다.
- 이후 JS 파싱과 실행이 종료되면 렌더링 엔진으로 다시 제어권을 넘겨 DOM생성 재게
- JS 엔진은 JS코드를 파싱하여 저수준언어로 변환하고 실행하는 역할을 한다.
- JS엔진은 JS코드를 파싱하고 AST(추상적 구문 트리)생성하고 AST를 기반으로 인터프리터가 실행할 수 있는 중간코드인 바이트코드를 생성하여 실행
리플로우와 리페인트
- JS코드에 DOMAPI가 사용되면 DOM이나 CSSOM이 변경되어 다시 렌더 트리 결합되고 변경된 렌더 트리를 기반으로 레이아웃과 페인트 과정을 거쳐 리 렌더링된다. 이를 리플로우, 리페인트라 한다.
- 리플로우는 레이아웃 계산을 다시 하는 것
- 리페인트는 다시 페인트(화면에 픽셀 렌더링)하는 것
JS파싱에 의한 HTML파싱 중단
- 브라우저는 위에서 아래로 순차적으로 파싱하고 실행하기 때문에 script태그 위치에 따라 DOM생성이 지연된다. 만약 DOM생성이 완벽하게 되지 않았을 때 DOM API를 사용하는 JS코드를 파싱 하게 되면 문제가 발생하므로 script는 body요소 가장 아래의 위치하는 것이 좋다.
script태그의 async/defer 어트리뷰트
- JS 파싱에 의한 DOM생성이 중단되는 문제를 근본적으로 해결하기 위해 HTML5부터 async와 defer 어트리뷰트 추가
- async어트리뷰트: HTML파싱과 JS파일 로드가 비동기적으로 동시 진행, 단 JS 파싱과 실행은 JS파일 로드가 완료된 직후 진행되며 HTML파싱이 중단된다.
- defer어트리뷰트: 비동기적으로 동시 진행, JS파싱과 실행은 HTML이 파싱이 완료된 직후 진행된다.
39장 DOM
- DOM은 HTML문서의 계층적 구조와 정보를 표현하며 이를 제어할 수 있는 API, 즉 프로퍼티와 메서드를 제공하는 트리 자료 구조이다.
- HTML요소는 HTML문서를 구성하는 개별적인 요소이다.
- HTML요소는 렌더링 엔진에 의해 파싱되어 DOM을 구성하는 요소 노드 객체로 변환된다.
- 어트리뷰트는 어트리뷰트노드, 텍스트는 텍스트노드로 변환
- 모든 노드 객체들을 트리 자료구조로 구성한 것이 DOM
노드 객체 타입
- 문서 노드: DOM트리 최상위 존재하는 루트 노드, document 객체 가리킴, HTML 문서당 document 객체 유일, DOM트리의 노드들에 접근하기 위한 진입점 역할을 담당
- 요소 노드: HTML 요소를 가리키는 객체, 부자 관계를 가지며 이를 통해 구조화한다.
- 어트리뷰트 노드: 요소의 어트리뷰트를 가리키는 객체, 요소 노드에만 연결되어 있다.
- 텍스트 노드: HTML요소의 텍스트를 가리키는 객체, 자식이 없는 리프 노드임, DOM트리 최종단이다.
DOM API는 책을 참고….