`<img src="data:image/png;base64,iVBORw0...">` 같은 코드를 보신 적이 있을 겁니다. 이미지 파일을 따로 두지 않고 그 내용을 글자로 바꿔 문서 안에 통째로 넣은 것입니다. 편리해 보이는데, 아무 데나 쓰면 페이지가 오히려 느려집니다.
무엇과 무엇을 맞바꾸는가
Base64는 바이너리 3바이트를 글자 4개로 표현합니다. 그래서 결과가 원본보다 **약 33% 깁니다.** 이 손해를 감수하고 얻는 것은 '파일을 따로 요청하지 않아도 된다'는 것 하나입니다. 이 거래가 이득인지는 이미지 크기와 개수에 달려 있습니다.
| 따로 파일로 둘 때 | Base64로 넣을 때 | |
|---|---|---|
| 전송량 | 원본 크기 | 약 1.33배 |
| 요청 수 | 이미지마다 1회 | 0회 (문서에 포함) |
| 브라우저 캐시 | 이미지 단위로 재사용 | 불가 — 문서와 함께 매번 내려온다 |
| 문서 크기 | 그대로 | 이미지만큼 커진다 |
| 교체 | 파일만 바꾸면 끝 | 문서를 고쳐야 한다 |
캐시를 잃는 것이 가장 큰 손해다
표에서 실제로 가장 아픈 줄은 캐시입니다. 파일로 두면 브라우저가 한 번 받아 두고 다음 페이지에서 다시 쓰지만, 문서 안에 글자로 박혀 있으면 페이지를 열 때마다 그 덩어리가 함께 내려옵니다. 로고를 Base64로 넣고 페이지가 20개라면, 사용자는 같은 로고를 20번 받는 셈입니다.
CSS에 넣으면 더 미묘해집니다. CSS 파일은 보통 캐시가 잘 되므로 이미지도 함께 캐시되지만, 대신 **CSS를 다 받기 전까지는 페이지가 그려지지 않습니다.** 무거운 이미지를 CSS에 박으면 첫 화면이 늦어집니다.
이득인 경우
- **수 KB 이하의 작은 아이콘** — 요청 하나를 아끼는 이득이 33% 손해보다 큽니다.
- **외부 파일을 쓸 수 없는 곳** — 이메일 서명, 한 파일로 배포하는 HTML 문서, 오프라인 리포트.
- **깜빡임을 없애야 하는 자리** — 배경 패턴처럼 늦게 나타나면 눈에 띄는 아주 작은 이미지.
- **빌드 결과에 파일을 추가하기 곤란할 때** — 설정 한 줄로 끝나는 임시 자산.
손해인 경우
- **사진** — 수백 KB가 1.33배로 늘고 캐시도 못 씁니다. 거의 항상 파일이 낫습니다.
- **여러 페이지에서 반복되는 이미지** — 로고·헤더 배경은 캐시의 이득이 가장 큰 대상입니다.
- **자주 바뀌는 이미지** — 바꿀 때마다 문서를 고치고 배포해야 합니다.
- **아이콘이 여러 개** — 그럴 때는 SVG를 직접 넣거나 스프라이트가 더 낫습니다.
작은 아이콘이라면 SVG를 먼저 보라
단순한 아이콘이라면 PNG를 Base64로 넣는 것보다 SVG 코드를 그대로 넣는 편이 대개 짧습니다. SVG는 이미 글자로 된 형식이라 33% 손해가 없고, 색을 CSS로 바꿀 수 있으며, 어떤 해상도에서도 또렷합니다. Base64가 필요한 것은 보통 SVG로 표현할 수 없는 그림일 때입니다.
변환은 브라우저 안에서 끝나므로 이미지가 서버로 올라가지 않습니다. 반대 방향, 즉 받은 data URI 문자열을 다시 이미지 파일로 되돌리는 것도 같은 자리에서 됩니다 — 로그나 API 응답에 박힌 문자열이 무슨 그림인지 확인할 때 쓸 만합니다.