web

브라우저(Web Browser)란?

브라우저는 인터넷을 통해 웹사이트에 접속하고 웹 콘텐츠를 사용자에게 표시하는 소프트웨어입니다. 오늘날 우리가 사용하는 대부분의 애플리케이션은 브라우저를 통해 작동하며, 브라우저는 웹 페이지를 구성하는 다양한 요소들을 해석하고 시각적으로 렌더링합니다. 이 글에서는 브라우저의 기본 개념, 동작 원리, 주요 엔진에 대해 살펴보겠습니다.

웹 개발을 할 때 브라우저에 대한 이해는 매우 중요합니다. 브라우저는 HTML 문서를 해석하고 CSS를 적용하며, JavaScript를 실행하는 등 웹 페이지의 구조와 스타일을 제어합니다. 각 브라우저는 조금씩 다른 방식으로 동작하기 때문에, 이를 이해하면 웹 애플리케이션을 최적화하고 디버깅하는 데 큰 도움이 됩니다. 또한, 렌더링 엔진의 동작 원리를 이해하면 DOM 조작, CSS, JavaScript 로딩 최적화에 대한 통찰을 얻을 수 있습니다.

브라우저는 사용자에게 웹 페이지를 제공하기 위해 여러 복잡한 과정을 거칩니다. 이 과정은 HTML, CSS, JavaScript 코드가 렌더링되고, 상호작용하는 방식에 따라 다양한 단계로 나눌 수 있습니다. 브라우저가 웹 페이지를 어떻게 처리하는지 이해하는 것은 웹 개발에서 매우 중요합니다. 이제 브라우저의 주요 동작 방식을 살펴보겠습니다.

1. DOM (Document Object Model)

DOM은 웹 페이지의 HTML 문서를 객체 형식으로 표현한 것입니다. 이는 웹 페이지의 구조와 콘텐츠를 브라우저가 이해하고 조작할 수 있게 해주는 인터페이스입니다. 브라우저가 HTML 문서를 파싱하면, 이 문서는 트리 형태로 변환되어 DOM이 됩니다. 개발자는 이 DOM을 통해 웹 페이지의 구조를 동적으로 조작할 수 있습니다.

DOM의 동작 과정

- 브라우저는 HTML 파일을 다운로드한 후, 이를 파싱하여 DOM 트리를 생성합니다.
- DOM 트리는 HTML 문서의 각 요소(예: \<div\>, \<h1\>)를 객체로 표현한 트리 구조입니다.
- JavaScript 코드에서 document.getElementById()와 같은 메서드를 사용하여 DOM 요소를 선택하고 조작할 수 있습니다.

이러한 DOM을 이해하면 페이지의 동적 콘텐츠 변경, 이벤트 처리 및 성능 최적화 작업의 시작이라 할 수 있습니다.

2. CSSOM(CSS Object Model)

CSSOM은 CSS 스타일 시트를 객체 모델로 표현한 것입니다. CSSOM은 DOM과 마찬가지로 브라우저가 웹 페이지의 스타일을 이해하고 적용할 수 있도록 합니다. CSSOM은 스타일 시트를 파싱하고, CSS 규칙을 객체 형식으로 변환한 후, 이를 DOM 트리와 결합하여 최종적인 레이아웃을 결정하는 데 사용됩니다.

CSSOM의 동작 과정:

- 브라우저는 HTML 파일과 별도로 CSS 파일을 다운로드하여 파싱합니다.
- CSSOM은 각 CSS 규칙을 객체로 변환하고, 이를 DOM 요소와 결합하여 스타일을 적용합니다.
- 브라우저는 스타일 계산과 레이아웃 계산을 통해 화면에 렌더링할 최종적인 스타일을 결정합니다.

CSSOM과 DOM은 렌더링 트리(Render Tree)를 형성하게 되며, 이는 웹 페이지의 레이아웃을 결정하는 데 사용됩니다.

3. Javascript 엔진

브라우저 내의 JavaScript 엔진은 JavaScript 코드를 해석하고 실행하는 역할을 합니다. 대표적인 JavaScript 엔진으로는 Chrome의 V8, Firefox의 SpiderMonkey, Safari의 JavaScriptCore 등이 있습니다. JavaScript 엔진은 웹 페이지에서 동적인 콘텐츠와 상호작용을 처리하며, 이는 페이지가 어떻게 반응하는지에 대한 중요한 부분입니다.

JavaScript 엔진의 동작 과정:

