Package 2.0 | Rich IR document contract 1.0.0 | Local validation

Markdown Engine

A deterministic parsing and validation boundary for teams that need Markdown to behave like an operational contract, not an unchecked blob of prose.

Input
GFM Markdown plus YAML frontmatter
Output
Stable JSON, rich IR, precise diagnostics
Boundary
No network, no arbitrary plugins, no hidden semantics

Plain-language story

It checks the important parts of Markdown before people depend on it.

Teams often keep serious work in Markdown: release checklists, operating specs, handoff notes, requirements, and agent instructions. Those files are easy for humans to read, but most tools still treat them like loose text.

That means a document can look finished while a required section is missing, a table column was renamed, a release gate has no owner, or an evidence link no longer proves anything. The mistake is usually found later, during review, release, or handoff.

Markdown Engine lets a team write simple rules for the document: these sections must exist, these fields at the top must be present, these IDs must be unique, and these links must point to the right evidence. Then it checks the file locally and returns clear pass/fail results that a person, CI job, or agent can trust.

Before

The Markdown looks fine.

A checklist reads well, but a release gate, owner field, or evidence link can silently drift out of shape.

Rule

The expected shape is written down.

A small rules file says which headings, fields, tables, IDs, text, and links the document must contain.

After

The document proves it is ready.

The engine gives the same answer every time and points to what is wrong before the file is reviewed, merged, published, or handed to an agent.

Consumer value

Use Markdown where failure needs evidence.

Markdown Engine gives downstream tools a stable document model, deterministic validation, and diagnostics that can be reviewed, stored, diffed, and gated in CI.

Parse once, consume safely

Normalize GFM, frontmatter, source ranges, links, lists, tables, sections, and text spans into an engine-owned IR instead of binding consumers to raw parser ASTs.

Make document rules explicit

Express required headings, frontmatter fields, table columns, IDs, literal text, links, and trace references with closed, YAML-friendly profile data.

Fail locally before review

Run the CLI or API before a release, handoff, or agent task and get structured diagnostics instead of late reviewer discovery.

Protect the deterministic boundary

Profile inputs are data. Regex-like keys, executable-like keys, accessors, proxies, cycles, and unsafe shapes are rejected as inert config errors.

Where it fits

A foundation for profiled Markdown systems.

The package is intentionally narrow: parse, normalize, validate, serialize. That makes it useful as the deterministic substrate for docs platforms, release operations, requirements evidence, and future agent runtime lenses.

01

Docs and platform teams

Keep required document sections, frontmatter, links, tables, and structural IDs consistent across repositories.

02

Release operators

Turn release checklists into repeatable local gates before npm packing, publishing, or human approval.

03

Agent runtime builders

Feed coding agents normalized document contracts and deterministic evidence instead of asking them to infer process from raw Markdown.

Grounded workflows

Fixture workflows and profile patterns.

The first three narratives map to shipped fixture profiles and passing Markdown documents. The `SKILL.md` and `PLAYBOOK.md` patterns show how consumers can define their own document types with the same deterministic contract model.

Operational spec

Confirm every handoff carries the same structure.

A platform team wants each operating spec to include objective, constraints, execution plan, risk register, and handoff links. Markdown Engine validates those sections, checks table shape, enforces `OPS-RISK` IDs, and proves the expected handoff link is present.

  • Frontmatter includes `title`, `owner`, and `status`.
  • Required sections appear in strict order.
  • Risk IDs are unique and use the `OPS-RISK` prefix.
profile.yaml
syntaxVersion: markdown-engine.validation@v1
documentVersion: 1.0.0
rules:
  - id: frontmatter.required
    select:
      target: document
    assert:
      frontmatterRequired:
        fields:
          - title
          - owner
          - status

  - id: sections.required
    select:
      target: document
    assert:
      sectionsRequired:
        order: strict
        headings:
          - Objective
          - Context / Constraints
          - Execution Plan
          - Risk Register
          - Handoff Links

  - id: risk.table.columns
    select:
      target: table
      section: Risk Register
      header:
        - ID
        - Mitigation
        - Status
    assert:
      tableColumnsRequired:
        columns:
          - ID
          - Mitigation
          - Status

  - id: risk.ids.unique
    select:
      target: tableCell
      section: Risk Register
      column: ID
    assert:
      ids:
        prefix: OPS-RISK
        unique: true

  - id: handoff.link
    select:
      target: link
      section: Handoff Links
      text: handoff packet
      url: ./handoff-packet.md
    assert:
      exists: true
pass.md
---
title: Operational Spec Example
owner: platform-team
status: ready
---

# Objective

Mission control uses this structural profile to confirm a small operating spec
has the required sections, handoff links, and risk tracking details.

# Context / Constraints

The example stays generic. It validates Markdown headings, tables, IDs, list
content, literal text, and links without attaching domain meaning to the core
engine.

# Execution Plan

- MUST Validate profile fixtures locally.
- MUST Record evidence before requesting review.
- Keep the checks deterministic and local-only.

# Risk Register

| ID | Mitigation | Status |
| --- | --- | --- |
| OPS-RISK-1 | Keep examples structural. | tracked |
| OPS-RISK-2 | Keep commands local. | closed |

# Handoff Links

The [handoff packet](./handoff-packet.md) records follow-up review notes for the
next operator.

Quickstart

Install, validate, then integrate.

Start with the CLI to inspect behavior against bundled fixtures, then move the same deterministic path into your application code.

1

Install the package

Add the engine to the project that owns your Markdown workflow.

shell
npm install @jasonbelmonti/markdown-engine
2

Run a bundled profile

Validate a real release checklist fixture and inspect JSON output.

shell
npm exec -- markdown-engine validate \
  --file node_modules/@jasonbelmonti/markdown-engine/fixtures/declarative-validation/examples/release-checklist/pass.md \
  --profile node_modules/@jasonbelmonti/markdown-engine/fixtures/declarative-validation/examples/release-checklist/profile.yaml
3

Use the API in your workflow

Parse, normalize to rich IR, compile the profile, and validate locally.

TypeScript
import {
  normalize,
  parse,
  parseValidationProfile,
  validateWithProfile,
} from "@jasonbelmonti/markdown-engine";

const parsed = parse(markdown, { path: "release.md" });
const normalized = normalize(parsed.parsed);
const profileResult = parseValidationProfile(profileYaml);

if (!profileResult.profile) {
  throw new Error(profileResult.diagnostics[0]?.message ?? "Invalid profile");
}

const result = validateWithProfile(
  normalized.document,
  profileResult.profile,
  { includeEvidence: true },
);

console.log(result.valid, result.diagnostics);

Stable contracts

Built for downstream consumers.

Package 2.0 keeps the serialized rich IR at `documentVersion: "1.0.0"` and makes that shape the default output for `normalize(parsed)`. Legacy consumers can still request the retained `0.0.0` document shape explicitly.