HTML 엔티티 변환, 5개 문자 인코딩 규칙

게시글이나 템플릿에 코드나 특수문자가 포함된 텍스트를 그대로 노출하려다 태그로 해석되거나 화면이 깨지는 문제는, 부등호·앰퍼샌드·따옴표 다섯 문자를 정해진 HTML 엔티티로 바꾸면 해결됩니다. 반대로 '이나 … 같은 엔티티가 코드 그대로 노출됐다면, 정해진 규칙에 따라 원래 문자로 되돌리면 됩니다. 이 글은 그 인코딩·디코딩이 실제로 어떤 순서와 규칙으로 계산되는지를 정리합니다.

요약 ① 인코딩은 & < > " ' 다섯 문자를 순서대로 &amp; &lt; &gt; &quot; &#39;로 바꾸며, &를 가장 먼저 처리합니다. ② 디코딩은 &#39;·&#x27; 같은 10진수·16진수 숫자 엔티티와 &amp;·&hellip; 같은 명명된 엔티티를 원래 문자로 되돌립니다. ③ 범위를 벗어난 숫자나 등록되지 않은 이름은 변환되지 않고 입력한 그대로 남습니다.

코드나 특수문자가 화면에서 깨지는 이유

HTML 문서에서 꺾쇠괄호(< >)는 태그를 여닫는 신호이고, 앰퍼샌드(&)는 엔티티가 시작된다는 신호입니다. 브라우저는 이 문자를 보면 화면에 그대로 찍지 않고 태그나 엔티티의 일부로 해석하려 합니다.

블로그나 게시판 본문에 코드를 그대로 붙여넣을 때 이 차이가 드러납니다. <p class="box">텍스트</p> 같은 예시 코드를 그대로 붙이면, 브라우저는 이걸 글자로 보여주는 대신 실제 태그로 해석해 화면에서 사라지거나 레이아웃이 깨집니다.

따옴표가 포함된 속성값도 마찬가지로, 편집기에 따라 앞뒤 텍스트가 잘려나가는 경우가 있습니다.

반대 방향의 문제도 있습니다. 어딘가에서 복사한 텍스트에 &#39;이나 &amp;처럼 엔티티가 코드 형태 그대로 노출되는 경우입니다. 원래는 작은따옴표나 앰퍼샌드로 보여야 할 자리인데, 인코딩된 값을 디코딩하지 않고 그대로 옮겨 붙였을 때 이렇게 남습니다.

도구 없이 직접 계산하는 방법

인코딩이 계산되는 방식

인코딩은 다섯 문자를 정해진 엔티티로 바꾸는 표 대응입니다. 아래 표대로 문자열을 하나씩 치환하면 도구와 같은 결과가 나옵니다.

문자엔티티코드포인트
&&amp;U+0026 (10진수 38)
<&lt;U+003C (10진수 60)
>&gt;U+003E (10진수 62)
"&quot;U+0022 (10진수 34)
'&#39;U+0027 (10진수 39)

순서가 중요합니다. &부터 먼저 바꿔야 합니다. <를 먼저 &lt;로 바꾼 뒤에 &를 처리하면, 방금 만든 &lt; 안의 &까지 다시 걸려 &amp;lt;로 바뀌어 버립니다. &를 가장 먼저 처리하면 이 문제가 생기지 않습니다.

디코딩이 계산되는 방식

디코딩은 반대로, 문자열에서 &로 시작해 ;로 끝나는 조각을 찾아 원래 문자로 되돌리는 작업입니다. &로 시작하지만 뒤에 ;이 없는 문자열은 애초에 엔티티 패턴으로 인식되지 않습니다.

숫자로 시작하는 조각(&#39;, &#x27;)은 # 뒤의 숫자를 코드포인트로 읽습니다. 앞에 x나 X가 있으면 16진수, 없으면 10진수입니다. 예를 들어 10진수 39와 16진수 27은 둘 다 U+0027, 즉 작은따옴표를 가리키는 같은 코드포인트입니다.

이름으로 된 조각(&amp;, &hellip;)은 정해진 이름표에서 찾아 바꿉니다. amp(&), lt(<), gt(>), quot("), apos('), nbsp(공백), copy(©), reg(®), trade(™), hellip(…), mdash(—), ndash(–), middot(·), deg(°), euro(€), won(₩) — 이 열여섯 개가 대표적으로 쓰이는 이름입니다.

HTML 표준에는 이보다 훨씬 많은 명명된 문자 참조가 정의돼 있지만, 이름이 없는 문자라도 숫자 코드포인트로는 항상 표현할 수 있습니다. 특정 문자의 코드포인트는 운영체제 문자표(윈도우 문자표, macOS 문자 뷰어)나 유니코드 공식 차트에서 확인할 수 있습니다.

HTML 엔티티 인코드·디코드

입력한 텍스트는 서버로 전송되지 않고, 키를 입력할 때마다 브라우저 안에서 즉시 계산됩니다.

헷갈리기 쉬운 지점

가장 흔한 실수는 이미 엔티티로 바뀐 텍스트를 다시 인코딩하는 것입니다. 인코딩은 문맥을 판단하지 않고 &부터 순서대로 무조건 치환하기 때문에, 이미 &lt;인 텍스트를 다시 인코딩하면 그 안의 &까지 바뀌어 &amp;lt;라는 이중 인코딩 결과가 나옵니다.

디코딩 쪽에서는 반대로 "왜 안 바뀌지"라는 혼란이 자주 생깁니다. 등록되지 않은 이름이나 유효 범위를 벗어난 숫자는 안전하게 원문 그대로 남기도록 되어 있기 때문입니다.

상황실제 처리 결과
이미 인코딩된 텍스트를 다시 인코딩&가 다시 &amp;로 바뀌어 이중 인코딩됩니다 (예: &lt;&amp;lt;)
표에 없는 이름 (예: &foo;)변환되지 않고 입력한 그대로 남습니다
유효 범위를 벗어난 숫자 (예: &#x110000;, U+10FFFF 초과)코드포인트로 변환할 수 없어 그대로 남습니다
대문자로 쓴 이름 (예: &AMP;)이름 조회는 대소문자를 구분하지 않아 정상 변환됩니다
&로 시작하지만 뒤에 ;이 없는 문자열엔티티 패턴이 아니므로 애초에 디코딩 대상이 아닙니다

인코딩 결과는 항상 소문자 형태(&amp; &lt; &gt; &quot; &#39;)로만 나옵니다. 대문자 이름(&AMP; 등)은 디코딩할 때만 인식되고, 인코딩 결과로는 나오지 않습니다.

정리

  • 인코딩 대상은 & < > " ' 다섯 문자뿐이고, &가 가장 먼저 바뀝니다.
  • 디코딩은 10진수(&#39;)·16진수(&#x27;) 숫자 엔티티와 정해진 이름표의 명명된 엔티티를 원래 문자로 되돌립니다.
  • 표에 없는 이름이나 유효 범위를 벗어난 숫자는 변환되지 않고 입력한 그대로 남습니다.
  • 이미 엔티티로 바뀐 텍스트를 다시 인코딩하면 &가 또 바뀌어 이중 인코딩이 됩니다.
  • 계산은 브라우저 안에서 입력할 때마다 즉시 이뤄지며 서버로 전송되지 않습니다.
HTML 엔티티 인코드·디코드

입력한 텍스트는 서버로 전송되지 않고, 키를 입력할 때마다 브라우저 안에서 즉시 계산됩니다.

자주 묻는 질문

어떤 문자가 몇 개나 인코딩되나요?

& < > " ' 다섯 문자입니다. &amp; &lt; &gt; &quot; &#39; 순서로, &가 가장 먼저 처리됩니다. 이 순서 때문에 나중에 만들어진 엔티티 안의 &가 다시 바뀌는 이중 인코딩이 방지됩니다.

&#39;&#x27;은 같은 뜻인가요?

네, 같습니다. 39는 10진수, 27은 16진수 표기이고 둘 다 U+0027, 즉 작은따옴표를 가리킵니다. 표기만 다를 뿐 디코딩 결과는 동일합니다.

알 수 없는 엔티티 이름을 넣으면 어떻게 되나요?

지원하는 이름표(amp, lt, gt, quot, apos, nbsp, copy, reg, trade, hellip, mdash, ndash, middot, deg, euro, won)에 없으면 변환하지 않고 입력한 그대로 남깁니다. 오류 표시 없이 원문을 보존하는 방식입니다.

입력한 텍스트가 서버로 전송되나요?

아니요. 인코딩·디코딩 계산은 모두 브라우저 안에서만 이뤄지며, 입력한 텍스트는 서버로 전송되거나 저장되지 않습니다. 키를 입력할 때마다 결과가 즉시 다시 계산됩니다.

가격 보기카톡 무료 상담