- 파싱: JavaScript 코드가 로드되면, 엔진은 코드를 파싱하여 Abstract Syntax Tree(AST)로 변환합니다.
- 컴파일: AST를 바탕으로, JavaScript 엔진은 코드를 바이트코드로 컴파일합니다. 
(V8 엔진의 경우, 이 과정을 즉시 수행하여 JIT(Just-In-Time) 컴파일을 사용합니다.)
- 실행: 컴파일된 바이트코드는 최적화된 방식으로 실행됩니다. 이 단계에서는 실행 중 발생하는 동적 동작도 처리됩니다.

JavaScript 엔진의 성능 최적화가 중요한 이유는, 동적인 웹 애플리케이션에서 JavaScript 코드가 웹 페이지의 동작과 반응성을 직접적으로 영향을 미치기 때문입니다.

브라우저의 렌더링 과정

브라우저가 웹 페이지를 표시하는 과정은 다음과 같은 단계로 나눌 수 있습니다:


1. HTML 파싱: HTML 문서를 파싱하여 DOM 트리를 만듭니다.
2. CSS 파싱: CSS 파일을 파싱하여 CSSOM 트리를 만듭니다.
3. 렌더링 트리 구성: DOM과 CSSOM을 결합하여 렌더링 트리를 생성하고, 이 트리는 화면에 표시될 요소를 포함합니다.
4. 레이아웃: 렌더링 트리를 사용하여 각 요소의 정확한 위치와 크기를 계산합니다.
5. 페인팅: 각 요소를 화면에 그립니다.
6. 컴포지팅: 최종적으로 페인팅된 요소들을 하나의 화면으로 결합하여 사용자에게 표시합니다.
7. JavaScript가 페이지 동작에 영향을 미칠 때마다, 렌더링 트리를 다시 계산해야 하므로 성능 최적화가 매우 중요합니다.

브라우저의 동작 방식을 이해하면 웹 페이지의 성능 최적화와 디버깅에 많은 도움이 됩니다. DOM과 CSSOM을 어떻게 처리하는지, JavaScript 엔진이 코드 실행을 어떻게 최적화하는지 알아두면 웹 애플리케이션의 품질을 높이는 데 중요한 기초가 됩니다. 또한, 브라우저의 렌더링 과정을 이해하면 레이아웃 변경, 리플로우(reflow), 리페인트(repaint) 등의 최적화 기법을 적용할 수 있습니다.

네트워크 통신

우리는 브라우저를 연결하기 위해 인터넷을 기본적으로 연결을 한다. 즉, 웹은 서버와의 통신이 필요하다. 그리고 통신을 브라우저가 하기 위해서는 네트워크에 요청을 보내고 응답을 받아오는 기능이 필수적으로 필요하다. 따라서 데이터를 네트워크에서 가져오거나 서버와 상호작용을 위해서는 네트워크 통신에 대해 알아야 한다.

우리가 주소창에 URL나 검색어를 치고, 데이터 Fetching 하는 과정을 간단히 살펴보자. URL을 파싱(domain, params 등)하고 http나 https를 반환한다. NON-ASCII 코드가 필요하다면 URL의 한국어나 특수문자를 변경하여 인코딩한다. 이때 브라우저는 HSTS(HTTP Strict Transport Security) 목록을 체크하고, 검색한 URL이 목록에 있다면 https 프로토콜을 추가하고, 그렇지 않다면 http를 붙인다. 그 후에 DNS(도메인과 연결된 IP 주소를 알려주는 것) 룩업을 시작한다. 브라우저 자체에 DNS 캐시가 있다면, 캐시에서 IP 주소를 찾는다. 없는 경우라면 운영체제 cache에서 찾고, 여기도 없다면 로컬 라우터나 ISP(Internet Service Procider)에 있는 DNS 서버에 요청하여 IP 주소를 찾는다. 53 포트를 열어 UDP(User Datagram Protocol) 프로토콜을 통해 DNS 서버와 통신을 시작하게 된다. 통신이 된다면, 서버의 IP 주소로 http(80 포트)/https(443 포트) 요청을 시작하고 TCP 소켓 연결을 요청한다. TCP 해더를 채우기 위해서는 네트워크 계층에 요청을 우선 한다. 그리고 IP 헤더를 채우기 위해 전송 계층에 요청을 하고, 데이터 링크 계층에 요청을 해서 이더넷 프레임 헤더를 채운다. 그리고 네트워크의 데이터 패킷이 디지털에서 전기 신호로 변환되고, 서버와 클라이언트 간의 3way 핸드셰이크 후에 데이터를 클라이언트로 보낸다. 전송 계층에서 마지막으로 핸드 세이크가 일어나면 브라우저는 패킷에서 데이터를 얻게 된다.


보안 및 개인 정보 보호

