import { source, oneLineTrim } from 'common-tags'; import { Context, MdNode, Parser, HTMLConvertorMap } from '@toast-ui/toastmark'; import { Node, Schema } from 'prosemirror-model'; import { createSpecs } from '@/wysiwyg/specCreator'; import Convertor from '@/convertors/convertor'; import { WwToDOMAdaptor } from '@/wysiwyg/adaptor/wwToDOMAdaptor'; import EventEmitter from '@/event/eventEmitter'; import { ToMdConvertorMap, ToMdConvertorContext, NodeInfo, MarkInfo } from '@t/convertor'; import { createHTMLSchemaMap } from '@/wysiwyg/nodes/html'; import { sanitizeHTML } from '@/sanitizer/htmlSanitizer'; import { createHTMLrenderer } from './markdown/util'; function createSchema() { const specs = createSpecs({}); return new Schema({ nodes: specs.nodes, marks: specs.marks, }); } describe('Convertor', () => { let convertor: Convertor; let schema: Schema; const parser = new Parser({ disallowedHtmlBlockTags: ['br', 'img'], }); function assertConverting(markdown: string, expected: string) { const mdNode = parser.parse(markdown); const wwNode = convertor.toWysiwygModel(mdNode); const result = convertor.toMarkdownText(wwNode!); expect(result).toBe(expected); } beforeEach(() => { schema = createSchema(); convertor = new Convertor(schema, {}, {}, new EventEmitter()); }); describe('should convert between markdown and wysiwyg node to', () => { it('empty content', () => { assertConverting('', ''); }); it('paragraph', () => { const markdown = 'foo'; assertConverting(markdown, markdown); }); it('headings', () => { const markdown = source` # heading1 ## heading2 ### heading3 #### heading4 ##### heading5 ###### heading6 `; const expected = source` # heading1 ## heading2 ### heading3 #### heading4 ##### heading5 ###### heading6 `; assertConverting(markdown, expected); }); it('codeBlock', () => { const markdown = source` \`\`\` foo \`\`\` `; assertConverting(markdown, markdown); }); it('bullet list', () => { const markdown = source` * foo * bar * qux * baz `; assertConverting(markdown, markdown); }); it('ordered list', () => { const markdown = source` 1. foo 2. bar 3. baz `; assertConverting(markdown, markdown); }); it('blockQuote', () => { const markdown = source` > foo > bar >> baz > > qux > >> quxx `; const expected = source` > foo > bar > > baz > > qux > > > quxx `; assertConverting(markdown, expected); }); it('thematicBreak', () => { const markdown = source` --- *** - - - * * * * `; const expected = source` *** *** *** *** `; assertConverting(markdown, expected); }); it('image', () => { const markdown = source` ![](imgUrl) ![altText](imgUrl) ![altText](img*Url) ![altText](url?key=abc&attribute=abc) `; const expected = source` ![](imgUrl) ![altText](imgUrl) ![altText](img*Url) ![altText](url?key=abc&attribute=abc) `; assertConverting(markdown, expected); }); it('link', () => { const markdown = source` [](url)foo [text](url) [text](ur*l) [Editor](https://github.com/nhn_test/tui.editor) [this.is_a_test_link.com](this.is_a_test_link.com) [text](url?key=abc&attribute=abc) `; const expected = source` foo [text](url) [text](ur*l) [Editor](https://github.com/nhn_test/tui.editor) [this.is_a_test_link.com](this.is_a_test_link.com) [text](url?key=abc&attribute=abc) `; assertConverting(markdown, expected); }); it('code', () => { const markdown = '`foo bar baz`'; assertConverting(markdown, markdown); }); it('emphasis (strong, italic) syntax', () => { const markdown = source` **foo** __bar__ *baz* _qux_ `; const expected = source` **foo** **bar** *baz* *qux* `; assertConverting(markdown, expected); }); it('strike', () => { const markdown = '~~strike~~'; assertConverting(markdown, markdown); }); it('table', () => { const markdown = source` | thead | thead | | --- | --- | | tbody | tbody | | thead |thead | | -- | ----- | | tbody|tbody| | tbody|tbody| ||| |-|-| ||| `; const expected = source` | thead | thead | | ----- | ----- | | tbody | tbody | | thead | thead | | ----- | ----- | | tbody | tbody | | tbody | tbody | | | | | --- | --- | | | | `; assertConverting(markdown, `${expected}\n`); }); it('table with column align syntax', () => { const markdown = source` | default | left | right | center | | --- | :--- | ---: | :---: | | tbody | tbody | tbody | tbody | | | | | | | --- | :--- | ---: | :---: | | default | left | right | center | `; const expected = source` | default | left | right | center | | ------- | :--- | ----: | :----: | | tbody | tbody | tbody | tbody | | | | | | | --- | :--- | ---: | :---: | | default | left | right | center | `; assertConverting(markdown, `${expected}\n`); }); it('table with inline syntax', () => { const markdown = source` | ![altText](imgUrl) | foo ![altText](imgUrl) baz | | ---- | ---- | | [linkText](linkUrl) | foo [linkText](linkUrl) baz | | **foo** _bar_ ~~baz~~ | **foo** *bar* ~~baz~~ [linkText](linkUrl) | `; const expected = source` | ![altText](imgUrl) | foo ![altText](imgUrl) baz | | --- | -------- | | [linkText](linkUrl) | foo [linkText](linkUrl) baz | | **foo** *bar* ~~baz~~ | **foo** *bar* ~~baz~~ [linkText](linkUrl) | `; assertConverting(markdown, `${expected}\n`); }); // @TODO: should normalize table cell // it('should normalize wrong table syntax when converting', () => { // const markdown = source` // | col1 | col2 | col3 | // | --- | --- | // | cell1 | cell2 | cell3 | // `; // const expected = source` // | col1 | col2 | col3 | // | ---- | ---- | ---- | // | cell1 | cell2 | | // `; // assertConverting(markdown, `${expected}\n`); // }); it('task', () => { const markdown = source` * [ ] foo * [x] baz * [x] bar 1. [x] foo 2. [ ] bar `; assertConverting(markdown, markdown); }); it('list in blockQuote', () => { const markdown = source` > * foo > * baz > * bar >> 1. qux > > 2. quxx `; const expected = source` > * foo > * baz > * bar > > 1. qux > > 2. quxx `; assertConverting(markdown, expected); }); it('block nodes in list', () => { const markdown = source` 1. foo \`\`\` bar \`\`\` > bam `; const expected = source` 1. foo \`\`\` bar \`\`\` > bam `; assertConverting(markdown, expected); }); it('soft break', () => { const markdown = source` foo bar baz qux `; const expected = source` foo bar baz qux `; assertConverting(markdown, expected); }); it('
', () => { const markdown = source` foo
bar

baz


qux `; const expected = source` foo bar
baz

qux `; assertConverting(markdown, expected); }); it('
with soft break', () => { const markdown = source` foo
bar

baz
qux
quux
quuz `; const expected = source` foo
bar

baz
qux
quux

quuz `; assertConverting(markdown, expected); }); it('
with html inline node', () => { const markdown = source` foo bar Para Word
`; const expected = source` foo bar Para Word `; assertConverting(markdown, expected); }); it('
with following
', () => { const markdown = source` text1
text2

text3 `; const expected = source` text1 text2 text3 `; assertConverting(markdown, expected); }); it('
in the middle of the paragraph', () => { const markdown = source` text1
te
xt2

text3 `; const expected = source` text1 te xt2 text3 `; assertConverting(markdown, expected); }); it('should convert html comment', () => { const markdown = source` `; assertConverting(markdown, markdown); }); }); describe('convert inline html', () => { it('emphasis type', () => { const markdown = source` foo foo foo foo foo foo foo `; assertConverting(markdown, markdown); }); it('link type', () => { const markdown = source` foo test `; assertConverting(markdown, markdown); }); it('table with
', () => { const markdown = source` | thead
thead | thead | | ----- | ----- | | tbody
tbody | tbody | | tbody | tbody
tbody
tbody | | tbody | **tbody**
_tbody_
~~tbody~~
\`tbody\` | | tbody | ![img](imgUrl)
[link](linkUrl) | `; const expected = source` | thead
thead | thead | | ---------- | ----- | | tbody
tbody | tbody | | tbody | tbody
tbody
tbody | | tbody | **tbody**
*tbody*
~~tbody~~
\`tbody\` | | tbody | ![img](imgUrl)
[link](linkUrl) | `; assertConverting(markdown, `${expected}\n`); }); it('table with list', () => { const markdown = source` | thead | | ----- | | | |
  1. ordered
| | | | | |
  1. mix**ed**
| |
  1. mixed
| | foobaz | | ![altText](imgUrl) **mixed** | `; const expected = source` | thead | | ----- | | | |
  1. ordered
| | | | | |
  1. mixed
| |
  1. mixed
| | foobaz | | ![altText](imgUrl) **mixed** | `; assertConverting(markdown, `${expected}\n`); }); it('table with unmatched html list', () => { const markdown = source` | thead | | ----- | |