This site provides a machine-readable index at /llms.txt.

Skip to main content Skip to navigation

Code-block argument reference

Pennington applies two grammars to a fenced code block: info-string tokens on the opening fence line (language, optional colon-suffix, key=value attributes), and [!code …] directives embedded in line-trailing comments. Markdig parses the info string and exposes the language token on FencedCodeBlock.Info and the attribute tail on FencedCodeBlock.Arguments; the directive pass runs against the highlighted HTML before the block is rendered.

This page is the grammar spec. For task-oriented usage see the Markdown extensions catalog and the How-To guides linked below.

Fence info-string grammar

The info string is the text on the opening fence line after the three backticks. Markdig tokenises it left-to-right: the first whitespace-separated token is the language (with an optional colon-suffix), and remaining tokens are key=value attribute pairs. Values may be bare, single-quoted, or double-quoted — quoting is required only when the value contains whitespace.

info-string   := language [ ":" suffix ] ( WS attribute )*
language      := IDENT                              ; for example csharp, razor, text
suffix        := "path" | "xmldocid" | "xmldocid,bodyonly" | "xmldocid-diff" | "xmldocid-diff,bodyonly"
attribute     := key "=" value
key           := IDENT
value         := bare-value | "'" quoted-value "'" | '"' quoted-value '"'
bare-value    := any run of non-whitespace chars
quoted-value  := any chars up to the matching quote

Markdig exposes the language and colon-suffix on FencedCodeBlock.Info and the attribute tail on FencedCodeBlock.Arguments. Pennington's built-in extensions read attribute keys case-insensitively.

Attributes

The table below lists the key=value attributes Pennington's built-in extensions consume from the info string. A custom Markdig extension registered into the pipeline can read additional keys directly from FencedCodeBlock.Arguments.

Name Values Description Example
tabs true Marks adjacent fenced blocks for grouping into a single tabbed widget. ```csharp tabs=true title="C#"
title any quoted string Tab label shown on the tabbed widget; falls back to the normalised language name when omitted. ```csharp tabs=true title="Program.cs"

Suffix forms (code-embedding)

The four colon-suffix forms switch a fenced block from literal content to a code-embedding directive preprocessed before highlighting; suffix forms are resolved by an ICodeBlockPreprocessor, with Pennington.Roslyn shipping the implementation for xmldocid and xmldocid-diff.

Form Body shape Description
<lang>:path one file path relative to the solution directory Embeds the entire file contents as the code-block body.
<lang>:xmldocid one XmlDocId per line (T:, M:, P:, F:, E:) Embeds each symbol's declaration and body, concatenated in order.
<lang>:xmldocid,bodyonly one XmlDocId per line Embeds only the member body, stripping the declaration line and enclosing braces.
<lang>:xmldocid-diff exactly two XmlDocIds, before then after Emits a unified diff between the two symbols' source text; accepts the ,bodyonly suffix.

[!code …] directives

A directive is the literal text [!code <notation>] wrapped in a line-trailing comment marker recognised for the block's language (//, #, --, <!--, *, %, ', REM, ;, /*); the directive pass runs against the highlighted HTML. The comment marker is stripped when the directive consumes the whole comment and preserved when trailing content remains; the directive itself is always removed from the rendered line.

Directive Behavior Example
highlight (alias hl) Adds class highlight to the line and has-highlighted to the <pre>. var x = 1; // [!code highlight]
++ Adds class diff-add to the line and has-diff to the <pre>. var x = 1; // [!code ++]
-- Adds class diff-remove to the line and has-diff to the <pre>. var x = 0; // [!code --]
focus Adds class focused to the line, has-focused to the <pre>, and blurred to every non-focused line. var x = 1; // [!code focus]
error Adds class error to the line and has-errors to the <pre>. throw new(); // [!code error]
warning Adds class warning to the line and has-warnings to the <pre>. // TODO // [!code warning]
word:TEXT Wraps the first occurrence of TEXT on the line in <span class="word-highlight">. var token = Get(); // [!code word:token]
word:TEXT\|MESSAGE As word:, but wraps the span in a callout carrying MESSAGE. // [!code word:token\|The auth token]
include-start / include-end Marks a region to retain; all lines outside paired include regions are dropped. // [!code include-start] ... // [!code include-end]
exclude-start / exclude-end Marks a region to drop; lines inside are removed from the rendered output. // [!code exclude-start] ... // [!code exclude-end]

See also