사용자와 상호작용하는 브라우저는 사용자의 개인 정보를 다룰 수밖에 없다. 따라서 개발자는 보안 취약점을 이해하고 웹 애플리케이션에서 사용자의 개인 정보를 안전하게 처리하는 방법을 알아야 한다. 또한, 브라우저가 제공하는 보안 메커니즘을 활용이해하고 활용하여, 사용자를 보호할 수 있는 웹을 만들어야 한다.


Browser

브라우저는 사용자에게 화면을 보여주는 것이 궁극정인 목적이라고도 할 수 있다. 이러한 과정을 렌더링 과정이라 할 수 있다. 렌더링이란 HTML, CSS, Javascript 등의 웹 콘텐츠를 해석하고 화면에 그리는 것을 말한다. 브라우저는 크게 Mozilla의 Gecko, Apple의 WebKit , Chromium Blink 세 가지로 나뉜다. 이러한 브라우저들을 구성하는 요수 중에 사실상 중요한 것은 엔진이라 할 수 있겠다. 간단한 개념과 엔진들의 종류를 알아보자. 우선은 엔진의 종류로는 브라우저 엔진과 렌더링 엔진으로 나뉜다.

Browser Engine

사용자의 이벤트부터(인터페이스), 화면을 그래픽으로 보여주기까지의 과정을 관여한다. 웹이 점점 발전함에 따라 엔진은 고도화가 되었고, 렌더링 엔진과 JavaScript 구문을 분석하는 런타임 JavaScript 엔진이 별도 분리 되었다고 볼 수 있다.

Rendering Engine

사용자가 요청한 HTML문서와 CSS를 파싱 하여 화면에 그리는 역할을 수행한다. 사실 Rendering Engine은 넓은 의미로 브라우저 엔진으로 불리기도 한다. 왜냐하면 JavaScript 엔진 자체가 Nodejs로 독립적으로 실행할 수 있지만, Rendering Engine은 브라우저에 포함되어 있어서 독립적 실행이 불가능하기 때문이다.

Apple의 Webkit

WebKit은 Apple이 개발한 오픈소스 웹 렌더링 엔진으로 HTML, CSS, JavaScript를 해석하는 역할을 한다. Apple에서 사용 중인 iOS, macOS, Safari 브라우저와 Apple 제품에서 주로 사용 중이다. 기본적으로 웹 표준을 준수하여 W3C에서 정의 한 표준안을 따른다. 또한 오픈 소스로 공개되어 있어 모든 개발자들이 코드를 확인하거나 기여를 할 수 있다. WebKit은 Nitro라는 고성능 JavaScript 엔진을 내장하고 있다.

Chromium Blink

Google이 개발한 웹 렌더링 엔진으로, Chromium 프로젝트와 Google Chrome 브라우저에서 사용되고 있다. Blink는 웹 페이지의 HTML, CSS, JavaScript 등의 콘텐츠를 해석하고 시각적으로 표현하는 역할을 한다. Blink는 기존에 사용되던 WebKit 렌더링 엔진에서 분기된 것으로, Chromium 프로젝트의 요구사항과 목표에 맞게 개발되었다고 할 수 있다. Blink는 Chromium의 핵심 구성 요소로, 사용자에게 빠른 속도와 탁월한 사용자 경험을 제공하기 위해 지속적으로 개선되고 최적화 중이다.

일반적인 브라우저와 마찬가지로 Blink는 웹 표준을 준수하여 개발되었다. W3C(World Wide Web Consortium)에서 정의된 표준 권고안을 따르며, HTML/CSS/JAVASCRIPT 등의 최신 웹 기술을 지원한다. Blink은 Chromium의 다중 프로세스 아키텍처를 기반으로 동작한다. 그래서 각 페이지 탭이나 설치하여 사용되는 확장 프로세스는 별도의 프로세스에서 동작한다. 이를 통해 안정성과 보안 향상뿐만 아니라 여러 작업을 동시에 처리하고 빠른 렌더링 속도를 실형 할 수 있다고 할 수 있다. 렌더링을 조금 더 빠르게 하기 위해 Blink는 증분 렌더링(incremental rendering) 기법을 적용한다. 증분 렌더링이란, 페이지의 일부분이 변경되었을 때, 전체 페이지를 다시 렌더링 하는 것이 아니라, 변경된 부분만 업데이트하는 것을 말한다. 이를 통해 페이지의 로딩 속도와 반응성을 향상할 수 있다. 마지막으로 다양한 플랫폼과 장치에서 동작할 수 있도록 설계되어 PC, 모바일, 태블릿 등 다양한 환경경에서 일관된 사용자 경험을 제공한다. 따라서 개발자는 쉽게 Blink를 기반으로 프로덕트를 다양한 플랫폼에 쉽게 배포할 수 있다.