kjdev / hoextdown

Hoextdown is an extension to Hoedown
MIT License
23 stars 15 forks source link

The problem with the code as it exists is that it is impossible to in… #28

Closed jasharpe closed 8 years ago

jasharpe commented 8 years ago

The problem with the code as it exists is that it is impossible to include a pipe literal in a code span in a table! For example, this Markdown is broken:

foo | bar `|` | baz
--- | --- | ---
foo | bar | baz

There are two issues that prevent including pipes in codespans in tables:

  1. Codespans don't support any kind of escaping (this is specified in the original Markdown spec).
  2. Pipe-detection logic in table parsing doesn't care whether a pipe is inside a codespan or not.

(2) is actually desirable, since this allows splitting codespan contents across multiple lines when using the --multiline-tables extension. e.g. we want this to work as expected ("bar baz" being rendered as a codespan for the middle header cell):

| foo | `bar | baz |
:     : baz` :     :
| --- | ---- | --- |
| foo | bar  | baz |

So the solution goes after (1), allowing some limited escaping, only for pipes and colons inside tables.

The solution implemented here is that in tables, literal pipes and colons (in the case of multiline extension rows) must be escaped with a backslash, even in codespans. This escaping backslash is then removed from the text before it is passed to parse_inline to render cell contents.

This allows a simple rule that is easy to understand and implement by a Markdown author: "Any literal pipe on a regular row, and any literal colon on a continued row, must be escaped by a backslash."

An implementation detail is that we replace is_escaped with is_backslashed for pipes/colons in tables. This is a stricter check, since is_escaped will not consider the pipe in "\|" to be escaped, while is_backslashed will. This is to allow \| to render as "|" a literal pipe in a codespan, and \\| to render as "|". (See the added tests for more examples of how this stricter escaping allows greater expressiveness.)

This is not likely to break any existing Markdown, because the only cases to break would be an even number of backslashes directly before a pipe that is intended as a separator, e.g.

foo \\| bar
----- | ---
foo   | bar

This is a really, really rare edge case, that I doubt anyone does intentionally.

codecov-io commented 8 years ago

Current coverage is 75.76%

Merging #28 into master will increase coverage by +0.12% as of c63af3a

@@            master     #28   diff @@
======================================
  Files           14      14       
  Stmts         4102    4126    +24
  Branches         0       0       
  Methods          0       0       
======================================
+ Hit           3103    3126    +23
  Partial          0       0       
- Missed         999    1000     +1

Review entire Coverage Diff as of c63af3a

Powered by Codecov. Updated on successful CI builds.