Sashmark / Blog

Markdown reference links: syntax and plain-text fixes

Bobby Huang ·

This page walks through the definition line, how labels are matched, the full, collapsed and shortcut forms, and title quoting. A numbered list in the body covers the causes behind a definition line that prints as plain text, each tested with pandoc. Switching a file between the two link styles gets its own section near the end.

Key takeaways

  • An inline link and a reference link appear in the opening section, written for the same sentence.
  • The definition line gets its own section, with the parts named one by one.
  • Label matching and the full, collapsed and shortcut forms each have a tested example.
  • A numbered list explains the cases where a definition line prints as plain text.
  • The conversion section shows a pandoc command and what to check in its output.

An agent writes a status note with twenty links in it, and every sentence ends in a long path in parentheses. The raw file turns into a wall of paths. Markdown reference links fix that by moving each address to its own line.

They can also fail quietly. When a definition sits in the wrong spot, pandoc gives no warning. The definition prints as text, and the link that needed it prints as brackets. This guide walks through the syntax, the three forms, title quoting, and a numbered pass for definitions that print as plain text.

Inline links and reference links

CommonMark names two basic kinds of link. An inline link puts the address right after the link text. A reference link puts the address somewhere else in the document and points to it by label.

The same sentence, written both ways:

Read the [handoff note](notes/handoff.md) before you start.

Read the [handoff note][handoff] before you start.

[handoff]: notes/handoff.md "Handoff from Jane Doe"

Pandoc turns both sentences into a link to notes/handoff.md. The second one also carries the title from the definition line. The definition line itself adds nothing to the page.

For relative paths and links between files, see linking one file to another. Our one-page reference shows both link styles beside every other element.

The definition line

A definition line has this shape: [label]: destination "optional title". In order, it holds:

  1. The label in square brackets. At most three leading spaces are allowed before it.
  2. A colon right after the closing bracket.
  3. The destination, the address the link goes to. The gap after the colon can hold spaces, tabs, and at most one line ending.
  4. An optional title, set apart from the destination by spaces or tabs.

Nothing else may follow on the line. The definition isn't a visible element. It only gives a label a target that links elsewhere in the file can use.

A label can't be blank: it needs some character other than a space, tab or line ending. Unescaped [ or ] characters aren't allowed inside it, and its length tops out at 999 characters.

Placement is loose. A definition may sit above the links that rely on it or below them. Many writers keep them together near the end of a section or file so the prose reads cleanly. When two definitions share one label, the parser uses the first and ignores the second.

How labels match

Labels are compared after a cleanup step. The parser strips the brackets, applies Unicode case folding, trims spaces, tabs and line endings at both ends, and squeezes each inner run of them down to one space. So case doesn't matter:

See the [plan][PLAN] and the [Plan][].

[plan]: plans/plan.md

Pandoc links both, because PLAN, Plan and plan all fold to one value. A typo breaks the match. [plan][plans] against a [plan]: line has no match, so the brackets stay on the page as typed.

Full, collapsed and shortcut forms

Once a definition exists, you can point at it three ways:

Full: [the latest plan][plan]
Collapsed: [plan][]
Shortcut: [plan]

[plan]: plans/plan.md
  • Full. The link text comes first, then the label. Use it when the words in your sentence differ from the label.
  • Collapsed. The label doubles as the link text, followed by an empty pair []. The spec treats [plan][] the same as [plan][plan].
  • Shortcut. Just the label in brackets. The spec treats [plan] the same as [plan][].

All three produced the same link target in pandoc. One trap applies to the full and collapsed forms: no space may sit between the two bracket pairs. Write [latest plan] [plan] with a space and pandoc renders [latest plan] as literal text, while [plan] alone becomes a shortcut link. The spec gives this rule as a guard against two shortcut links being read as one.

Quoting a title

Wrap a title in straight double quotes, straight single quotes, or parentheses:

[a]: a.md "Double quotes"
[b]: b.md 'Single quotes'
[c]: c.md (Parentheses)

Pandoc gave each link the matching title. A title may run over several lines, but a blank line inside it breaks the definition. To use the quote character inside the title, put a backslash before it, or pick another pair. In many viewers, hovering over the link pops the title up as a tooltip; some display nothing.

Why a definition prints as plain text

Each case below was tested with pandoc -f commonmark -t html on a scratch file. Work down the list.

  1. Separate the definition from the paragraph above. The spec won't let a definition start partway through a paragraph. In this file the second line joins the paragraph above it as plain text, and [plan] stays as brackets:

    Notes from Jane Doe follow.
    [plan]: plans/plan.md
    

    One empty line between them fixes it. A definition may follow a heading with no blank line, though, and it needs no blank line after it.

  2. Cut the indent to three spaces or fewer. Four spaces of indent turn the line into an indented code block, so pandoc outputs it inside a pre element. Three spaces still work.

  3. Move it out of a code fence. Inside a fenced block the line is literal code. How a fence begins and ends is covered in the code blocks post.

  4. Delete anything after the title. A line like [plan]: plans/plan.md "Plan" (draft) has extra characters after the title, so it fails as a definition and prints as a paragraph.

  5. Put a space before the title. The title must be set apart from the destination by spaces or tabs. In the spec's own example, <bar>(baz) with no space fails.

  6. Check that a destination is there. A label and colon with no destination after them isn't a definition.

  7. Check the label spelling. If the line vanished from the page but the link still shows brackets, the definition worked and the label in your sentence doesn't match it.

Then render again and compare the page with the raw text.

Convert a file between styles

Pandoc can rewrite a file in either direction. To turn inline links into reference links:

pandoc -f commonmark -t commonmark --reference-links notes.md

On a test file, pandoc moved the addresses into definition lines after the last paragraph and indented each by two spaces, which is within the three the spec allows. Leave off --reference-links and pandoc writes every link inline. Pandoc also rewraps the text as it goes, so run it on a copy and compare before you keep the result. Our reformatting-on-save post explains how rewrapping bloats a diff.

A note on footnotes

A footnote marker like [^1] looks a lot like a shortcut reference link, but footnotes are a separate feature covered in Markdown footnotes.

Where Sashmark fits

Our planned desktop app, Sashmark, will render and edit Markdown that your agents change over and over. It is in development and has not been released. Planned for v1: links, block quotes, code blocks, tables, lists and headings rendered live, plus editing directly in the rendered view, where the plan is for saving to keep every line you leave alone exactly as it was, byte for byte. A Changes View is also planned, to mark what changed after your previous read. The app itself has no AI features. To track progress, see our help pages, roadmap and planned features.

Project news: sashmark.com.

Questions

Why would a definition line print as plain text?
The numbered fix list works through the causes and what to check.
Do reference labels have to match in case?
Our matching-labels section answers this, with a short example you can test.
Where in the file can the definition lines go?
Placement, and what happens when a label is defined twice, are covered in the definition line section.
Are footnotes a kind of reference link?
The short section near the end points to the footnotes post, which covers their syntax.

What Sashmark plans for v1: Features · Roadmap

View as Markdown