parser

package
v0.1.6 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Jul 6, 2026 License: MIT Imports: 31 Imported by: 0

Documentation

Overview

Package parser implements the Markdown processing pipeline for kwelea.

The two exported entry points are:

  • Parse converts a Markdown source file into rendered HTML, an in-page table-of-contents, and the plain-text H1 title (if present). It runs the full goldmark pipeline including syntax highlighting, admonitions, and D2 diagram rendering.

  • ChromaCSS generates a combined Chroma stylesheet containing both a light-mode and a dark-mode rule set, written once per build to assets/chroma.css in the output directory.

Markdown extensions provided by this package:

  • Admonitions: ::: info / ::: tip / ::: warning / ::: danger / ::: details blocks rendered as styled <div> or <details> elements.

  • D2 diagrams: fenced code blocks with language "d2" are compiled to inline SVG pairs (light + dark) using the D2 Go library.

  • Code-block title and line highlighting: fenced code blocks accept title="…" and {n,m-p} attributes on the opening fence. The title is rendered as a label bar above the block; the range is applied as a class="highlight-line" on the matching lines. Implementation lives in highlight.go (NewCodeAttrsExtension).

Index

Constants

This section is empty.

Variables

View Source
var Admonitions goldmark.Extender = &admonitionsExtension{}

Admonitions is the goldmark.Extender that adds ::: container block support.

View Source
var KindAdmonition = goldmarkast.NewNodeKind("Admonition")

KindAdmonition is the goldmark AST node kind for ::: container blocks.

View Source
var KindCodeBlock = goldmarkast.NewNodeKind("CodeBlock")

KindCodeBlock is the goldmark AST node kind for a fenced code block that carries kwelea-specific attributes (title and/or line highlights).

View Source
var KindD2 = goldmarkast.NewNodeKind("D2Diagram")

KindD2 is the goldmark AST node kind for rendered D2 diagrams.

Functions

func ChromaCSS

func ChromaCSS(themeCfg config.ThemeConfig) (string, error)

ChromaCSS generates a combined Chroma syntax-highlighting CSS string for both the light and dark themes specified in themeCfg.

Both themes' rules are scoped — light to :root:not([data-theme="dark"]), dark to [data-theme="dark"] — so they activate only for their matching attribute value, matching the toggle logic in the template.

Scoping the light rules (not just the dark ones) matters: a Chroma style commonly leaves some token types with no explicit colour, relying on the base foreground colour instead (e.g. github-dark has no entry for plain identifiers or punctuation). If light rules were left unscoped, that unscoped light-theme colour would directly match the element in dark mode too — and a rule that directly matches an element always wins over a colour the element would otherwise inherit from .chroma's own (correctly dark) base colour, regardless of [data-theme="dark"] specificity. The result was barely-legible dark-navy text on a dark background for any token the dark style doesn't explicitly colour.

WithLineNumbers must match the options used by renderCodeBlockBody so this generates the matching ".ln"/"line" CSS — plain highlighted blocks never emit that markup, so the extra rules are simply unused for them.

func NewCodeAttrsExtension added in v0.1.6

func NewCodeAttrsExtension(themeCfg config.ThemeConfig) goldmark.Extender

NewCodeAttrsExtension returns a goldmark.Extender that adds title and line-highlight support to fenced code blocks. The theme name matches the one used to build the chroma stylesheet (see ChromaCSS); only the light style is needed (see renderCodeBlockBody).

func NewD2Extension

func NewD2Extension() goldmark.Extender

NewD2Extension returns a goldmark.Extender that intercepts ```d2 fenced code blocks at AST-transform time and replaces them with pre-rendered dual-theme inline SVG.

func Parse

func Parse(filePath string, src []byte, themeCfg config.ThemeConfig) (template.HTML, []nav.TocItem, string, error)

Parse processes a Markdown source file and returns the rendered HTML body, a table of contents extracted from h2/h3 headings, the plain text of the first H1 heading (empty string if absent), and any error.

The first H1 heading is stripped from the AST before rendering so that it does not appear in the HTML body — the page template renders the title from Page.Title, avoiding a duplicate. The extracted text is returned so the builder can use it as a Page.Title fallback when frontmatter provides no title.

filePath is used for error messages only. themeCfg selects the Chroma style names written into CSS classes (see ChromaCSS for the matching stylesheet).

Types

type AdmonitionNode

type AdmonitionNode struct {
	goldmarkast.BaseBlock
	AdmonitionType string // "info" | "tip" | "warning" | "danger" | "details"
	Title          string // for details: the <summary> text; otherwise empty
}

AdmonitionNode is an AST block node wrapping a ::: container block. Its children are the parsed Markdown contents of the block body.

func NewAdmonitionNode

func NewAdmonitionNode(admonType, title string) *AdmonitionNode

NewAdmonitionNode allocates an AdmonitionNode with the given type and title.

func (*AdmonitionNode) Dump

func (n *AdmonitionNode) Dump(source []byte, level int)

Dump writes a debug representation of the node to standard output, satisfying the goldmark ast.Node interface.

func (*AdmonitionNode) Kind

Kind returns KindAdmonition, satisfying the goldmark ast.Node interface.

type CodeBlockNode added in v0.1.6

type CodeBlockNode struct {
	goldmarkast.BaseBlock
	Language     string       // "" when no language was specified
	Title        string       // "" when no title was specified
	Highlight    []int        // 1-indexed lines to highlight (nil/empty when none)
	HighlightSet map[int]bool // set form for O(1) membership
	Source       []byte       // raw source bytes (lines joined with '\n')
}

CodeBlockNode is an AST block node that replaces a FencedCodeBlock during the codeAttrsTransformer pass when the block's info string contains title="…" or {n,m-p} attributes. The source bytes are stored verbatim because Chroma tokenises from the raw source.

func (*CodeBlockNode) Dump added in v0.1.6

func (n *CodeBlockNode) Dump(source []byte, level int)

Dump writes a debug representation of the node to standard output, satisfying the goldmark ast.Node interface.

func (*CodeBlockNode) Kind added in v0.1.6

Kind returns KindCodeBlock, satisfying the goldmark ast.Node interface.

type D2Node

type D2Node struct {
	goldmarkast.BaseBlock
	SVG []byte // rendered HTML: <div class="d2-diagram"><div class="d2-light">…</div><div class="d2-dark">…</div></div>
}

D2Node is an AST block node that holds pre-rendered SVG HTML for a D2 diagram. It replaces FencedCodeBlock nodes with language "d2" during the AST transform pass, before goldmark-highlighting processes fenced blocks.

func (*D2Node) Dump

func (n *D2Node) Dump(source []byte, level int)

Dump writes a debug representation of the node to standard output, satisfying the goldmark ast.Node interface.

func (*D2Node) Kind

func (n *D2Node) Kind() goldmarkast.NodeKind

Kind returns KindD2, satisfying the goldmark ast.Node interface.

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL