123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963964965966967968969970971972973974975976977978979980981982983984985986987988989990991992993994995996997998999100010011002100310041005100610071008100910101011101210131014101510161017101810191020102110221023102410251026102710281029103010311032103310341035103610371038103910401041104210431044104510461047104810491050105110521053105410551056105710581059106010611062106310641065106610671068106910701071107210731074107510761077107810791080108110821083108410851086108710881089109010911092109310941095109610971098109911001101110211031104110511061107110811091110111111121113111411151116111711181119112011211122112311241125112611271128112911301131113211331134113511361137113811391140114111421143114411451146114711481149115011511152115311541155115611571158115911601161116211631164116511661167116811691170117111721173117411751176117711781179118011811182118311841185118611871188118911901191119211931194119511961197119811991200120112021203120412051206120712081209121012111212121312141215121612171218121912201221122212231224122512261227122812291230123112321233123412351236123712381239124012411242124312441245124612471248124912501251125212531254125512561257125812591260126112621263126412651266126712681269127012711272127312741275127612771278127912801281128212831284128512861287128812891290129112921293129412951296129712981299130013011302130313041305130613071308130913101311131213131314131513161317 |
- // CodeMirror, copyright (c) by Marijn Haverbeke and others
- // Distributed under an MIT license: https://codemirror.net/LICENSE
- (function() {
- var config = {tabSize: 4, indentUnit: 2}
- var mode = CodeMirror.getMode(config, "markdown");
- function MT(name) { test.mode(name, mode, Array.prototype.slice.call(arguments, 1)); }
- var modeHighlightFormatting = CodeMirror.getMode(config, {name: "markdown", highlightFormatting: true});
- function FT(name) { test.mode(name, modeHighlightFormatting, Array.prototype.slice.call(arguments, 1)); }
- var modeMT_noXml = CodeMirror.getMode(config, {name: "markdown", xml: false});
- function MT_noXml(name) { test.mode(name, modeMT_noXml, Array.prototype.slice.call(arguments, 1)); }
- var modeMT_noFencedHighlight = CodeMirror.getMode(config, {name: "markdown", fencedCodeBlockHighlighting: false});
- function MT_noFencedHighlight(name) { test.mode(name, modeMT_noFencedHighlight, Array.prototype.slice.call(arguments, 1)); }
- var modeAtxNoSpace = CodeMirror.getMode(config, {name: "markdown", allowAtxHeaderWithoutSpace: true});
- function AtxNoSpaceTest(name) { test.mode(name, modeAtxNoSpace, Array.prototype.slice.call(arguments, 1)); }
- var modeOverrideClasses = CodeMirror.getMode(config, {
- name: "markdown",
- strikethrough: true,
- emoji: true,
- tokenTypeOverrides: {
- "header" : "override-header",
- "code" : "override-code",
- "quote" : "override-quote",
- "list1" : "override-list1",
- "list2" : "override-list2",
- "list3" : "override-list3",
- "hr" : "override-hr",
- "image" : "override-image",
- "imageAltText": "override-image-alt-text",
- "imageMarker": "override-image-marker",
- "linkInline" : "override-link-inline",
- "linkEmail" : "override-link-email",
- "linkText" : "override-link-text",
- "linkHref" : "override-link-href",
- "em" : "override-em",
- "strong" : "override-strong",
- "strikethrough" : "override-strikethrough",
- "emoji" : "override-emoji"
- }});
- function TokenTypeOverrideTest(name) { test.mode(name, modeOverrideClasses, Array.prototype.slice.call(arguments, 1)); }
- var modeFormattingOverride = CodeMirror.getMode(config, {
- name: "markdown",
- highlightFormatting: true,
- tokenTypeOverrides: {
- "formatting" : "override-formatting"
- }});
- function FormatTokenTypeOverrideTest(name) { test.mode(name, modeFormattingOverride, Array.prototype.slice.call(arguments, 1)); }
- var modeET = CodeMirror.getMode(config, {name: "markdown", emoji: true});
- function ET(name) { test.mode(name, modeET, Array.prototype.slice.call(arguments, 1)); }
- FT("formatting_emAsterisk",
- "[em&formatting&formatting-em *][em foo][em&formatting&formatting-em *]");
- FT("formatting_emUnderscore",
- "[em&formatting&formatting-em _][em foo][em&formatting&formatting-em _]");
- FT("formatting_strongAsterisk",
- "[strong&formatting&formatting-strong **][strong foo][strong&formatting&formatting-strong **]");
- FT("formatting_strongUnderscore",
- "[strong&formatting&formatting-strong __][strong foo][strong&formatting&formatting-strong __]");
- FT("formatting_codeBackticks",
- "[comment&formatting&formatting-code `][comment foo][comment&formatting&formatting-code `]");
- FT("formatting_doubleBackticks",
- "[comment&formatting&formatting-code ``][comment foo ` bar][comment&formatting&formatting-code ``]");
- FT("formatting_atxHeader",
- "[header&header-1&formatting&formatting-header&formatting-header-1 # ][header&header-1 foo # bar ][header&header-1&formatting&formatting-header&formatting-header-1 #]");
- FT("formatting_setextHeader",
- "[header&header-1 foo]",
- "[header&header-1&formatting&formatting-header&formatting-header-1 =]");
- FT("formatting_blockquote",
- "[quote"e-1&formatting&formatting-quote&formatting-quote-1 > ][quote"e-1 foo]");
- FT("formatting_list",
- "[variable-2&formatting&formatting-list&formatting-list-ul - ][variable-2 foo]");
- FT("formatting_list",
- "[variable-2&formatting&formatting-list&formatting-list-ol 1. ][variable-2 foo]");
- FT("formatting_link",
- "[link&formatting&formatting-link [][link foo][link&formatting&formatting-link ]]][string&formatting&formatting-link-string&url (][string&url http://example.com/][string&formatting&formatting-link-string&url )]");
- FT("formatting_linkReference",
- "[link&formatting&formatting-link [][link foo][link&formatting&formatting-link ]]][string&formatting&formatting-link-string&url [][string&url bar][string&formatting&formatting-link-string&url ]]]",
- "[link&formatting&formatting-link [][link bar][link&formatting&formatting-link ]]:] [string&url http://example.com/]");
- FT("formatting_linkWeb",
- "[link&formatting&formatting-link <][link http://example.com/][link&formatting&formatting-link >]");
- FT("formatting_linkEmail",
- "[link&formatting&formatting-link <][link user@example.com][link&formatting&formatting-link >]");
- FT("formatting_escape",
- "[formatting-escape \\*]");
- FT("formatting_image",
- "[formatting&formatting-image&image&image-marker !][formatting&formatting-image&image&image-alt-text&link [[][image&image-alt-text&link alt text][formatting&formatting-image&image&image-alt-text&link ]]][formatting&formatting-link-string&string&url (][url&string http://link.to/image.jpg][formatting&formatting-link-string&string&url )]");
- FT("codeBlock",
- "[comment&formatting&formatting-code-block ```css]",
- "[tag foo]",
- "[comment&formatting&formatting-code-block ```]");
- MT("plainText",
- "foo");
- // Don't style single trailing space
- MT("trailingSpace1",
- "foo ");
- // Two or more trailing spaces should be styled with line break character
- MT("trailingSpace2",
- "foo[trailing-space-a ][trailing-space-new-line ]");
- MT("trailingSpace3",
- "foo[trailing-space-a ][trailing-space-b ][trailing-space-new-line ]");
- MT("trailingSpace4",
- "foo[trailing-space-a ][trailing-space-b ][trailing-space-a ][trailing-space-new-line ]");
- // Code blocks using 4 spaces (regardless of CodeMirror.tabSize value)
- MT("codeBlocksUsing4Spaces",
- " [comment foo]");
- // Code blocks using 4 spaces with internal indentation
- MT("codeBlocksUsing4SpacesIndentation",
- " [comment bar]",
- " [comment hello]",
- " [comment world]",
- " [comment foo]",
- "bar");
- // Code blocks should end even after extra indented lines
- MT("codeBlocksWithTrailingIndentedLine",
- " [comment foo]",
- " [comment bar]",
- " [comment baz]",
- " ",
- "hello");
- // Code blocks using 1 tab (regardless of CodeMirror.indentWithTabs value)
- MT("codeBlocksUsing1Tab",
- "\t[comment foo]");
- // No code blocks directly after paragraph
- // http://spec.commonmark.org/0.19/#example-65
- MT("noCodeBlocksAfterParagraph",
- "Foo",
- " Bar");
- MT("codeBlocksAfterATX",
- "[header&header-1 # foo]",
- " [comment code]");
- MT("codeBlocksAfterSetext",
- "[header&header-2 foo]",
- "[header&header-2 ---]",
- " [comment code]");
- MT("codeBlocksAfterFencedCode",
- "[comment ```]",
- "[comment foo]",
- "[comment ```]",
- " [comment code]");
- // Inline code using backticks
- MT("inlineCodeUsingBackticks",
- "foo [comment `bar`]");
- // Block code using single backtick (shouldn't work)
- MT("blockCodeSingleBacktick",
- "[comment `]",
- "[comment foo]",
- "[comment `]");
- // Unclosed backticks
- // Instead of simply marking as CODE, it would be nice to have an
- // incomplete flag for CODE, that is styled slightly different.
- MT("unclosedBackticks",
- "foo [comment `bar]");
- // Per documentation: "To include a literal backtick character within a
- // code span, you can use multiple backticks as the opening and closing
- // delimiters"
- MT("doubleBackticks",
- "[comment ``foo ` bar``]");
- // Tests based on Dingus
- // http://daringfireball.net/projects/markdown/dingus
- //
- // Multiple backticks within an inline code block
- MT("consecutiveBackticks",
- "[comment `foo```bar`]");
- // Multiple backticks within an inline code block with a second code block
- MT("consecutiveBackticks",
- "[comment `foo```bar`] hello [comment `world`]");
- // Unclosed with several different groups of backticks
- MT("unclosedBackticks",
- "[comment ``foo ``` bar` hello]");
- // Closed with several different groups of backticks
- MT("closedBackticks",
- "[comment ``foo ``` bar` hello``] world");
- // info string cannot contain backtick, thus should result in inline code
- MT("closingFencedMarksOnSameLine",
- "[comment ``` code ```] foo");
- // atx headers
- // http://daringfireball.net/projects/markdown/syntax#header
- MT("atxH1",
- "[header&header-1 # foo]");
- MT("atxH2",
- "[header&header-2 ## foo]");
- MT("atxH3",
- "[header&header-3 ### foo]");
- MT("atxH4",
- "[header&header-4 #### foo]");
- MT("atxH5",
- "[header&header-5 ##### foo]");
- MT("atxH6",
- "[header&header-6 ###### foo]");
- // http://spec.commonmark.org/0.19/#example-24
- MT("noAtxH7",
- "####### foo");
- // http://spec.commonmark.org/0.19/#example-25
- MT("noAtxH1WithoutSpace",
- "#5 bolt");
- // CommonMark requires a space after # but most parsers don't
- AtxNoSpaceTest("atxNoSpaceAllowed_H1NoSpace",
- "[header&header-1 #foo]");
- AtxNoSpaceTest("atxNoSpaceAllowed_H4NoSpace",
- "[header&header-4 ####foo]");
- AtxNoSpaceTest("atxNoSpaceAllowed_H1Space",
- "[header&header-1 # foo]");
- // Inline styles should be parsed inside headers
- MT("atxH1inline",
- "[header&header-1 # foo ][header&header-1&em *bar*]");
- MT("atxIndentedTooMuch",
- "[header&header-1 # foo]",
- " [comment # bar]");
- // disable atx inside blockquote until we implement proper blockquote inner mode
- // TODO: fix to be CommonMark-compliant
- MT("atxNestedInsideBlockquote",
- "[quote"e-1 > # foo]");
- MT("atxAfterBlockquote",
- "[quote"e-1 > foo]",
- "[header&header-1 # bar]");
- // Setext headers - H1, H2
- // Per documentation, "Any number of underlining =’s or -’s will work."
- // http://daringfireball.net/projects/markdown/syntax#header
- // Ideally, the text would be marked as `header` as well, but this is
- // not really feasible at the moment. So, instead, we're testing against
- // what works today, to avoid any regressions.
- //
- // Check if single underlining = works
- MT("setextH1",
- "[header&header-1 foo]",
- "[header&header-1 =]");
- // Check if 3+ ='s work
- MT("setextH1",
- "[header&header-1 foo]",
- "[header&header-1 ===]");
- // Check if single underlining - works
- MT("setextH2",
- "[header&header-2 foo]",
- "[header&header-2 -]");
- // Check if 3+ -'s work
- MT("setextH2",
- "[header&header-2 foo]",
- "[header&header-2 ---]");
- // http://spec.commonmark.org/0.19/#example-45
- MT("setextH2AllowSpaces",
- "[header&header-2 foo]",
- " [header&header-2 ---- ]");
- // http://spec.commonmark.org/0.19/#example-44
- MT("noSetextAfterIndentedCodeBlock",
- " [comment foo]",
- "[hr ---]");
- MT("setextAfterFencedCode",
- "[comment ```]",
- "[comment foo]",
- "[comment ```]",
- "[header&header-2 bar]",
- "[header&header-2 ---]");
- MT("setextAferATX",
- "[header&header-1 # foo]",
- "[header&header-2 bar]",
- "[header&header-2 ---]");
- // http://spec.commonmark.org/0.19/#example-51
- MT("noSetextAfterQuote",
- "[quote"e-1 > foo]",
- "[hr ---]",
- "",
- "[quote"e-1 > foo]",
- "[quote"e-1 bar]",
- "[hr ---]");
- MT("noSetextAfterList",
- "[variable-2 - foo]",
- "[hr ---]");
- MT("noSetextAfterList_listContinuation",
- "[variable-2 - foo]",
- "bar",
- "[hr ---]");
- MT("setextAfterList_afterIndentedCode",
- "[variable-2 - foo]",
- "",
- " [comment bar]",
- "[header&header-2 baz]",
- "[header&header-2 ---]");
- MT("setextAfterList_afterFencedCodeBlocks",
- "[variable-2 - foo]",
- "",
- " [comment ```]",
- " [comment bar]",
- " [comment ```]",
- "[header&header-2 baz]",
- "[header&header-2 ---]");
- MT("setextAfterList_afterHeader",
- "[variable-2 - foo]",
- " [variable-2&header&header-1 # bar]",
- "[header&header-2 baz]",
- "[header&header-2 ---]");
- MT("setextAfterList_afterHr",
- "[variable-2 - foo]",
- "",
- " [hr ---]",
- "[header&header-2 bar]",
- "[header&header-2 ---]");
- MT("setext_nestedInlineMarkup",
- "[header&header-1 foo ][em&header&header-1 *bar*]",
- "[header&header-1 =]");
- MT("setext_linkDef",
- "[link [[aaa]]:] [string&url http://google.com 'title']",
- "[hr ---]");
- // currently, looks max one line ahead, thus won't catch valid CommonMark
- // markup
- MT("setext_oneLineLookahead",
- "foo",
- "[header&header-1 bar]",
- "[header&header-1 =]");
- // ensure we don't regard space after dash as a list
- MT("setext_emptyList",
- "[header&header-2 foo]",
- "[header&header-2 - ]",
- "foo");
- // Single-line blockquote with trailing space
- MT("blockquoteSpace",
- "[quote"e-1 > foo]");
- // Single-line blockquote
- MT("blockquoteNoSpace",
- "[quote"e-1 >foo]");
- // No blank line before blockquote
- MT("blockquoteNoBlankLine",
- "foo",
- "[quote"e-1 > bar]");
- MT("blockquoteNested",
- "[quote"e-1 > foo]",
- "[quote"e-1 >][quote"e-2 > foo]",
- "[quote"e-1 >][quote"e-2 >][quote"e-3 > foo]");
- // ensure quote-level is inferred correctly even if indented
- MT("blockquoteNestedIndented",
- " [quote"e-1 > foo]",
- " [quote"e-1 >][quote"e-2 > foo]",
- " [quote"e-1 >][quote"e-2 >][quote"e-3 > foo]");
- // ensure quote-level is inferred correctly even if indented
- MT("blockquoteIndentedTooMuch",
- "foo",
- " > bar");
- // Single-line blockquote followed by normal paragraph
- MT("blockquoteThenParagraph",
- "[quote"e-1 >foo]",
- "",
- "bar");
- // Multi-line blockquote (lazy mode)
- MT("multiBlockquoteLazy",
- "[quote"e-1 >foo]",
- "[quote"e-1 bar]");
- // Multi-line blockquote followed by normal paragraph (lazy mode)
- MT("multiBlockquoteLazyThenParagraph",
- "[quote"e-1 >foo]",
- "[quote"e-1 bar]",
- "",
- "hello");
- // Multi-line blockquote (non-lazy mode)
- MT("multiBlockquote",
- "[quote"e-1 >foo]",
- "[quote"e-1 >bar]");
- // Multi-line blockquote followed by normal paragraph (non-lazy mode)
- MT("multiBlockquoteThenParagraph",
- "[quote"e-1 >foo]",
- "[quote"e-1 >bar]",
- "",
- "hello");
- // disallow lists inside blockquote for now because it causes problems outside blockquote
- // TODO: fix to be CommonMark-compliant
- MT("listNestedInBlockquote",
- "[quote"e-1 > - foo]");
- // disallow fenced blocks inside blockquote because it causes problems outside blockquote
- // TODO: fix to be CommonMark-compliant
- MT("fencedBlockNestedInBlockquote",
- "[quote"e-1 > ```]",
- "[quote"e-1 > code]",
- "[quote"e-1 > ```]",
- // ensure we still allow inline code
- "[quote"e-1 > ][quote"e-1&comment `code`]");
- // Header with leading space after continued blockquote (#3287, negative indentation)
- MT("headerAfterContinuedBlockquote",
- "[quote"e-1 > foo]",
- "[quote"e-1 bar]",
- "",
- " [header&header-1 # hello]");
- // Check list types
- MT("listAsterisk",
- "foo",
- "bar",
- "",
- "[variable-2 * foo]",
- "[variable-2 * bar]");
- MT("listPlus",
- "foo",
- "bar",
- "",
- "[variable-2 + foo]",
- "[variable-2 + bar]");
- MT("listDash",
- "foo",
- "bar",
- "",
- "[variable-2 - foo]",
- "[variable-2 - bar]");
- MT("listNumber",
- "foo",
- "bar",
- "",
- "[variable-2 1. foo]",
- "[variable-2 2. bar]");
- MT("listFromParagraph",
- "foo",
- "[variable-2 1. bar]",
- "[variable-2 2. hello]");
- // List after hr
- MT("listAfterHr",
- "[hr ---]",
- "[variable-2 - bar]");
- // List after header
- MT("listAfterHeader",
- "[header&header-1 # foo]",
- "[variable-2 - bar]");
- // hr after list
- MT("hrAfterList",
- "[variable-2 - foo]",
- "[hr -----]");
- MT("hrAfterFencedCode",
- "[comment ```]",
- "[comment code]",
- "[comment ```]",
- "[hr ---]");
- // allow hr inside lists
- // (require prev line to be empty or hr, TODO: non-CommonMark-compliant)
- MT("hrInsideList",
- "[variable-2 - foo]",
- "",
- " [hr ---]",
- " [hr ---]",
- "",
- " [comment ---]");
- MT("consecutiveHr",
- "[hr ---]",
- "[hr ---]",
- "[hr ---]");
- // Formatting in lists (*)
- MT("listAsteriskFormatting",
- "[variable-2 * ][variable-2&em *foo*][variable-2 bar]",
- "[variable-2 * ][variable-2&strong **foo**][variable-2 bar]",
- "[variable-2 * ][variable-2&em&strong ***foo***][variable-2 bar]",
- "[variable-2 * ][variable-2&comment `foo`][variable-2 bar]");
- // Formatting in lists (+)
- MT("listPlusFormatting",
- "[variable-2 + ][variable-2&em *foo*][variable-2 bar]",
- "[variable-2 + ][variable-2&strong **foo**][variable-2 bar]",
- "[variable-2 + ][variable-2&em&strong ***foo***][variable-2 bar]",
- "[variable-2 + ][variable-2&comment `foo`][variable-2 bar]");
- // Formatting in lists (-)
- MT("listDashFormatting",
- "[variable-2 - ][variable-2&em *foo*][variable-2 bar]",
- "[variable-2 - ][variable-2&strong **foo**][variable-2 bar]",
- "[variable-2 - ][variable-2&em&strong ***foo***][variable-2 bar]",
- "[variable-2 - ][variable-2&comment `foo`][variable-2 bar]");
- // Formatting in lists (1.)
- MT("listNumberFormatting",
- "[variable-2 1. ][variable-2&em *foo*][variable-2 bar]",
- "[variable-2 2. ][variable-2&strong **foo**][variable-2 bar]",
- "[variable-2 3. ][variable-2&em&strong ***foo***][variable-2 bar]",
- "[variable-2 4. ][variable-2&comment `foo`][variable-2 bar]");
- // Paragraph lists
- MT("listParagraph",
- "[variable-2 * foo]",
- "",
- "[variable-2 * bar]");
- // Multi-paragraph lists
- //
- // 4 spaces
- MT("listMultiParagraph",
- "[variable-2 * foo]",
- "",
- "[variable-2 * bar]",
- "",
- " [variable-2 hello]");
- // 4 spaces, extra blank lines (should still be list, per Dingus)
- MT("listMultiParagraphExtra",
- "[variable-2 * foo]",
- "",
- "[variable-2 * bar]",
- "",
- "",
- " [variable-2 hello]");
- // 4 spaces, plus 1 space (should still be list, per Dingus)
- MT("listMultiParagraphExtraSpace",
- "[variable-2 * foo]",
- "",
- "[variable-2 * bar]",
- "",
- " [variable-2 hello]",
- "",
- " [variable-2 world]");
- // 1 tab
- MT("listTab",
- "[variable-2 * foo]",
- "",
- "[variable-2 * bar]",
- "",
- "\t[variable-2 hello]");
- // No indent
- MT("listNoIndent",
- "[variable-2 * foo]",
- "",
- "[variable-2 * bar]",
- "",
- "hello");
- MT("listCommonMarkIndentationCode",
- "[variable-2 * Code blocks also affect]",
- " [variable-3 * The next level starts where the contents start.]",
- " [variable-3 * Anything less than that will keep the item on the same level.]",
- " [variable-3 * Each list item can indent the first level further and further.]",
- " [variable-3 * For the most part, this makes sense while writing a list.]",
- " [keyword * This means two items with same indentation can be different levels.]",
- " [keyword * Each level has an indent requirement that can change between items.]",
- " [keyword * A list item that meets this will be part of the next level.]",
- " [variable-3 * Otherwise, it will be part of the level where it does meet this.]",
- " [variable-2 * World]");
- // should handle nested and un-nested lists
- MT("listCommonMark_MixedIndents",
- "[variable-2 * list1]",
- " [variable-2 list1]",
- " [variable-2&header&header-1 # heading still part of list1]",
- " [variable-2 text after heading still part of list1]",
- "",
- " [comment indented codeblock]",
- " [variable-2 list1 after code block]",
- " [variable-3 * list2]",
- // amount of spaces on empty lines between lists doesn't matter
- " ",
- // extra empty lines irrelevant
- "",
- "",
- " [variable-3 indented text part of list2]",
- " [keyword * list3]",
- "",
- " [variable-3 text at level of list2]",
- "",
- " [variable-2 de-indented text part of list1 again]",
- "",
- " [variable-2&comment ```]",
- " [comment code]",
- " [variable-2&comment ```]",
- "",
- " [variable-2 text after fenced code]");
- // should correctly parse numbered list content indentation
- MT("listCommonMark_NumeberedListIndent",
- "[variable-2 1000. list with base indent of 6]",
- "",
- " [variable-2 text must be indented 6 spaces at minimum]",
- "",
- " [variable-2 9-spaces indented text still part of list]",
- "",
- " [comment indented codeblock starts at 10 spaces]",
- "",
- " [comment text indented by 5 spaces no longer belong to list]");
- // should consider tab as 4 spaces
- MT("listCommonMark_TabIndented",
- "[variable-2 * list]",
- "\t[variable-3 * list2]",
- "",
- "\t\t[variable-3 part of list2]");
- MT("listAfterBlockquote",
- "[quote"e-1 > foo]",
- "[variable-2 - bar]");
- // shouldn't create sublist if it's indented more than allowed
- MT("nestedListIndentedTooMuch",
- "[variable-2 - foo]",
- " [variable-2 - bar]");
- MT("listIndentedTooMuchAfterParagraph",
- "foo",
- " - bar");
- // Blockquote
- MT("blockquote",
- "[variable-2 * foo]",
- "",
- "[variable-2 * bar]",
- "",
- " [variable-2"e"e-1 > hello]");
- // Code block
- MT("blockquoteCode",
- "[variable-2 * foo]",
- "",
- "[variable-2 * bar]",
- "",
- " [comment > hello]",
- "",
- " [variable-2 world]");
- // Code block followed by text
- MT("blockquoteCodeText",
- "[variable-2 * foo]",
- "",
- " [variable-2 bar]",
- "",
- " [comment hello]",
- "",
- " [variable-2 world]");
- // Nested list
- MT("listAsteriskNested",
- "[variable-2 * foo]",
- "",
- " [variable-3 * bar]");
- MT("listPlusNested",
- "[variable-2 + foo]",
- "",
- " [variable-3 + bar]");
- MT("listDashNested",
- "[variable-2 - foo]",
- "",
- " [variable-3 - bar]");
- MT("listNumberNested",
- "[variable-2 1. foo]",
- "",
- " [variable-3 2. bar]");
- MT("listMixed",
- "[variable-2 * foo]",
- "",
- " [variable-3 + bar]",
- "",
- " [keyword - hello]",
- "",
- " [variable-2 1. world]");
- MT("listBlockquote",
- "[variable-2 * foo]",
- "",
- " [variable-3 + bar]",
- "",
- " [quote"e-1&variable-3 > hello]");
- MT("listCode",
- "[variable-2 * foo]",
- "",
- " [variable-3 + bar]",
- "",
- " [comment hello]");
- // Code with internal indentation
- MT("listCodeIndentation",
- "[variable-2 * foo]",
- "",
- " [comment bar]",
- " [comment hello]",
- " [comment world]",
- " [comment foo]",
- " [variable-2 bar]");
- // List nesting edge cases
- MT("listNested",
- "[variable-2 * foo]",
- "",
- " [variable-3 * bar]",
- "",
- " [variable-3 hello]"
- );
- MT("listNested",
- "[variable-2 * foo]",
- "",
- " [variable-3 * bar]",
- "",
- " [keyword * foo]"
- );
- // Code followed by text
- MT("listCodeText",
- "[variable-2 * foo]",
- "",
- " [comment bar]",
- "",
- "hello");
- // Following tests directly from official Markdown documentation
- // http://daringfireball.net/projects/markdown/syntax#hr
- MT("hrSpace",
- "[hr * * *]");
- MT("hr",
- "[hr ***]");
- MT("hrLong",
- "[hr *****]");
- MT("hrSpaceDash",
- "[hr - - -]");
- MT("hrDashLong",
- "[hr ---------------------------------------]");
- //Images
- MT("Images",
- "[image&image-marker !][image&image-alt-text&link [[alt text]]][string&url (http://link.to/image.jpg)]")
- //Images with highlight alt text
- MT("imageEm",
- "[image&image-marker !][image&image-alt-text&link [[][image-alt-text&em&image&link *alt text*][image&image-alt-text&link ]]][string&url (http://link.to/image.jpg)]");
- MT("imageStrong",
- "[image&image-marker !][image&image-alt-text&link [[][image-alt-text&strong&image&link **alt text**][image&image-alt-text&link ]]][string&url (http://link.to/image.jpg)]");
- MT("imageEmStrong",
- "[image&image-marker !][image&image-alt-text&link [[][image&image-alt-text&em&strong&link ***alt text***][image&image-alt-text&link ]]][string&url (http://link.to/image.jpg)]");
- // Inline link with title
- MT("linkTitle",
- "[link [[foo]]][string&url (http://example.com/ \"bar\")] hello");
- // Inline link without title
- MT("linkNoTitle",
- "[link [[foo]]][string&url (http://example.com/)] bar");
- // Inline link with image
- MT("linkImage",
- "[link [[][link&image&image-marker !][link&image&image-alt-text&link [[alt text]]][string&url (http://link.to/image.jpg)][link ]]][string&url (http://example.com/)] bar");
- // Inline link with Em
- MT("linkEm",
- "[link [[][link&em *foo*][link ]]][string&url (http://example.com/)] bar");
- // Inline link with Strong
- MT("linkStrong",
- "[link [[][link&strong **foo**][link ]]][string&url (http://example.com/)] bar");
- // Inline link with EmStrong
- MT("linkEmStrong",
- "[link [[][link&em&strong ***foo***][link ]]][string&url (http://example.com/)] bar");
- MT("multilineLink",
- "[link [[foo]",
- "[link bar]]][string&url (https://foo#_a)]",
- "should not be italics")
- // Image with title
- MT("imageTitle",
- "[image&image-marker !][image&image-alt-text&link [[alt text]]][string&url (http://example.com/ \"bar\")] hello");
- // Image without title
- MT("imageNoTitle",
- "[image&image-marker !][image&image-alt-text&link [[alt text]]][string&url (http://example.com/)] bar");
- // Image with asterisks
- MT("imageAsterisks",
- "[image&image-marker !][image&image-alt-text&link [[ ][image&image-alt-text&em&link *alt text*][image&image-alt-text&link ]]][string&url (http://link.to/image.jpg)] bar");
- // Not a link. Should be normal text due to square brackets being used
- // regularly in text, especially in quoted material, and no space is allowed
- // between square brackets and parentheses (per Dingus).
- MT("notALink",
- "[link [[foo]]] (bar)");
- // Reference-style links
- MT("linkReference",
- "[link [[foo]]][string&url [[bar]]] hello");
- // Reference-style links with Em
- MT("linkReferenceEm",
- "[link [[][link&em *foo*][link ]]][string&url [[bar]]] hello");
- // Reference-style links with Strong
- MT("linkReferenceStrong",
- "[link [[][link&strong **foo**][link ]]][string&url [[bar]]] hello");
- // Reference-style links with EmStrong
- MT("linkReferenceEmStrong",
- "[link [[][link&em&strong ***foo***][link ]]][string&url [[bar]]] hello");
- // Reference-style links with optional space separator (per documentation)
- // "You can optionally use a space to separate the sets of brackets"
- MT("linkReferenceSpace",
- "[link [[foo]]] [string&url [[bar]]] hello");
- // Should only allow a single space ("...use *a* space...")
- MT("linkReferenceDoubleSpace",
- "[link [[foo]]] [link [[bar]]] hello");
- // Reference-style links with implicit link name
- MT("linkImplicit",
- "[link [[foo]]][string&url [[]]] hello");
- // @todo It would be nice if, at some point, the document was actually
- // checked to see if the referenced link exists
- // Link label, for reference-style links (taken from documentation)
- MT("labelNoTitle",
- "[link [[foo]]:] [string&url http://example.com/]");
- MT("labelIndented",
- " [link [[foo]]:] [string&url http://example.com/]");
- MT("labelSpaceTitle",
- "[link [[foo bar]]:] [string&url http://example.com/ \"hello\"]");
- MT("labelDoubleTitle",
- "[link [[foo bar]]:] [string&url http://example.com/ \"hello\"] \"world\"");
- MT("labelTitleDoubleQuotes",
- "[link [[foo]]:] [string&url http://example.com/ \"bar\"]");
- MT("labelTitleSingleQuotes",
- "[link [[foo]]:] [string&url http://example.com/ 'bar']");
- MT("labelTitleParentheses",
- "[link [[foo]]:] [string&url http://example.com/ (bar)]");
- MT("labelTitleInvalid",
- "[link [[foo]]:] [string&url http://example.com/] bar");
- MT("labelLinkAngleBrackets",
- "[link [[foo]]:] [string&url <http://example.com/> \"bar\"]");
- MT("labelTitleNextDoubleQuotes",
- "[link [[foo]]:] [string&url http://example.com/]",
- "[string \"bar\"] hello");
- MT("labelTitleNextSingleQuotes",
- "[link [[foo]]:] [string&url http://example.com/]",
- "[string 'bar'] hello");
- MT("labelTitleNextParentheses",
- "[link [[foo]]:] [string&url http://example.com/]",
- "[string (bar)] hello");
- MT("labelTitleNextMixed",
- "[link [[foo]]:] [string&url http://example.com/]",
- "(bar\" hello");
- MT("labelEscape",
- "[link [[foo \\]] ]]:] [string&url http://example.com/]");
- MT("labelEscapeColon",
- "[link [[foo \\]]: bar]]:] [string&url http://example.com/]");
- MT("labelEscapeEnd",
- "\\[[foo\\]]: http://example.com/");
- MT("linkWeb",
- "[link <http://example.com/>] foo");
- MT("linkWebDouble",
- "[link <http://example.com/>] foo [link <http://example.com/>]");
- MT("linkEmail",
- "[link <user@example.com>] foo");
- MT("linkEmailDouble",
- "[link <user@example.com>] foo [link <user@example.com>]");
- MT("emAsterisk",
- "[em *foo*] bar");
- MT("emUnderscore",
- "[em _foo_] bar");
- MT("emInWordAsterisk",
- "foo[em *bar*]hello");
- MT("emInWordUnderscore",
- "foo_bar_hello");
- // Per documentation: "...surround an * or _ with spaces, it’ll be
- // treated as a literal asterisk or underscore."
- MT("emEscapedBySpaceIn",
- "foo [em _bar _ hello_] world");
- MT("emEscapedBySpaceOut",
- "foo _ bar [em _hello_] world");
- MT("emEscapedByNewline",
- "foo",
- "_ bar [em _hello_] world");
- // Unclosed emphasis characters
- // Instead of simply marking as EM / STRONG, it would be nice to have an
- // incomplete flag for EM and STRONG, that is styled slightly different.
- MT("emIncompleteAsterisk",
- "foo [em *bar]");
- MT("emIncompleteUnderscore",
- "foo [em _bar]");
- MT("strongAsterisk",
- "[strong **foo**] bar");
- MT("strongUnderscore",
- "[strong __foo__] bar");
- MT("emStrongAsterisk",
- "[em *foo][em&strong **bar*][strong hello**] world");
- MT("emStrongUnderscore",
- "[em _foo ][em&strong __bar_][strong hello__] world");
- // "...same character must be used to open and close an emphasis span.""
- MT("emStrongMixed",
- "[em _foo][em&strong **bar*hello__ world]");
- MT("emStrongMixed",
- "[em *foo ][em&strong __bar_hello** world]");
- MT("linkWithNestedParens",
- "[link [[foo]]][string&url (bar(baz))]")
- // These characters should be escaped:
- // \ backslash
- // ` backtick
- // * asterisk
- // _ underscore
- // {} curly braces
- // [] square brackets
- // () parentheses
- // # hash mark
- // + plus sign
- // - minus sign (hyphen)
- // . dot
- // ! exclamation mark
- MT("escapeBacktick",
- "foo \\`bar\\`");
- MT("doubleEscapeBacktick",
- "foo \\\\[comment `bar\\\\`]");
- MT("escapeAsterisk",
- "foo \\*bar\\*");
- MT("doubleEscapeAsterisk",
- "foo \\\\[em *bar\\\\*]");
- MT("escapeUnderscore",
- "foo \\_bar\\_");
- MT("doubleEscapeUnderscore",
- "foo \\\\[em _bar\\\\_]");
- MT("escapeHash",
- "\\# foo");
- MT("doubleEscapeHash",
- "\\\\# foo");
- MT("escapeNewline",
- "\\",
- "[em *foo*]");
- // Class override tests
- TokenTypeOverrideTest("overrideHeader1",
- "[override-header&override-header-1 # Foo]");
- TokenTypeOverrideTest("overrideHeader2",
- "[override-header&override-header-2 ## Foo]");
- TokenTypeOverrideTest("overrideHeader3",
- "[override-header&override-header-3 ### Foo]");
- TokenTypeOverrideTest("overrideHeader4",
- "[override-header&override-header-4 #### Foo]");
- TokenTypeOverrideTest("overrideHeader5",
- "[override-header&override-header-5 ##### Foo]");
- TokenTypeOverrideTest("overrideHeader6",
- "[override-header&override-header-6 ###### Foo]");
- TokenTypeOverrideTest("overrideCode",
- "[override-code `foo`]");
- TokenTypeOverrideTest("overrideCodeBlock",
- "[override-code ```]",
- "[override-code foo]",
- "[override-code ```]");
- TokenTypeOverrideTest("overrideQuote",
- "[override-quote&override-quote-1 > foo]",
- "[override-quote&override-quote-1 > bar]");
- TokenTypeOverrideTest("overrideQuoteNested",
- "[override-quote&override-quote-1 > foo]",
- "[override-quote&override-quote-1 >][override-quote&override-quote-2 > bar]",
- "[override-quote&override-quote-1 >][override-quote&override-quote-2 >][override-quote&override-quote-3 > baz]");
- TokenTypeOverrideTest("overrideLists",
- "[override-list1 - foo]",
- "",
- " [override-list2 + bar]",
- "",
- " [override-list3 * baz]",
- "",
- " [override-list1 1. qux]",
- "",
- " [override-list2 - quux]");
- TokenTypeOverrideTest("overrideHr",
- "[override-hr * * *]");
- TokenTypeOverrideTest("overrideImage",
- "[override-image&override-image-marker !][override-image&override-image-alt-text&link [[alt text]]][override-link-href&url (http://link.to/image.jpg)]");
- TokenTypeOverrideTest("overrideLinkText",
- "[override-link-text [[foo]]][override-link-href&url (http://example.com)]");
- TokenTypeOverrideTest("overrideLinkEmailAndInline",
- "[override-link-email <][override-link-inline foo@example.com>]");
- TokenTypeOverrideTest("overrideEm",
- "[override-em *foo*]");
- TokenTypeOverrideTest("overrideStrong",
- "[override-strong **foo**]");
- TokenTypeOverrideTest("overrideStrikethrough",
- "[override-strikethrough ~~foo~~]");
- TokenTypeOverrideTest("overrideEmoji",
- "[override-emoji :foo:]");
- FormatTokenTypeOverrideTest("overrideFormatting",
- "[override-formatting-escape \\*]");
- // Tests to make sure GFM-specific things aren't getting through
- MT("taskList",
- "[variable-2 * ][link&variable-2 [[ ]]][variable-2 bar]");
- MT("fencedCodeBlocks",
- "[comment ```]",
- "[comment foo]",
- "",
- "[comment bar]",
- "[comment ```]",
- "baz");
- MT("fencedCodeBlocks_invalidClosingFence_trailingText",
- "[comment ```]",
- "[comment foo]",
- "[comment ``` must not have trailing text]",
- "[comment baz]");
- MT("fencedCodeBlocks_invalidClosingFence_trailingTabs",
- "[comment ```]",
- "[comment foo]",
- "[comment ```\t]",
- "[comment baz]");
- MT("fencedCodeBlocks_validClosingFence",
- "[comment ```]",
- "[comment foo]",
- // may have trailing spaces
- "[comment ``` ]",
- "baz");
- MT("fencedCodeBlocksInList_closingFenceIndented",
- "[variable-2 - list]",
- " [variable-2&comment ```]",
- " [comment foo]",
- " [variable-2&comment ```]",
- " [variable-2 baz]");
- MT("fencedCodeBlocksInList_closingFenceIndentedTooMuch",
- "[variable-2 - list]",
- " [variable-2&comment ```]",
- " [comment foo]",
- " [comment ```]",
- " [comment baz]");
- MT("fencedCodeBlockModeSwitching",
- "[comment ```javascript]",
- "[variable foo]",
- "",
- "[comment ```]",
- "bar");
- MT_noFencedHighlight("fencedCodeBlock_noHighlight",
- "[comment ```javascript]",
- "[comment foo]",
- "[comment ```]");
- MT("fencedCodeBlockModeSwitchingObjc",
- "[comment ```objective-c]",
- "[keyword @property] [variable NSString] [operator *] [variable foo];",
- "[comment ```]",
- "bar");
- MT("fencedCodeBlocksMultipleChars",
- "[comment `````]",
- "[comment foo]",
- "[comment ```]",
- "[comment foo]",
- "[comment `````]",
- "bar");
- MT("fencedCodeBlocksTildes",
- "[comment ~~~]",
- "[comment foo]",
- "[comment ~~~]",
- "bar");
- MT("fencedCodeBlocksTildesMultipleChars",
- "[comment ~~~~~]",
- "[comment ~~~]",
- "[comment foo]",
- "[comment ~~~~~]",
- "bar");
- MT("fencedCodeBlocksMultipleChars",
- "[comment `````]",
- "[comment foo]",
- "[comment ```]",
- "[comment foo]",
- "[comment `````]",
- "bar");
- MT("fencedCodeBlocksMixed",
- "[comment ~~~]",
- "[comment ```]",
- "[comment foo]",
- "[comment ~~~]",
- "bar");
- MT("fencedCodeBlocksAfterBlockquote",
- "[quote"e-1 > foo]",
- "[comment ```]",
- "[comment bar]",
- "[comment ```]");
- // fencedCode indented too much should act as simple indentedCode
- // (hence has no highlight formatting)
- FT("tooMuchIndentedFencedCode",
- " [comment ```]",
- " [comment code]",
- " [comment ```]");
- MT("autoTerminateFencedCodeWhenLeavingList",
- "[variable-2 - list1]",
- " [variable-3 - list2]",
- " [variable-3&comment ```]",
- " [comment code]",
- " [variable-3 - list2]",
- " [variable-2&comment ```]",
- " [comment code]",
- "[quote"e-1 > foo]");
- // Tests that require XML mode
- MT("xmlMode",
- "[tag&bracket <][tag div][tag&bracket >]",
- " *foo*",
- " [tag&bracket <][tag http://github.com][tag&bracket />]",
- "[tag&bracket </][tag div][tag&bracket >]",
- "[link <http://github.com/>]");
- MT("xmlModeWithMarkdownInside",
- "[tag&bracket <][tag div] [attribute markdown]=[string 1][tag&bracket >]",
- "[em *foo*]",
- "[link <http://github.com/>]",
- "[tag </div>]",
- "[link <http://github.com/>]",
- "[tag&bracket <][tag div][tag&bracket >]",
- "[tag&bracket </][tag div][tag&bracket >]");
- MT("xmlModeLineBreakInTags",
- "[tag&bracket <][tag div] [attribute id]=[string \"1\"]",
- " [attribute class]=[string \"sth\"][tag&bracket >]xxx",
- "[tag&bracket </][tag div][tag&bracket >]");
- MT("xmlModeCommentWithBlankLine",
- "[comment <!-- Hello]",
- "",
- "[comment World -->]");
- MT("xmlModeCDATA",
- "[atom <![CDATA[ Hello]",
- "",
- "[atom FooBar]",
- "[atom Test ]]]]>]");
- MT("xmlModePreprocessor",
- "[meta <?php] [meta echo '1234'; ?>]");
- MT_noXml("xmlHighlightDisabled",
- "<div>foo</div>");
- // Tests Emojis
- ET("emojiDefault",
- "[builtin :foobar:]");
- ET("emojiTable",
- " :--:");
- })();
|