Studying/JavaScript

DOMpurify를 사용하면 iframe 태그를 불러오지 못 하는 이유

Kim Da Ham 2023. 7. 22. 13:50

문제 발생

Portfolly 프로젝트에서 '포트폴리오 등록 페이지'를 구현하던 중, dangerouslySetInnerHTML 를 안전하게 사용하기 위해 DOMpurify를 사용했습니다.

 

그런데 그 결과 <iframe> 태그가 화면에 출력되지 않는 문제가 발생했습니다.

 

 

 

원인

그 이유는 DOMpurify에서 허용하는/허용하지 않는 디폴트 태그/속성이 정해져있기 때문입니다.

 

DOMpurify에서 허용하지 않는 목록 중 <iframe> 태그가 있었던 것입니다.

 

더 다양한 금지 목록은 아래 링크에서 확인할 수 있습니다.

 

 

Default TAGs ATTRIBUTEs allow list & blocklist

DOMPurify - a DOM-only, super-fast, uber-tolerant XSS sanitizer for HTML, MathML and SVG. DOMPurify works with a secure default, but offers a lot of configurability and hooks. Demo: - cure53/DOMPurify

github.com

 

 

 

해결 방법

따라서 별도로 <iframe> 태그를 사용할 수 있게 정의해야 합니다.

 

만약 모든 디폴트 태그 + <iframe> 태그를 허용하고 싶을 경우, 아래 코드와 같이 ADD_TAGS 속성에 "iframe"을 추가합니다.

 

DOMPurify.sanitize(dirty, { ADD_TAGS: ["iframe"], ADD_ATTR: ['allow', 'allowfullscreen', 'frameborder', 'scrolling'] });

 

오직 <iframe> 태그만 허용하고 싶을 경우 아래 코드와 같이 ALLOWED_TAGS 속성에 "iframe"을 추가합니다.

 

DOMPurify.sanitize(dirty, { ALLOWED_TAGS: ["iframe"], ADD_ATTR: ['allow', 'allowfullscreen', 'frameborder', 'scrolling'] });

 

 

저는 '포트폴리오 등록' 페이지에서 에디터가 다룰 수 있는 HTML만 허용하고 싶었고, 따라서 다음과 같이 코드를 정리해봤습니다.

 

import dompurify from "dompurify";

const headings = ['h1', 'h2', 'h3', 'h4', 'h5', 'h6'];
const media = ['iframe', 'img'];
const inlineElements = ['span', 'u', 'a', 'strong', 's', 'em'];
const blockElements = ['p', 'br'];

const ALLOWED_TAGS = [...headings, ...media, ...inlineElements, ...blockElements];

const sanitizer = dompurify.sanitize;

const sanitize = (htmlContent: string) => {
return sanitizer(htmlContent,
  {
    ALLOWED_TAGS: ALLOWED_TAGS,
    ADD_ATTR: ['allow', 'allowfullscreen', 'frameborder', 'scrolling', 'href']
  })
};

 

 

처음엔 이렇게 하나하나 노가다 식으로 원하는 태그를 추가하는 게 맞는 건가...? 싶었는데, 멘토님께서 괜찮다고 하셔서 안심하고 사용했습니다.

 

 

 

참고 사이트

 

How to allow an iframe tag in `dompurify` including all of its attributes

I want dompurify to allow iframe tags, and I add iframe as an exception(ADD_TAGS). But that removes some attributes of it. I want all attributes to be there. <!doctype html> <html> ...

stackoverflow.com