-
Notifications
You must be signed in to change notification settings - Fork 5
react markdown
이를 위하여 두 가지 선택지가 있었다.
1️⃣ 라이브러리 사용
2️⃣ react markdown editor 직접 구현
react 자체에 대한 학습 부족과 현재의 개발 진행 속도를 고려하여 팀내에서 우선 1️⃣의 방법을 택하였다.
시간이 남는다면, 전체 markdown문법이 아니더라도 대표적인 문법만 고려하여 2️⃣의 방법으로 refactoring 해보는 것도 좋을 것 같다.
리액트에서 markdown과 html을 변환해 가며 사용할 수 있는 다양한 방법과 라이브러리가 있었다.
그 중에서 react-markdown
라이브러리를 사용하게 되었다.
이유는 다양한 props와 플러그인을 통해 선택적으로 적용해볼 수 있고, 무엇보다 공식 repository가 이해하기 쉽게 잘 정리 되어있었기 때문이다.
이하는 공식 repo에서 해당 라이브러리를 사용해야 하는 이유로 명시한 내용
There are other ways for markdown in React out there so why use this one?
The two main reasons are that they often rely on dangerouslySetInnerHTML or have bugs with how they handle markdown.
react-markdown uses a syntax tree to build the virtual dom which allows for updating only the changing DOM instead of completely overwriting.
react-markdown is 100% CommonMark (optionally GFM) compliant and has extensions to support custom syntax.
1️⃣ react-markdown 설치
npm install react-markdown -D
2️⃣ 컴포넌트 사용을 위해 import
import ReactMarkdown from 'react-markdown'
3️⃣ 위에서 import한 ReactMarkdown을 컴포넌트 형태로 사용할 수 있다.
이때 markdown 형식으로 작성된 source를 props로 주면, 옵션에 따른 html 코드로 변환하여 브라우저에 나타내 준다.
<ReactMarkdown source={source}/>
4️⃣ props
공식 repo
공식 repo에서 기본 html효과 적용 및 사용자가 정의한 효과를 적용시키는 방법을 알 수 있다.
renderers에 Node-types : 사용자 정의 callback
의 형태로 원하는 html효과를 만들어 적용할 수 있다.
5️⃣ plugins
plugins
위의 plugins에서 적용하고 싶은 plugin을 npm을 통해 install하고 ReactMarkdown의 plugins props에 설정해주면 된다.
import ReactMarkdown from 'react-markdown';
import gfm from 'remark-gfm';
.
.
.
<ReactMarkdown
plugins={[gfm]} // strikethrough, tables, tasklists and URLs를 지원하기 위한 plugin
source={source} // database로 부터 받아와서 설정할 soruce
skipHtml={false} // 기본값으로 true가 설정되어있다. markdown source안에서 html태그를 무시하지 않도록 false로 option변경
allowDangerousHtml // 리액트에서는 기본적으로 string형태의 html을 허용하지 않으므로 허용을 위해 명시해줘야한다. (cross-site scripting (XSS) 공격을 막기 위함)
renderers={{ // 사용자 정의 html효과 적용 (각각 콜백함수는 직접 작성하여 적용)
blockquote: BlockQuoteBlock,
code: CodeBlock,
inlineCode: InlineCodeBlock,
tableCell: TableCellBlock,
}}
/>