Skip to content

fix: escape pipe characters in column titles#56

Closed
greymoth-jp wants to merge 1 commit into
haltcase:canaryfrom
greymoth-jp:fix/escape-pipes-in-column-titles
Closed

fix: escape pipe characters in column titles#56
greymoth-jp wants to merge 1 commit into
haltcase:canaryfrom
greymoth-jp:fix/escape-pipes-in-column-titles

Conversation

@greymoth-jp

Copy link
Copy Markdown

Cell values are escaped through toCellText so a | becomes \|, and there is a test for it ("escapes pipe characters in cells by default"). Column titles skip that step: getColumnTitle returns the supplied name, the toHeaderTitle result, or the cased key verbatim. So a pipe in a column title lands in the header row unescaped:

import { tablemark } from "tablemark";

tablemark([{ range: 5 }, { range: 12 }], { columns: [{ name: "Min | Max" }] });
| Min | Max |
| :-------- |
| 5         |
| 12        |

The header row now has two cells while the delimiter row has one. The GFM tables spec requires the header row to match the delimiter row in cell count, otherwise the block is not parsed as a table. Rendered through marked the whole table collapses into a paragraph. The same "Min | Max" placed in a body cell comes out as Min \| Max, so the two paths disagree.

Fix

Escape pipes in the resolved column title the same way cell values are escaped. I pulled the existing pipe escaping out of toCellText into a small escapePipes helper so both the cell path and the title path use one routine. With the fix the example becomes:

| Min \| Max |
| :--------- |
| 5          |
| 12         |

which parses as a one column table with the header Min | Max.

Tests

Added "escapes pipe characters in column titles by default" alongside the existing cell test. Reverting the change makes the new snapshot mismatch. Full suite passes (76), and oxlint, eslint, prettier and tsc --noEmit are clean.

Cell values are escaped through `toCellText`, but column titles were
emitted verbatim. A column `name` containing a pipe (or a key that keeps
its pipe through the header-case transform) put an unescaped `|` in the
header row, giving it more cells than the delimiter row. Per the GFM
spec the table is then not recognized at all.

Escape the resolved column title the same way cell values are escaped,
via a shared `escapePipes` helper.
@haltcase-bot

haltcase-bot Bot commented Jun 30, 2026

Copy link
Copy Markdown

Hey @greymoth-jp, thanks for contributing! If you haven't read the contributing guide that outlines the process, you can do so here.

Maintainers: once checks have passed, comment !release this and I'll begin merging this for you.

@greymoth-jp

Copy link
Copy Markdown
Author

Closing this to clean up my open PRs. It's a small change and not really worth taking up your review time. Sorry for the noise.

@greymoth-jp greymoth-jp closed this Jul 4, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant