NAVER D2

객체 모델 생성 | Web | Google Developers

이 글은 탈리 가르시엘(Tali Garsiel) 저자의 원문을 한글 번역한 Naver D2에 기고된 글을 원문으로, 다양한 자료를 섞었습니다.

브라우저 (Browser)

Browse → 검색, Browser → 검색하는자

“Browser(검색 하는 자)” 이름 답게 사용자가 URI를 브라우저에 요청하면 해당 URI를 검색하여 해당하는 URI를 가진 서버에 자원을 요청하고 URI를 가져와, 브라우저의 윈도우에서 표현해준다. 이 자원은 HTML 문서가 일반적이지만 PDF, Image 다양한 자원의 형태가 넘어올 수 있다. 이러한 자원의 주소는 URI(Uniform Resource Identifier)에 의해 정해진다.

브라우저는 HTML과 CSS 명세에 따라 해석해서 윈도우 영역에 렌더링 해준다. 명세는 W3C(World Wide Web Consortium)에서 제정한다. 과거에는 여러 브라우저가 일부만 W3C에서 제공하는 명세에 따라서 개발자들이 호환성 구현에 어려움을 겪었으나 현재는 대다수의 브라우저가 명세를 따르게 되었다.

다양한 브라우저들은 공통으로 아래의 기능을 지원한다.

  • URI를 입력할 수 있는 주소 표시 줄
  • 이전 버튼과 다음 버튼
  • 북마크
  • 새로 고침 버튼과 작업을 중지 할 수 있는 정지 버튼
  • 홈 버튼

물론 브라우저 마다 이 기능 외에도 추가로 지원하는 기능들이 있다.

브라우저(Browser)의 구조

HTTP 1.1 기준

브라우저의 구조는 아래와 같다.

  • 브라우저의 흐름

    1) 사용자 인터페이스에서 유저가 URI를 입력하여 브라우저 엔진에 전달한다.

    2) 브라우저 엔진에서 URI에 대해 쿠키로 저장한 자료가 있으면 자료 저장소에서 가져온다.

    3) 렌더링 엔진은 브라우저 엔진에서 가져온 쿠키 값과 URI 데이터를 통신, 자바스크립트 해석기, UI 백엔드 로 전파한다.

    4) 통신 레이어에 URI에 대해 데이터를 요청하고 응답할 때까지 기다린다.

    5) 요청받은 데이터에서 JavaScript는 JavaScript 해석기에서 분석하여 렌더링 엔진에서 HTML CSS와 함께 분석한다.

    6) 브라우저 렌더링 화면에 띄워준다.

  1. 사용자 인터페이스
    주소 표시 줄, 이전/다음 버튼, 홈버튼, 새로 고침 / 정지 버튼 등 요청한 페이지를 보여주는 창 외의 사용자가 컨트롤 할 수 있는 부분을 일컫는다.
  2. 브라우저 엔진
    사용자 인터페이스와 렌더링 엔진 사이의 동작을 제어한다.
  3. 렌더링 엔진
    요청한 URI를 브라우저에서 받아 콘텐츠를 표시해준다. HTML을 요청하면 HTML과 CSS를 파싱하여 창에 보여준다.
  4. 통신
    HTTP 요청과 같은 네트워크 처리를 담당하는 부분, 이 부분은 독립적인 인터페이스라 각 플랫폼의 하부에서 (OS) 실행된다.
  5. 자바스크립트 해석기
    자바스크립트를 해석하여 실행해주는 부분
  6. UI 백엔드
    렌더링 엔진이 브라우저에 페이지를 Rendering 할 때 Render Tree로 구성된 노드를 가로지르며 그려주는 역할을 한다.
  7. 자료 저장소
    이 부분은 자료를 저장하는 계층이다. 쿠키 등의 자료가 들어가 있으며, 자료는 컴퓨터의 하드디스크에 저장된다. HTML5에서는 더 쉽게 사용할 수 있도록 웹 데이터베이스를 사용할 수 있도록 지원한다.

Chrome은 일반적인 브라우저와 달리, 각 탭마다 렌더링 엔진 인스턴스가 생성된다. (그래서 메모리와 CPU를 많이 먹는다.) CPU → 통신 / 메모리 → 자바스크립트 오브젝트 등.

