all repos — grayfriday @ 55d8f72ddede11ea2eed7abe74a218a43444992b

blackfriday fork with a few changes

block_test.go (view raw)

   1//
   2// Blackfriday Markdown Processor
   3// Available at http://github.com/russross/blackfriday
   4//
   5// Copyright © 2011 Russ Ross <russ@russross.com>.
   6// Distributed under the Simplified BSD License.
   7// See README.md for details.
   8//
   9
  10//
  11// Unit tests for block parsing
  12//
  13
  14package blackfriday
  15
  16import (
  17	"testing"
  18)
  19
  20func runMarkdownBlock(input string, extensions int) string {
  21	htmlFlags := 0
  22	htmlFlags |= HTML_USE_XHTML
  23
  24	renderer := HtmlRenderer(htmlFlags, "", "")
  25
  26	return string(Markdown([]byte(input), renderer, extensions))
  27}
  28
  29func doTestsBlock(t *testing.T, tests []string, extensions int) {
  30	// catch and report panics
  31	var candidate string
  32	defer func() {
  33		if err := recover(); err != nil {
  34			t.Errorf("\npanic while processing [%#v]: %s\n", candidate, err)
  35		}
  36	}()
  37
  38	for i := 0; i+1 < len(tests); i += 2 {
  39		input := tests[i]
  40		candidate = input
  41		expected := tests[i+1]
  42		actual := runMarkdownBlock(candidate, extensions)
  43		if actual != expected {
  44			t.Errorf("\nInput   [%#v]\nExpected[%#v]\nActual  [%#v]",
  45				candidate, expected, actual)
  46		}
  47
  48		// now test every substring to stress test bounds checking
  49		if !testing.Short() {
  50			for start := 0; start < len(input); start++ {
  51				for end := start + 1; end <= len(input); end++ {
  52					candidate = input[start:end]
  53					_ = runMarkdownBlock(candidate, extensions)
  54				}
  55			}
  56		}
  57	}
  58}
  59
  60func TestPrefixHeaderNoExtensions(t *testing.T) {
  61	var tests = []string{
  62		"# Header 1\n",
  63		"<h1>Header 1</h1>\n",
  64
  65		"## Header 2\n",
  66		"<h2>Header 2</h2>\n",
  67
  68		"### Header 3\n",
  69		"<h3>Header 3</h3>\n",
  70
  71		"#### Header 4\n",
  72		"<h4>Header 4</h4>\n",
  73
  74		"##### Header 5\n",
  75		"<h5>Header 5</h5>\n",
  76
  77		"###### Header 6\n",
  78		"<h6>Header 6</h6>\n",
  79
  80		"####### Header 7\n",
  81		"<h6># Header 7</h6>\n",
  82
  83		"#Header 1\n",
  84		"<h1>Header 1</h1>\n",
  85
  86		"##Header 2\n",
  87		"<h2>Header 2</h2>\n",
  88
  89		"###Header 3\n",
  90		"<h3>Header 3</h3>\n",
  91
  92		"####Header 4\n",
  93		"<h4>Header 4</h4>\n",
  94
  95		"#####Header 5\n",
  96		"<h5>Header 5</h5>\n",
  97
  98		"######Header 6\n",
  99		"<h6>Header 6</h6>\n",
 100
 101		"#######Header 7\n",
 102		"<h6>#Header 7</h6>\n",
 103
 104		"Hello\n# Header 1\nGoodbye\n",
 105		"<p>Hello</p>\n\n<h1>Header 1</h1>\n\n<p>Goodbye</p>\n",
 106
 107		"* List\n# Header\n* List\n",
 108		"<ul>\n<li><p>List</p>\n\n<h1>Header</h1></li>\n\n<li><p>List</p></li>\n</ul>\n",
 109
 110		"* List\n#Header\n* List\n",
 111		"<ul>\n<li><p>List</p>\n\n<h1>Header</h1></li>\n\n<li><p>List</p></li>\n</ul>\n",
 112
 113		"*   List\n    * Nested list\n    # Nested header\n",
 114		"<ul>\n<li><p>List</p>\n\n<ul>\n<li><p>Nested list</p>\n\n" +
 115			"<h1>Nested header</h1></li>\n</ul></li>\n</ul>\n",
 116	}
 117	doTestsBlock(t, tests, 0)
 118}
 119
 120func TestPrefixHeaderSpaceExtension(t *testing.T) {
 121	var tests = []string{
 122		"# Header 1\n",
 123		"<h1>Header 1</h1>\n",
 124
 125		"## Header 2\n",
 126		"<h2>Header 2</h2>\n",
 127
 128		"### Header 3\n",
 129		"<h3>Header 3</h3>\n",
 130
 131		"#### Header 4\n",
 132		"<h4>Header 4</h4>\n",
 133
 134		"##### Header 5\n",
 135		"<h5>Header 5</h5>\n",
 136
 137		"###### Header 6\n",
 138		"<h6>Header 6</h6>\n",
 139
 140		"####### Header 7\n",
 141		"<p>####### Header 7</p>\n",
 142
 143		"#Header 1\n",
 144		"<p>#Header 1</p>\n",
 145
 146		"##Header 2\n",
 147		"<p>##Header 2</p>\n",
 148
 149		"###Header 3\n",
 150		"<p>###Header 3</p>\n",
 151
 152		"####Header 4\n",
 153		"<p>####Header 4</p>\n",
 154
 155		"#####Header 5\n",
 156		"<p>#####Header 5</p>\n",
 157
 158		"######Header 6\n",
 159		"<p>######Header 6</p>\n",
 160
 161		"#######Header 7\n",
 162		"<p>#######Header 7</p>\n",
 163
 164		"Hello\n# Header 1\nGoodbye\n",
 165		"<p>Hello</p>\n\n<h1>Header 1</h1>\n\n<p>Goodbye</p>\n",
 166
 167		"* List\n# Header\n* List\n",
 168		"<ul>\n<li><p>List</p>\n\n<h1>Header</h1></li>\n\n<li><p>List</p></li>\n</ul>\n",
 169
 170		"* List\n#Header\n* List\n",
 171		"<ul>\n<li>List\n#Header</li>\n<li>List</li>\n</ul>\n",
 172
 173		"*   List\n    * Nested list\n    # Nested header\n",
 174		"<ul>\n<li><p>List</p>\n\n<ul>\n<li><p>Nested list</p>\n\n" +
 175			"<h1>Nested header</h1></li>\n</ul></li>\n</ul>\n",
 176	}
 177	doTestsBlock(t, tests, EXTENSION_SPACE_HEADERS)
 178}
 179
 180func TestPrefixHeaderIdExtension(t *testing.T) {
 181	var tests = []string{
 182		"# Header 1 {#someid}\n",
 183		"<h1 id=\"someid\">Header 1</h1>\n",
 184
 185		"# Header 1 {#someid}   \n",
 186		"<h1 id=\"someid\">Header 1</h1>\n",
 187
 188		"# Header 1         {#someid}\n",
 189		"<h1 id=\"someid\">Header 1</h1>\n",
 190
 191		"# Header 1 {#someid\n",
 192		"<h1>Header 1 {#someid</h1>\n",
 193
 194		"# Header 1 {#someid\n",
 195		"<h1>Header 1 {#someid</h1>\n",
 196
 197		"# Header 1 {#someid}}\n",
 198		"<h1 id=\"someid\">Header 1</h1>\n\n<p>}</p>\n",
 199
 200		"## Header 2 {#someid}\n",
 201		"<h2 id=\"someid\">Header 2</h2>\n",
 202
 203		"### Header 3 {#someid}\n",
 204		"<h3 id=\"someid\">Header 3</h3>\n",
 205
 206		"#### Header 4 {#someid}\n",
 207		"<h4 id=\"someid\">Header 4</h4>\n",
 208
 209		"##### Header 5 {#someid}\n",
 210		"<h5 id=\"someid\">Header 5</h5>\n",
 211
 212		"###### Header 6 {#someid}\n",
 213		"<h6 id=\"someid\">Header 6</h6>\n",
 214
 215		"####### Header 7 {#someid}\n",
 216		"<h6 id=\"someid\"># Header 7</h6>\n",
 217
 218		"# Header 1 # {#someid}\n",
 219		"<h1 id=\"someid\">Header 1</h1>\n",
 220
 221		"## Header 2 ## {#someid}\n",
 222		"<h2 id=\"someid\">Header 2</h2>\n",
 223
 224		"Hello\n# Header 1\nGoodbye\n",
 225		"<p>Hello</p>\n\n<h1>Header 1</h1>\n\n<p>Goodbye</p>\n",
 226
 227		"* List\n# Header {#someid}\n* List\n",
 228		"<ul>\n<li><p>List</p>\n\n<h1 id=\"someid\">Header</h1></li>\n\n<li><p>List</p></li>\n</ul>\n",
 229
 230		"* List\n#Header {#someid}\n* List\n",
 231		"<ul>\n<li><p>List</p>\n\n<h1 id=\"someid\">Header</h1></li>\n\n<li><p>List</p></li>\n</ul>\n",
 232
 233		"*   List\n    * Nested list\n    # Nested header {#someid}\n",
 234		"<ul>\n<li><p>List</p>\n\n<ul>\n<li><p>Nested list</p>\n\n" +
 235			"<h1 id=\"someid\">Nested header</h1></li>\n</ul></li>\n</ul>\n",
 236	}
 237	doTestsBlock(t, tests, EXTENSION_HEADER_IDS)
 238}
 239
 240func TestUnderlineHeaders(t *testing.T) {
 241	var tests = []string{
 242		"Header 1\n========\n",
 243		"<h1>Header 1</h1>\n",
 244
 245		"Header 2\n--------\n",
 246		"<h2>Header 2</h2>\n",
 247
 248		"A\n=\n",
 249		"<h1>A</h1>\n",
 250
 251		"B\n-\n",
 252		"<h2>B</h2>\n",
 253
 254		"Paragraph\nHeader\n=\n",
 255		"<p>Paragraph</p>\n\n<h1>Header</h1>\n",
 256
 257		"Header\n===\nParagraph\n",
 258		"<h1>Header</h1>\n\n<p>Paragraph</p>\n",
 259
 260		"Header\n===\nAnother header\n---\n",
 261		"<h1>Header</h1>\n\n<h2>Another header</h2>\n",
 262
 263		"   Header\n======\n",
 264		"<h1>Header</h1>\n",
 265
 266		"    Code\n========\n",
 267		"<pre><code>Code\n</code></pre>\n\n<p>========</p>\n",
 268
 269		"Header with *inline*\n=====\n",
 270		"<h1>Header with <em>inline</em></h1>\n",
 271
 272		"*   List\n    * Sublist\n    Not a header\n    ------\n",
 273		"<ul>\n<li>List\n\n<ul>\n<li>Sublist\nNot a header\n------</li>\n</ul></li>\n</ul>\n",
 274
 275		"Paragraph\n\n\n\n\nHeader\n===\n",
 276		"<p>Paragraph</p>\n\n<h1>Header</h1>\n",
 277
 278		"Trailing space \n====        \n\n",
 279		"<h1>Trailing space</h1>\n",
 280
 281		"Trailing spaces\n====        \n\n",
 282		"<h1>Trailing spaces</h1>\n",
 283
 284		"Double underline\n=====\n=====\n",
 285		"<h1>Double underline</h1>\n\n<p>=====</p>\n",
 286	}
 287	doTestsBlock(t, tests, 0)
 288}
 289
 290func TestHorizontalRule(t *testing.T) {
 291	var tests = []string{
 292		"-\n",
 293		"<p>-</p>\n",
 294
 295		"--\n",
 296		"<p>--</p>\n",
 297
 298		"---\n",
 299		"<hr />\n",
 300
 301		"----\n",
 302		"<hr />\n",
 303
 304		"*\n",
 305		"<p>*</p>\n",
 306
 307		"**\n",
 308		"<p>**</p>\n",
 309
 310		"***\n",
 311		"<hr />\n",
 312
 313		"****\n",
 314		"<hr />\n",
 315
 316		"_\n",
 317		"<p>_</p>\n",
 318
 319		"__\n",
 320		"<p>__</p>\n",
 321
 322		"___\n",
 323		"<hr />\n",
 324
 325		"____\n",
 326		"<hr />\n",
 327
 328		"-*-\n",
 329		"<p>-*-</p>\n",
 330
 331		"- - -\n",
 332		"<hr />\n",
 333
 334		"* * *\n",
 335		"<hr />\n",
 336
 337		"_ _ _\n",
 338		"<hr />\n",
 339
 340		"-----*\n",
 341		"<p>-----*</p>\n",
 342
 343		"   ------   \n",
 344		"<hr />\n",
 345
 346		"Hello\n***\n",
 347		"<p>Hello</p>\n\n<hr />\n",
 348
 349		"---\n***\n___\n",
 350		"<hr />\n\n<hr />\n\n<hr />\n",
 351	}
 352	doTestsBlock(t, tests, 0)
 353}
 354
 355func TestUnorderedList(t *testing.T) {
 356	var tests = []string{
 357		"* Hello\n",
 358		"<ul>\n<li>Hello</li>\n</ul>\n",
 359
 360		"* Yin\n* Yang\n",
 361		"<ul>\n<li>Yin</li>\n<li>Yang</li>\n</ul>\n",
 362
 363		"* Ting\n* Bong\n* Goo\n",
 364		"<ul>\n<li>Ting</li>\n<li>Bong</li>\n<li>Goo</li>\n</ul>\n",
 365
 366		"* Yin\n\n* Yang\n",
 367		"<ul>\n<li><p>Yin</p></li>\n\n<li><p>Yang</p></li>\n</ul>\n",
 368
 369		"* Ting\n\n* Bong\n* Goo\n",
 370		"<ul>\n<li><p>Ting</p></li>\n\n<li><p>Bong</p></li>\n\n<li><p>Goo</p></li>\n</ul>\n",
 371
 372		"+ Hello\n",
 373		"<ul>\n<li>Hello</li>\n</ul>\n",
 374
 375		"+ Yin\n+ Yang\n",
 376		"<ul>\n<li>Yin</li>\n<li>Yang</li>\n</ul>\n",
 377
 378		"+ Ting\n+ Bong\n+ Goo\n",
 379		"<ul>\n<li>Ting</li>\n<li>Bong</li>\n<li>Goo</li>\n</ul>\n",
 380
 381		"+ Yin\n\n+ Yang\n",
 382		"<ul>\n<li><p>Yin</p></li>\n\n<li><p>Yang</p></li>\n</ul>\n",
 383
 384		"+ Ting\n\n+ Bong\n+ Goo\n",
 385		"<ul>\n<li><p>Ting</p></li>\n\n<li><p>Bong</p></li>\n\n<li><p>Goo</p></li>\n</ul>\n",
 386
 387		"- Hello\n",
 388		"<ul>\n<li>Hello</li>\n</ul>\n",
 389
 390		"- Yin\n- Yang\n",
 391		"<ul>\n<li>Yin</li>\n<li>Yang</li>\n</ul>\n",
 392
 393		"- Ting\n- Bong\n- Goo\n",
 394		"<ul>\n<li>Ting</li>\n<li>Bong</li>\n<li>Goo</li>\n</ul>\n",
 395
 396		"- Yin\n\n- Yang\n",
 397		"<ul>\n<li><p>Yin</p></li>\n\n<li><p>Yang</p></li>\n</ul>\n",
 398
 399		"- Ting\n\n- Bong\n- Goo\n",
 400		"<ul>\n<li><p>Ting</p></li>\n\n<li><p>Bong</p></li>\n\n<li><p>Goo</p></li>\n</ul>\n",
 401
 402		"*Hello\n",
 403		"<p>*Hello</p>\n",
 404
 405		"*   Hello \n",
 406		"<ul>\n<li>Hello</li>\n</ul>\n",
 407
 408		"*   Hello \n    Next line \n",
 409		"<ul>\n<li>Hello\nNext line</li>\n</ul>\n",
 410
 411		"Paragraph\n* No linebreak\n",
 412		"<p>Paragraph\n* No linebreak</p>\n",
 413
 414		"Paragraph\n\n* Linebreak\n",
 415		"<p>Paragraph</p>\n\n<ul>\n<li>Linebreak</li>\n</ul>\n",
 416
 417		"*   List\n    * Nested list\n",
 418		"<ul>\n<li>List\n\n<ul>\n<li>Nested list</li>\n</ul></li>\n</ul>\n",
 419
 420		"*   List\n\n    * Nested list\n",
 421		"<ul>\n<li><p>List</p>\n\n<ul>\n<li>Nested list</li>\n</ul></li>\n</ul>\n",
 422
 423		"*   List\n    Second line\n\n    + Nested\n",
 424		"<ul>\n<li><p>List\nSecond line</p>\n\n<ul>\n<li>Nested</li>\n</ul></li>\n</ul>\n",
 425
 426		"*   List\n    + Nested\n\n    Continued\n",
 427		"<ul>\n<li><p>List</p>\n\n<ul>\n<li>Nested</li>\n</ul>\n\n<p>Continued</p></li>\n</ul>\n",
 428
 429		"*   List\n   * shallow indent\n",
 430		"<ul>\n<li>List\n\n<ul>\n<li>shallow indent</li>\n</ul></li>\n</ul>\n",
 431
 432		"* List\n" +
 433			" * shallow indent\n" +
 434			"  * part of second list\n" +
 435			"   * still second\n" +
 436			"    * almost there\n" +
 437			"     * third level\n",
 438		"<ul>\n" +
 439			"<li>List\n\n" +
 440			"<ul>\n" +
 441			"<li>shallow indent</li>\n" +
 442			"<li>part of second list</li>\n" +
 443			"<li>still second</li>\n" +
 444			"<li>almost there\n\n" +
 445			"<ul>\n" +
 446			"<li>third level</li>\n" +
 447			"</ul></li>\n" +
 448			"</ul></li>\n" +
 449			"</ul>\n",
 450
 451		"* List\n        extra indent, same paragraph\n",
 452		"<ul>\n<li>List\n    extra indent, same paragraph</li>\n</ul>\n",
 453
 454		"* List\n\n        code block\n",
 455		"<ul>\n<li><p>List</p>\n\n<pre><code>code block\n</code></pre></li>\n</ul>\n",
 456
 457		"* List\n\n          code block with spaces\n",
 458		"<ul>\n<li><p>List</p>\n\n<pre><code>  code block with spaces\n</code></pre></li>\n</ul>\n",
 459
 460		"* List\n\n    * sublist\n\n    normal text\n\n    * another sublist\n",
 461		"<ul>\n<li><p>List</p>\n\n<ul>\n<li>sublist</li>\n</ul>\n\n<p>normal text</p>\n\n<ul>\n<li>another sublist</li>\n</ul></li>\n</ul>\n",
 462	}
 463	doTestsBlock(t, tests, 0)
 464}
 465
 466func TestOrderedList(t *testing.T) {
 467	var tests = []string{
 468		"1. Hello\n",
 469		"<ol>\n<li>Hello</li>\n</ol>\n",
 470
 471		"1. Yin\n2. Yang\n",
 472		"<ol>\n<li>Yin</li>\n<li>Yang</li>\n</ol>\n",
 473
 474		"1. Ting\n2. Bong\n3. Goo\n",
 475		"<ol>\n<li>Ting</li>\n<li>Bong</li>\n<li>Goo</li>\n</ol>\n",
 476
 477		"1. Yin\n\n2. Yang\n",
 478		"<ol>\n<li><p>Yin</p></li>\n\n<li><p>Yang</p></li>\n</ol>\n",
 479
 480		"1. Ting\n\n2. Bong\n3. Goo\n",
 481		"<ol>\n<li><p>Ting</p></li>\n\n<li><p>Bong</p></li>\n\n<li><p>Goo</p></li>\n</ol>\n",
 482
 483		"1 Hello\n",
 484		"<p>1 Hello</p>\n",
 485
 486		"1.Hello\n",
 487		"<p>1.Hello</p>\n",
 488
 489		"1.  Hello \n",
 490		"<ol>\n<li>Hello</li>\n</ol>\n",
 491
 492		"1.  Hello \n    Next line \n",
 493		"<ol>\n<li>Hello\nNext line</li>\n</ol>\n",
 494
 495		"Paragraph\n1. No linebreak\n",
 496		"<p>Paragraph\n1. No linebreak</p>\n",
 497
 498		"Paragraph\n\n1. Linebreak\n",
 499		"<p>Paragraph</p>\n\n<ol>\n<li>Linebreak</li>\n</ol>\n",
 500
 501		"1.  List\n    1. Nested list\n",
 502		"<ol>\n<li>List\n\n<ol>\n<li>Nested list</li>\n</ol></li>\n</ol>\n",
 503
 504		"1.  List\n\n    1. Nested list\n",
 505		"<ol>\n<li><p>List</p>\n\n<ol>\n<li>Nested list</li>\n</ol></li>\n</ol>\n",
 506
 507		"1.  List\n    Second line\n\n    1. Nested\n",
 508		"<ol>\n<li><p>List\nSecond line</p>\n\n<ol>\n<li>Nested</li>\n</ol></li>\n</ol>\n",
 509
 510		"1.  List\n    1. Nested\n\n    Continued\n",
 511		"<ol>\n<li><p>List</p>\n\n<ol>\n<li>Nested</li>\n</ol>\n\n<p>Continued</p></li>\n</ol>\n",
 512
 513		"1.  List\n   1. shallow indent\n",
 514		"<ol>\n<li>List\n\n<ol>\n<li>shallow indent</li>\n</ol></li>\n</ol>\n",
 515
 516		"1. List\n" +
 517			" 1. shallow indent\n" +
 518			"  2. part of second list\n" +
 519			"   3. still second\n" +
 520			"    4. almost there\n" +
 521			"     1. third level\n",
 522		"<ol>\n" +
 523			"<li>List\n\n" +
 524			"<ol>\n" +
 525			"<li>shallow indent</li>\n" +
 526			"<li>part of second list</li>\n" +
 527			"<li>still second</li>\n" +
 528			"<li>almost there\n\n" +
 529			"<ol>\n" +
 530			"<li>third level</li>\n" +
 531			"</ol></li>\n" +
 532			"</ol></li>\n" +
 533			"</ol>\n",
 534
 535		"1. List\n        extra indent, same paragraph\n",
 536		"<ol>\n<li>List\n    extra indent, same paragraph</li>\n</ol>\n",
 537
 538		"1. List\n\n        code block\n",
 539		"<ol>\n<li><p>List</p>\n\n<pre><code>code block\n</code></pre></li>\n</ol>\n",
 540
 541		"1. List\n\n          code block with spaces\n",
 542		"<ol>\n<li><p>List</p>\n\n<pre><code>  code block with spaces\n</code></pre></li>\n</ol>\n",
 543
 544		"1. List\n    * Mixted list\n",
 545		"<ol>\n<li>List\n\n<ul>\n<li>Mixted list</li>\n</ul></li>\n</ol>\n",
 546
 547		"1. List\n * Mixed list\n",
 548		"<ol>\n<li>List\n\n<ul>\n<li>Mixed list</li>\n</ul></li>\n</ol>\n",
 549
 550		"* Start with unordered\n 1. Ordered\n",
 551		"<ul>\n<li>Start with unordered\n\n<ol>\n<li>Ordered</li>\n</ol></li>\n</ul>\n",
 552
 553		"* Start with unordered\n    1. Ordered\n",
 554		"<ul>\n<li>Start with unordered\n\n<ol>\n<li>Ordered</li>\n</ol></li>\n</ul>\n",
 555
 556		"1. numbers\n1. are ignored\n",
 557		"<ol>\n<li>numbers</li>\n<li>are ignored</li>\n</ol>\n",
 558	}
 559	doTestsBlock(t, tests, 0)
 560}
 561
 562func TestPreformattedHtml(t *testing.T) {
 563	var tests = []string{
 564		"<div></div>\n",
 565		"<div></div>\n",
 566
 567		"<div>\n</div>\n",
 568		"<div>\n</div>\n",
 569
 570		"<div>\n</div>\nParagraph\n",
 571		"<p><div>\n</div>\nParagraph</p>\n",
 572
 573		"<div class=\"foo\">\n</div>\n",
 574		"<div class=\"foo\">\n</div>\n",
 575
 576		"<div>\nAnything here\n</div>\n",
 577		"<div>\nAnything here\n</div>\n",
 578
 579		"<div>\n  Anything here\n</div>\n",
 580		"<div>\n  Anything here\n</div>\n",
 581
 582		"<div>\nAnything here\n  </div>\n",
 583		"<div>\nAnything here\n  </div>\n",
 584
 585		"<div>\nThis is *not* &proceessed\n</div>\n",
 586		"<div>\nThis is *not* &proceessed\n</div>\n",
 587
 588		"<faketag>\n  Something\n</faketag>\n",
 589		"<p><faketag>\n  Something\n</faketag></p>\n",
 590
 591		"<div>\n  Something here\n</divv>\n",
 592		"<p><div>\n  Something here\n</divv></p>\n",
 593
 594		"Paragraph\n<div>\nHere? >&<\n</div>\n",
 595		"<p>Paragraph\n<div>\nHere? &gt;&amp;&lt;\n</div></p>\n",
 596
 597		"Paragraph\n\n<div>\nHow about here? >&<\n</div>\n",
 598		"<p>Paragraph</p>\n\n<div>\nHow about here? >&<\n</div>\n",
 599
 600		"Paragraph\n<div>\nHere? >&<\n</div>\nAnd here?\n",
 601		"<p>Paragraph\n<div>\nHere? &gt;&amp;&lt;\n</div>\nAnd here?</p>\n",
 602
 603		"Paragraph\n\n<div>\nHow about here? >&<\n</div>\nAnd here?\n",
 604		"<p>Paragraph</p>\n\n<p><div>\nHow about here? &gt;&amp;&lt;\n</div>\nAnd here?</p>\n",
 605
 606		"Paragraph\n<div>\nHere? >&<\n</div>\n\nAnd here?\n",
 607		"<p>Paragraph\n<div>\nHere? &gt;&amp;&lt;\n</div></p>\n\n<p>And here?</p>\n",
 608
 609		"Paragraph\n\n<div>\nHow about here? >&<\n</div>\n\nAnd here?\n",
 610		"<p>Paragraph</p>\n\n<div>\nHow about here? >&<\n</div>\n\n<p>And here?</p>\n",
 611	}
 612	doTestsBlock(t, tests, 0)
 613}
 614
 615func TestPreformattedHtmlLax(t *testing.T) {
 616	var tests = []string{
 617		"Paragraph\n<div>\nHere? >&<\n</div>\n",
 618		"<p>Paragraph</p>\n\n<div>\nHere? >&<\n</div>\n",
 619
 620		"Paragraph\n\n<div>\nHow about here? >&<\n</div>\n",
 621		"<p>Paragraph</p>\n\n<div>\nHow about here? >&<\n</div>\n",
 622
 623		"Paragraph\n<div>\nHere? >&<\n</div>\nAnd here?\n",
 624		"<p>Paragraph</p>\n\n<div>\nHere? >&<\n</div>\n\n<p>And here?</p>\n",
 625
 626		"Paragraph\n\n<div>\nHow about here? >&<\n</div>\nAnd here?\n",
 627		"<p>Paragraph</p>\n\n<div>\nHow about here? >&<\n</div>\n\n<p>And here?</p>\n",
 628
 629		"Paragraph\n<div>\nHere? >&<\n</div>\n\nAnd here?\n",
 630		"<p>Paragraph</p>\n\n<div>\nHere? >&<\n</div>\n\n<p>And here?</p>\n",
 631
 632		"Paragraph\n\n<div>\nHow about here? >&<\n</div>\n\nAnd here?\n",
 633		"<p>Paragraph</p>\n\n<div>\nHow about here? >&<\n</div>\n\n<p>And here?</p>\n",
 634	}
 635	doTestsBlock(t, tests, EXTENSION_LAX_HTML_BLOCKS)
 636}
 637
 638func TestFencedCodeBlock(t *testing.T) {
 639	var tests = []string{
 640		"``` go\nfunc foo() bool {\n\treturn true;\n}\n```\n",
 641		"<pre><code class=\"go\">func foo() bool {\n\treturn true;\n}\n</code></pre>\n",
 642
 643		"``` c\n/* special & char < > \" escaping */\n```\n",
 644		"<pre><code class=\"c\">/* special &amp; char &lt; &gt; &quot; escaping */\n</code></pre>\n",
 645
 646		"``` c\nno *inline* processing ~~of text~~\n```\n",
 647		"<pre><code class=\"c\">no *inline* processing ~~of text~~\n</code></pre>\n",
 648
 649		"```\nNo language\n```\n",
 650		"<pre><code>No language\n</code></pre>\n",
 651
 652		"``` {ocaml}\nlanguage in braces\n```\n",
 653		"<pre><code class=\"ocaml\">language in braces\n</code></pre>\n",
 654
 655		"```    {ocaml}      \nwith extra whitespace\n```\n",
 656		"<pre><code class=\"ocaml\">with extra whitespace\n</code></pre>\n",
 657
 658		"```{   ocaml   }\nwith extra whitespace\n```\n",
 659		"<pre><code class=\"ocaml\">with extra whitespace\n</code></pre>\n",
 660
 661		"~ ~~ java\nWith whitespace\n~~~\n",
 662		"<p>~ ~~ java\nWith whitespace\n~~~</p>\n",
 663
 664		"~~\nonly two\n~~\n",
 665		"<p>~~\nonly two\n~~</p>\n",
 666
 667		"```` python\nextra\n````\n",
 668		"<pre><code class=\"python\">extra\n</code></pre>\n",
 669
 670		"~~~ perl\nthree to start, four to end\n~~~~\n",
 671		"<p>~~~ perl\nthree to start, four to end\n~~~~</p>\n",
 672
 673		"~~~~ perl\nfour to start, three to end\n~~~\n",
 674		"<p>~~~~ perl\nfour to start, three to end\n~~~</p>\n",
 675
 676		"~~~ bash\ntildes\n~~~\n",
 677		"<pre><code class=\"bash\">tildes\n</code></pre>\n",
 678
 679		"``` lisp\nno ending\n",
 680		"<p>``` lisp\nno ending</p>\n",
 681
 682		"~~~ lisp\nend with language\n~~~ lisp\n",
 683		"<p>~~~ lisp\nend with language\n~~~ lisp</p>\n",
 684
 685		"```\nmismatched begin and end\n~~~\n",
 686		"<p>```\nmismatched begin and end\n~~~</p>\n",
 687
 688		"~~~\nmismatched begin and end\n```\n",
 689		"<p>~~~\nmismatched begin and end\n```</p>\n",
 690
 691		"   ``` oz\nleading spaces\n```\n",
 692		"<pre><code class=\"oz\">leading spaces\n</code></pre>\n",
 693
 694		"  ``` oz\nleading spaces\n ```\n",
 695		"<pre><code class=\"oz\">leading spaces\n</code></pre>\n",
 696
 697		" ``` oz\nleading spaces\n  ```\n",
 698		"<pre><code class=\"oz\">leading spaces\n</code></pre>\n",
 699
 700		"``` oz\nleading spaces\n   ```\n",
 701		"<pre><code class=\"oz\">leading spaces\n</code></pre>\n",
 702
 703		"    ``` oz\nleading spaces\n    ```\n",
 704		"<pre><code>``` oz\n</code></pre>\n\n<p>leading spaces\n    ```</p>\n",
 705
 706		"Bla bla\n\n``` oz\ncode blocks breakup paragraphs\n```\n\nBla Bla\n",
 707		"<p>Bla bla</p>\n\n<pre><code class=\"oz\">code blocks breakup paragraphs\n</code></pre>\n\n<p>Bla Bla</p>\n",
 708
 709		"Some text before a fenced code block\n``` oz\ncode blocks breakup paragraphs\n```\nAnd some text after a fenced code block",
 710		"<p>Some text before a fenced code block</p>\n\n<pre><code class=\"oz\">code blocks breakup paragraphs\n</code></pre>\n\n<p>And some text after a fenced code block</p>\n",
 711
 712		"`",
 713		"<p>`</p>\n",
 714
 715		"Bla bla\n\n``` oz\ncode blocks breakup paragraphs\n```\n\nBla Bla\n\n``` oz\nmultiple code blocks work okay\n```\n\nBla Bla\n",
 716		"<p>Bla bla</p>\n\n<pre><code class=\"oz\">code blocks breakup paragraphs\n</code></pre>\n\n<p>Bla Bla</p>\n\n<pre><code class=\"oz\">multiple code blocks work okay\n</code></pre>\n\n<p>Bla Bla</p>\n",
 717
 718		"Some text before a fenced code block\n``` oz\ncode blocks breakup paragraphs\n```\nSome text in between\n``` oz\nmultiple code blocks work okay\n```\nAnd some text after a fenced code block",
 719		"<p>Some text before a fenced code block</p>\n\n<pre><code class=\"oz\">code blocks breakup paragraphs\n</code></pre>\n\n<p>Some text in between</p>\n\n<pre><code class=\"oz\">multiple code blocks work okay\n</code></pre>\n\n<p>And some text after a fenced code block</p>\n",
 720	}
 721	doTestsBlock(t, tests, EXTENSION_FENCED_CODE)
 722}
 723
 724func TestTable(t *testing.T) {
 725	var tests = []string{
 726		"a | b\n---|---\nc | d\n",
 727		"<table>\n<thead>\n<tr>\n<th>a</th>\n<th>b</th>\n</tr>\n</thead>\n\n" +
 728			"<tbody>\n<tr>\n<td>c</td>\n<td>d</td>\n</tr>\n</tbody>\n</table>\n",
 729
 730		"a | b\n---|--\nc | d\n",
 731		"<p>a | b\n---|--\nc | d</p>\n",
 732
 733		"|a|b|c|d|\n|----|----|----|---|\n|e|f|g|h|\n",
 734		"<table>\n<thead>\n<tr>\n<th>a</th>\n<th>b</th>\n<th>c</th>\n<th>d</th>\n</tr>\n</thead>\n\n" +
 735			"<tbody>\n<tr>\n<td>e</td>\n<td>f</td>\n<td>g</td>\n<td>h</td>\n</tr>\n</tbody>\n</table>\n",
 736
 737		"*a*|__b__|[c](C)|d\n---|---|---|---\ne|f|g|h\n",
 738		"<table>\n<thead>\n<tr>\n<th><em>a</em></th>\n<th><strong>b</strong></th>\n<th><a href=\"C\">c</a></th>\n<th>d</th>\n</tr>\n</thead>\n\n" +
 739			"<tbody>\n<tr>\n<td>e</td>\n<td>f</td>\n<td>g</td>\n<td>h</td>\n</tr>\n</tbody>\n</table>\n",
 740
 741		"a|b|c\n---|---|---\nd|e|f\ng|h\ni|j|k|l|m\nn|o|p\n",
 742		"<table>\n<thead>\n<tr>\n<th>a</th>\n<th>b</th>\n<th>c</th>\n</tr>\n</thead>\n\n" +
 743			"<tbody>\n<tr>\n<td>d</td>\n<td>e</td>\n<td>f</td>\n</tr>\n\n" +
 744			"<tr>\n<td>g</td>\n<td>h</td>\n<td></td>\n</tr>\n\n" +
 745			"<tr>\n<td>i</td>\n<td>j</td>\n<td>k</td>\n</tr>\n\n" +
 746			"<tr>\n<td>n</td>\n<td>o</td>\n<td>p</td>\n</tr>\n</tbody>\n</table>\n",
 747
 748		"a|b|c\n---|---|---\n*d*|__e__|f\n",
 749		"<table>\n<thead>\n<tr>\n<th>a</th>\n<th>b</th>\n<th>c</th>\n</tr>\n</thead>\n\n" +
 750			"<tbody>\n<tr>\n<td><em>d</em></td>\n<td><strong>e</strong></td>\n<td>f</td>\n</tr>\n</tbody>\n</table>\n",
 751
 752		"a|b|c|d\n:--|--:|:-:|---\ne|f|g|h\n",
 753		"<table>\n<thead>\n<tr>\n<th align=\"left\">a</th>\n<th align=\"right\">b</th>\n" +
 754			"<th align=\"center\">c</th>\n<th>d</th>\n</tr>\n</thead>\n\n" +
 755			"<tbody>\n<tr>\n<td align=\"left\">e</td>\n<td align=\"right\">f</td>\n" +
 756			"<td align=\"center\">g</td>\n<td>h</td>\n</tr>\n</tbody>\n</table>\n",
 757
 758		"a|b|c\n---|---|---\n",
 759		"<table>\n<thead>\n<tr>\n<th>a</th>\n<th>b</th>\n<th>c</th>\n</tr>\n</thead>\n\n<tbody>\n</tbody>\n</table>\n",
 760
 761		"a| b|c | d | e\n---|---|---|---|---\nf| g|h | i |j\n",
 762		"<table>\n<thead>\n<tr>\n<th>a</th>\n<th>b</th>\n<th>c</th>\n<th>d</th>\n<th>e</th>\n</tr>\n</thead>\n\n" +
 763			"<tbody>\n<tr>\n<td>f</td>\n<td>g</td>\n<td>h</td>\n<td>i</td>\n<td>j</td>\n</tr>\n</tbody>\n</table>\n",
 764
 765		"a|b\\|c|d\n---|---|---\nf|g\\|h|i\n",
 766		"<table>\n<thead>\n<tr>\n<th>a</th>\n<th>b|c</th>\n<th>d</th>\n</tr>\n</thead>\n\n<tbody>\n<tr>\n<td>f</td>\n<td>g|h</td>\n<td>i</td>\n</tr>\n</tbody>\n</table>\n",
 767	}
 768	doTestsBlock(t, tests, EXTENSION_TABLES)
 769}
 770
 771func TestUnorderedListWith_EXTENSION_NO_EMPTY_LINE_BEFORE_BLOCK(t *testing.T) {
 772	var tests = []string{
 773		"* Hello\n",
 774		"<ul>\n<li>Hello</li>\n</ul>\n",
 775
 776		"* Yin\n* Yang\n",
 777		"<ul>\n<li>Yin</li>\n<li>Yang</li>\n</ul>\n",
 778
 779		"* Ting\n* Bong\n* Goo\n",
 780		"<ul>\n<li>Ting</li>\n<li>Bong</li>\n<li>Goo</li>\n</ul>\n",
 781
 782		"* Yin\n\n* Yang\n",
 783		"<ul>\n<li><p>Yin</p></li>\n\n<li><p>Yang</p></li>\n</ul>\n",
 784
 785		"* Ting\n\n* Bong\n* Goo\n",
 786		"<ul>\n<li><p>Ting</p></li>\n\n<li><p>Bong</p></li>\n\n<li><p>Goo</p></li>\n</ul>\n",
 787
 788		"+ Hello\n",
 789		"<ul>\n<li>Hello</li>\n</ul>\n",
 790
 791		"+ Yin\n+ Yang\n",
 792		"<ul>\n<li>Yin</li>\n<li>Yang</li>\n</ul>\n",
 793
 794		"+ Ting\n+ Bong\n+ Goo\n",
 795		"<ul>\n<li>Ting</li>\n<li>Bong</li>\n<li>Goo</li>\n</ul>\n",
 796
 797		"+ Yin\n\n+ Yang\n",
 798		"<ul>\n<li><p>Yin</p></li>\n\n<li><p>Yang</p></li>\n</ul>\n",
 799
 800		"+ Ting\n\n+ Bong\n+ Goo\n",
 801		"<ul>\n<li><p>Ting</p></li>\n\n<li><p>Bong</p></li>\n\n<li><p>Goo</p></li>\n</ul>\n",
 802
 803		"- Hello\n",
 804		"<ul>\n<li>Hello</li>\n</ul>\n",
 805
 806		"- Yin\n- Yang\n",
 807		"<ul>\n<li>Yin</li>\n<li>Yang</li>\n</ul>\n",
 808
 809		"- Ting\n- Bong\n- Goo\n",
 810		"<ul>\n<li>Ting</li>\n<li>Bong</li>\n<li>Goo</li>\n</ul>\n",
 811
 812		"- Yin\n\n- Yang\n",
 813		"<ul>\n<li><p>Yin</p></li>\n\n<li><p>Yang</p></li>\n</ul>\n",
 814
 815		"- Ting\n\n- Bong\n- Goo\n",
 816		"<ul>\n<li><p>Ting</p></li>\n\n<li><p>Bong</p></li>\n\n<li><p>Goo</p></li>\n</ul>\n",
 817
 818		"*Hello\n",
 819		"<p>*Hello</p>\n",
 820
 821		"*   Hello \n",
 822		"<ul>\n<li>Hello</li>\n</ul>\n",
 823
 824		"*   Hello \n    Next line \n",
 825		"<ul>\n<li>Hello\nNext line</li>\n</ul>\n",
 826
 827		"Paragraph\n* No linebreak\n",
 828		"<p>Paragraph</p>\n\n<ul>\n<li>No linebreak</li>\n</ul>\n",
 829
 830		"Paragraph\n\n* Linebreak\n",
 831		"<p>Paragraph</p>\n\n<ul>\n<li>Linebreak</li>\n</ul>\n",
 832
 833		"*   List\n    * Nested list\n",
 834		"<ul>\n<li>List\n\n<ul>\n<li>Nested list</li>\n</ul></li>\n</ul>\n",
 835
 836		"*   List\n\n    * Nested list\n",
 837		"<ul>\n<li><p>List</p>\n\n<ul>\n<li>Nested list</li>\n</ul></li>\n</ul>\n",
 838
 839		"*   List\n    Second line\n\n    + Nested\n",
 840		"<ul>\n<li><p>List\nSecond line</p>\n\n<ul>\n<li>Nested</li>\n</ul></li>\n</ul>\n",
 841
 842		"*   List\n    + Nested\n\n    Continued\n",
 843		"<ul>\n<li><p>List</p>\n\n<ul>\n<li>Nested</li>\n</ul>\n\n<p>Continued</p></li>\n</ul>\n",
 844
 845		"*   List\n   * shallow indent\n",
 846		"<ul>\n<li>List\n\n<ul>\n<li>shallow indent</li>\n</ul></li>\n</ul>\n",
 847
 848		"* List\n" +
 849			" * shallow indent\n" +
 850			"  * part of second list\n" +
 851			"   * still second\n" +
 852			"    * almost there\n" +
 853			"     * third level\n",
 854		"<ul>\n" +
 855			"<li>List\n\n" +
 856			"<ul>\n" +
 857			"<li>shallow indent</li>\n" +
 858			"<li>part of second list</li>\n" +
 859			"<li>still second</li>\n" +
 860			"<li>almost there\n\n" +
 861			"<ul>\n" +
 862			"<li>third level</li>\n" +
 863			"</ul></li>\n" +
 864			"</ul></li>\n" +
 865			"</ul>\n",
 866
 867		"* List\n        extra indent, same paragraph\n",
 868		"<ul>\n<li>List\n    extra indent, same paragraph</li>\n</ul>\n",
 869
 870		"* List\n\n        code block\n",
 871		"<ul>\n<li><p>List</p>\n\n<pre><code>code block\n</code></pre></li>\n</ul>\n",
 872
 873		"* List\n\n          code block with spaces\n",
 874		"<ul>\n<li><p>List</p>\n\n<pre><code>  code block with spaces\n</code></pre></li>\n</ul>\n",
 875
 876		"* List\n\n    * sublist\n\n    normal text\n\n    * another sublist\n",
 877		"<ul>\n<li><p>List</p>\n\n<ul>\n<li>sublist</li>\n</ul>\n\n<p>normal text</p>\n\n<ul>\n<li>another sublist</li>\n</ul></li>\n</ul>\n",
 878	}
 879	doTestsBlock(t, tests, EXTENSION_NO_EMPTY_LINE_BEFORE_BLOCK)
 880}
 881
 882func TestOrderedList_EXTENSION_NO_EMPTY_LINE_BEFORE_BLOCK(t *testing.T) {
 883	var tests = []string{
 884		"1. Hello\n",
 885		"<ol>\n<li>Hello</li>\n</ol>\n",
 886
 887		"1. Yin\n2. Yang\n",
 888		"<ol>\n<li>Yin</li>\n<li>Yang</li>\n</ol>\n",
 889
 890		"1. Ting\n2. Bong\n3. Goo\n",
 891		"<ol>\n<li>Ting</li>\n<li>Bong</li>\n<li>Goo</li>\n</ol>\n",
 892
 893		"1. Yin\n\n2. Yang\n",
 894		"<ol>\n<li><p>Yin</p></li>\n\n<li><p>Yang</p></li>\n</ol>\n",
 895
 896		"1. Ting\n\n2. Bong\n3. Goo\n",
 897		"<ol>\n<li><p>Ting</p></li>\n\n<li><p>Bong</p></li>\n\n<li><p>Goo</p></li>\n</ol>\n",
 898
 899		"1 Hello\n",
 900		"<p>1 Hello</p>\n",
 901
 902		"1.Hello\n",
 903		"<p>1.Hello</p>\n",
 904
 905		"1.  Hello \n",
 906		"<ol>\n<li>Hello</li>\n</ol>\n",
 907
 908		"1.  Hello \n    Next line \n",
 909		"<ol>\n<li>Hello\nNext line</li>\n</ol>\n",
 910
 911		"Paragraph\n1. No linebreak\n",
 912		"<p>Paragraph</p>\n\n<ol>\n<li>No linebreak</li>\n</ol>\n",
 913
 914		"Paragraph\n\n1. Linebreak\n",
 915		"<p>Paragraph</p>\n\n<ol>\n<li>Linebreak</li>\n</ol>\n",
 916
 917		"1.  List\n    1. Nested list\n",
 918		"<ol>\n<li>List\n\n<ol>\n<li>Nested list</li>\n</ol></li>\n</ol>\n",
 919
 920		"1.  List\n\n    1. Nested list\n",
 921		"<ol>\n<li><p>List</p>\n\n<ol>\n<li>Nested list</li>\n</ol></li>\n</ol>\n",
 922
 923		"1.  List\n    Second line\n\n    1. Nested\n",
 924		"<ol>\n<li><p>List\nSecond line</p>\n\n<ol>\n<li>Nested</li>\n</ol></li>\n</ol>\n",
 925
 926		"1.  List\n    1. Nested\n\n    Continued\n",
 927		"<ol>\n<li><p>List</p>\n\n<ol>\n<li>Nested</li>\n</ol>\n\n<p>Continued</p></li>\n</ol>\n",
 928
 929		"1.  List\n   1. shallow indent\n",
 930		"<ol>\n<li>List\n\n<ol>\n<li>shallow indent</li>\n</ol></li>\n</ol>\n",
 931
 932		"1. List\n" +
 933			" 1. shallow indent\n" +
 934			"  2. part of second list\n" +
 935			"   3. still second\n" +
 936			"    4. almost there\n" +
 937			"     1. third level\n",
 938		"<ol>\n" +
 939			"<li>List\n\n" +
 940			"<ol>\n" +
 941			"<li>shallow indent</li>\n" +
 942			"<li>part of second list</li>\n" +
 943			"<li>still second</li>\n" +
 944			"<li>almost there\n\n" +
 945			"<ol>\n" +
 946			"<li>third level</li>\n" +
 947			"</ol></li>\n" +
 948			"</ol></li>\n" +
 949			"</ol>\n",
 950
 951		"1. List\n        extra indent, same paragraph\n",
 952		"<ol>\n<li>List\n    extra indent, same paragraph</li>\n</ol>\n",
 953
 954		"1. List\n\n        code block\n",
 955		"<ol>\n<li><p>List</p>\n\n<pre><code>code block\n</code></pre></li>\n</ol>\n",
 956
 957		"1. List\n\n          code block with spaces\n",
 958		"<ol>\n<li><p>List</p>\n\n<pre><code>  code block with spaces\n</code></pre></li>\n</ol>\n",
 959
 960		"1. List\n    * Mixted list\n",
 961		"<ol>\n<li>List\n\n<ul>\n<li>Mixted list</li>\n</ul></li>\n</ol>\n",
 962
 963		"1. List\n * Mixed list\n",
 964		"<ol>\n<li>List\n\n<ul>\n<li>Mixed list</li>\n</ul></li>\n</ol>\n",
 965
 966		"* Start with unordered\n 1. Ordered\n",
 967		"<ul>\n<li>Start with unordered\n\n<ol>\n<li>Ordered</li>\n</ol></li>\n</ul>\n",
 968
 969		"* Start with unordered\n    1. Ordered\n",
 970		"<ul>\n<li>Start with unordered\n\n<ol>\n<li>Ordered</li>\n</ol></li>\n</ul>\n",
 971
 972		"1. numbers\n1. are ignored\n",
 973		"<ol>\n<li>numbers</li>\n<li>are ignored</li>\n</ol>\n",
 974	}
 975	doTestsBlock(t, tests, EXTENSION_NO_EMPTY_LINE_BEFORE_BLOCK)
 976}
 977
 978func TestFencedCodeBlock_EXTENSION_NO_EMPTY_LINE_BEFORE_BLOCK(t *testing.T) {
 979	var tests = []string{
 980		"``` go\nfunc foo() bool {\n\treturn true;\n}\n```\n",
 981		"<pre><code class=\"go\">func foo() bool {\n\treturn true;\n}\n</code></pre>\n",
 982
 983		"``` c\n/* special & char < > \" escaping */\n```\n",
 984		"<pre><code class=\"c\">/* special &amp; char &lt; &gt; &quot; escaping */\n</code></pre>\n",
 985
 986		"``` c\nno *inline* processing ~~of text~~\n```\n",
 987		"<pre><code class=\"c\">no *inline* processing ~~of text~~\n</code></pre>\n",
 988
 989		"```\nNo language\n```\n",
 990		"<pre><code>No language\n</code></pre>\n",
 991
 992		"``` {ocaml}\nlanguage in braces\n```\n",
 993		"<pre><code class=\"ocaml\">language in braces\n</code></pre>\n",
 994
 995		"```    {ocaml}      \nwith extra whitespace\n```\n",
 996		"<pre><code class=\"ocaml\">with extra whitespace\n</code></pre>\n",
 997
 998		"```{   ocaml   }\nwith extra whitespace\n```\n",
 999		"<pre><code class=\"ocaml\">with extra whitespace\n</code></pre>\n",
1000
1001		"~ ~~ java\nWith whitespace\n~~~\n",
1002		"<p>~ ~~ java\nWith whitespace\n~~~</p>\n",
1003
1004		"~~\nonly two\n~~\n",
1005		"<p>~~\nonly two\n~~</p>\n",
1006
1007		"```` python\nextra\n````\n",
1008		"<pre><code class=\"python\">extra\n</code></pre>\n",
1009
1010		"~~~ perl\nthree to start, four to end\n~~~~\n",
1011		"<p>~~~ perl\nthree to start, four to end\n~~~~</p>\n",
1012
1013		"~~~~ perl\nfour to start, three to end\n~~~\n",
1014		"<p>~~~~ perl\nfour to start, three to end\n~~~</p>\n",
1015
1016		"~~~ bash\ntildes\n~~~\n",
1017		"<pre><code class=\"bash\">tildes\n</code></pre>\n",
1018
1019		"``` lisp\nno ending\n",
1020		"<p>``` lisp\nno ending</p>\n",
1021
1022		"~~~ lisp\nend with language\n~~~ lisp\n",
1023		"<p>~~~ lisp\nend with language\n~~~ lisp</p>\n",
1024
1025		"```\nmismatched begin and end\n~~~\n",
1026		"<p>```\nmismatched begin and end\n~~~</p>\n",
1027
1028		"~~~\nmismatched begin and end\n```\n",
1029		"<p>~~~\nmismatched begin and end\n```</p>\n",
1030
1031		"   ``` oz\nleading spaces\n```\n",
1032		"<pre><code class=\"oz\">leading spaces\n</code></pre>\n",
1033
1034		"  ``` oz\nleading spaces\n ```\n",
1035		"<pre><code class=\"oz\">leading spaces\n</code></pre>\n",
1036
1037		" ``` oz\nleading spaces\n  ```\n",
1038		"<pre><code class=\"oz\">leading spaces\n</code></pre>\n",
1039
1040		"``` oz\nleading spaces\n   ```\n",
1041		"<pre><code class=\"oz\">leading spaces\n</code></pre>\n",
1042
1043		"    ``` oz\nleading spaces\n    ```\n",
1044		"<pre><code>``` oz\n</code></pre>\n\n<p>leading spaces</p>\n\n<pre><code>```\n</code></pre>\n",
1045	}
1046	doTestsBlock(t, tests, EXTENSION_FENCED_CODE|EXTENSION_NO_EMPTY_LINE_BEFORE_BLOCK)
1047}