HTML 소스코드를 보다 보면 data:image/png;base64,iVBORw0KGgo...로 시작하는 긴 문자열이 나올 때가 있다. 이미지 파일을 텍스트로 바꿔서 HTML 안에 직접 삽입한 것이다. 이게 Base64 인코딩이다.
Base64가 뭔가
바이너리 데이터(이미지, 파일 등)를 A~Z, a~z, 0~9, +, / 총 64개의 인쇄 가능한 문자로 변환하는 방식이다. 텍스트만 전송할 수 있는 환경(이메일, JSON, HTML 속성 등)에서 바이너리 데이터를 보낼 때 쓴다.
예시
원문: "Hello" → Base64:SGVsbG8=
원문: "안녕" → Base64:7JWI64WVSA==(UTF-8 기준)
끝에 붙는 = 기호는 패딩이다. Base64는 3바이트 단위로 인코딩하는데, 입력 데이터가 3의 배수가 아니면 부족한 만큼 =로 채운다.
어디에 쓰이나
| 활용처 | 설명 | 예시 |
|---|---|---|
| 이메일 첨부파일 | SMTP는 텍스트만 전송 가능. 파일을 Base64로 변환해서 메일 본문에 포함 | MIME 인코딩 |
| Data URL | 작은 이미지를 HTML/CSS에 직접 삽입. HTTP 요청 수 줄임 | background: url(data:image/...) |
| JWT 토큰 | 헤더와 페이로드를 Base64URL로 인코딩해서 전송 | eyJhbGci... |
| API 인증 | Basic Auth에서 사용자명:비밀번호를 Base64로 인코딩 | Authorization 헤더 |
Base64는 암호화가 아니다
가장 흔한 오해가 이것이다. Base64는 인코딩이지 암호화가 아니다. 누구나 디코딩할 수 있기 때문에 보안 목적으로 쓸 수 없다.
- 인코딩: 데이터의 형식을 변환 (누구나 복원 가능)
- 암호화: 키가 있어야 복원 가능 (보안 목적)
API 키나 비밀번호를 Base64로 인코딩해서 "숨겼다"고 생각하면 안 된다. Base64 문자열을 디코딩하면 원문이 그대로 나온다.
텍스트와 이미지 변환 방법
JavaScript에서
// 인코딩
btoa('Hello') // "SGVsbG8="
// 디코딩
atob('SGVsbG8=') // "Hello"
한글은 btoa로 직접 처리할 수 없다. UTF-8 변환 과정을 거쳐야 하는데, 복잡해진다.
온라인에서 바로 변환
Base64 변환 도구에 텍스트를 붙여넣거나 이미지를 드래그해서 놓으면 즉시 변환된다. 이미지를 넣으면 Data URL 형태로 생성되어, 그대로 HTML이나 CSS에 붙여넣을 수 있다. JWT 토큰을 붙여넣으면 헤더와 페이로드가 디코딩되어 내용을 확인할 수 있다.
Base64 사용 시 주의점
- 파일 크기 증가
- Base64로 변환하면 원본보다 약 33% 용량이 커진다. 3바이트를 4바이트로 표현하기 때문이다. 큰 이미지를 Data URL로 넣으면 HTML 파일 자체가 무거워진다.
- 캐싱 문제
- 외부 이미지 파일은 브라우저가 캐싱하지만, Data URL로 삽입된 이미지는 HTML이 로드될 때마다 다시 처리된다. 아이콘 같은 작은 이미지(1~2KB)에만 쓰는 게 좋다.
- Base64URL
- 표준 Base64에서 +를 -, /를 _로 바꾸고 패딩(=)을 제거한 형식이다. URL이나 파일명에 안전하게 쓸 수 있어서 JWT에서 이 형식을 사용한다.
Base64는 데이터의 "포장 방식"을 바꾸는 것이지 내용을 감추는 게 아니다. 바이너리를 텍스트로 옮겨야 할 때 쓰는 도구라는 점만 기억하면 실무에서 헷갈릴 일이 없다.