렌더링 엔진

렌더링 엔진의 역할은 요청 받은 내용을 브라우저의 화면에 표시하는 일이다.

다양한 형태의 자원을 나타낼 수 있는데 기본적으로 HTML과 Image를 표시한다. Chrome이나 엣지 등의 브라우저에서는 PDF 형태도 지원하는 경우가 있다.

  • 렌더링 엔진의 종류

    iOS : Webkit

    그 외 : Blink, Gecko

동작 과정

렌더링 엔진에서는 다음과 같은 순서를 따른다.

  1. DOM 트리 구축을 위한 HTML 파싱
    HTML 문서를 받아서 파싱하고 컨텐츠 트리 내부에서 태그(a, div)를 DOM(Document Object Map) 노드로 변환한다. 그 다음 CSS 파일과 함께 포함된 스타일 요소를 파싱한다. 스타일 정보와 HTML 표시 규칙들은 Render Tree라고 부르는 또 다른 트리를 생성한다.

  2. 렌더 트리 구축
    HTML과 CSS를 파싱해서 만들어진 렌더 트리는 색상 또는 면적 등의 시각적 속성을 갖고 있는 사각형을 포함하고 있다. 정해진 순서대로 렌더링하게 된다.

  3. 렌더 트리 배치
    렌더 트리 생성(구축)이 끝나면 배치가 시작된다. 각 노드가 정확한 위치에 표시되기 위해 이동한다.

  4. 렌더 트리 그리기
    배치를 완료하면 UI 백앤드에서 각 노드를 가로지르며 Paint 작업을 한다.

여기서 렌더링 엔진은 좀 더 좋은 사용자 경험을 주기 위해서 가능하면 빠르게 내용을 표시하는데 HTML 파싱을 통해 DOM 트리 구축 작업이 끝날 때까지 기다리지 않는다. 1번의 DOM 트리 구축이 계속 갱신되면서 2,3,4번 작업이 진행된다.

즉, 아까 봤던 통신 레이어에서 네트워크 작업을 계속 진행하면서 네트워크에서 아직 못 받은 내용을 기다림과 동시에 받은 데이터 일부를 화면에 출력하게 된다.

이 과정은 대다수의 렌더링 엔진이 비슷하게 동작한다.

  • Webkit의 동작 과정

  • Gecko의 동작 과정

  • Gecko는 시각적으로 처리되는 렌더를 형상 트리(Frame Tree)라고 표현한다. 각 요소를 형상(Frame)이라고 지칭하는 반면 WebKit은 렌더 트리(Render Tree)라고 표현하며 각 요소를 렌더 객체(Render Object)로 표현한다.

  • Webkit에서 배치(layout)이라고 부르는 반면, Gecko에서는 리플로우(Reflow)라 표현한다.

  • HTML과 CSS를 각각 파싱한 자료를 합쳐서 렌더 트리를 생성하는 작업을 Webkit에서 어태치먼트(Attatchment)라 표현하는 반면, Gecko 에서는 형상구축(Shape Building)이라 표현한다.

  • Webkit은 HTML과 Stylesheet를 처음부터 분리하여 작업하는 반면, Gecko는 HTML을 최초로 호출하고 콘텐츠싱크(Contents Sync)과정을 두어 Style Sheets를 분리해서 작업한다. 이 작업은 DOM을 생성하는 공정으로 웹킷과 비교하여 의미있는 차이점으로 보진 않는다.

파싱 (Parsing)

HTML

HTML은 일반적인 정규 파서로 파싱 할 수 없다. 그 이유는 다음과 같은데.

  1. HTML은 XML과 같이 문법이 Fit 하지 않고 유연하기 때문에
  2. HTML 오류에 대한 브라우저의 관용
  3. JavaScript와 같은 DOM을 조작하는 언어에서 토큰을 추가하거나 수정할 수 있기 때문에 변경에 의해서 재파싱이 이루어지므로

브라우저에서는 일반적으로 HTML 파서를 따로 개발해서 넣어둔다.

DOM

DOM (Document Object Model)

CSSOM

CSSOM (CSS Object Model)

Render Tree

Create Rendering Tree