Skip to content

petalo/legal-markdown-js

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

244 Commits
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Legal Markdown JS

TypeScript/Node.js implementation of LegalMarkdown

Try it live in the hosted playground.

What It Does

Legal Markdown JS processes legal markdown documents and can generate:

  • Processed markdown
  • HTML
  • PDF
  • DOCX

Core syntax supported:

  • Variables/helpers ({{field}}, helpers, loops)
  • Legal headers (l., ll., lll., ...)
  • Optional clauses ([text]{condition})
  • Cross references between sections (|reference|)
  • Imports (@import path/to/file.md)

Check the features overview document for more details.

Legal Markdown JS Playground

Install

npm

Run without installing globally:

npx legal-md contract.md output.md

Install the package locally in a project:

npm install legal-markdown-js

Available binaries:

  • legal-md
  • legal-md-ui
  • legal-md-playground

Homebrew

Install the standalone macOS binary:

brew tap petalo/legal-markdown
brew install legal-md

After installing with Homebrew, you can use:

  • legal-md
  • legal-md ui
  • legal-md playground

Install script

curl -fsSL https://github.com/petalo/legal-markdown-js/releases/latest/download/install.sh | sh

Quick Start

Install, then run your first conversion in seconds:

1. Install

# npm
npm install legal-markdown-js

# Homebrew (macOS)
brew tap petalo/legal-markdown && brew install legal-md

2. Process a document

Convert a Legal Markdown file to processed Markdown:

legal-md contract.md output.md

Generate HTML, PDF, or DOCX:

legal-md contract.md --html
legal-md contract.md --pdf
legal-md contract.md --docx
Input (contract.md) Output markdown Output HTML
---
client: ACME Corp
amount: 5000
include_warranty: true
---

l. Parties

Agreement with {{client}}.

l. Services

ll. Payment

Total due: ${{amount}}.

[ll. Warranty

Full warranty included.]{include_warranty}


# 1. Parties
Agreement with **ACME Corp**.
# 2. Services
## 2.1. Payment Total due: $5000.
## 2.2. Warranty Full warranty included. 
<h1>1. Parties</h1>
<p>Agreement with
  <strong>ACME Corp</strong>.
</p>
<h1>2. Services</h1>
<h2>2.1. Payment</h2>
<p>Total due: $5000.</p>
<h2>2.2. Warranty</h2>
<p>Full warranty included.</p>

Playground And UI

Hosted playground

Use the browser-based playground for a quick interactive test: petalo.github.io/legal-markdown-js

Interactive CLI

Launch the terminal UI:

legal-md-ui
# or
legal-md ui

Local playground

If you installed from npm or Homebrew:

legal-md-playground
# or
legal-md playground

If you are working from this repository:

npm run build:web
npm run web:serve

Useful variants:

# Vite dev server for playground development
npm run dev:web

# Serve an existing build on a custom port
npm run web:serve -- --port=3000

CLI Usage

Basic processing

# Input -> output markdown
legal-md input.md output.md

# Input -> stdout markdown
legal-md input.md --stdout

# Read from stdin
cat input.md | legal-md --stdin --stdout

Output formats

# HTML
legal-md input.md output.html --html

# PDF
legal-md input.md output.pdf --pdf

# DOCX
legal-md input.md output.docx --docx

# Highlighted review variants
legal-md input.md output.pdf --pdf --highlight
legal-md input.md output.docx --docx --highlight

PDF connector selection

# Auto (default)
legal-md input.md output.pdf --pdf

# Force specific backend
legal-md input.md output.pdf --pdf --pdf-connector puppeteer
legal-md input.md output.pdf --pdf --pdf-connector system-chrome
legal-md input.md output.pdf --pdf --pdf-connector weasyprint

auto resolution order is:

  1. puppeteer
  2. system-chrome
  3. weasyprint

Metadata export

legal-md contract.md --export-yaml -o metadata.yaml
legal-md contract.md --export-json -o metadata.json

Useful flags

legal-md contract.md --title "Master Services Agreement" --html
legal-md contract.md output.html --html --css ./styles/print.css
legal-md contract.md --enable-field-tracking --stdout

Programmatic API

import {
  processLegalMarkdown,
  generateHtml,
  generatePdf,
  generatePdfVersions,
  generateDocx,
  generateDocxVersions,
} from 'legal-markdown-js';

const source = `---\ntitle: Service Agreement\nclient: ACME\n---\n\nl. Parties\n\nAgreement with {{client}}.`;

const processed = await processLegalMarkdown(source, {
  enableFieldTracking: true,
});

const html = await generateHtml(source, {
  title: 'Service Agreement',
  includeHighlighting: true,
});

const pdf = await generatePdf(source, './output/agreement.pdf', {
  format: 'A4',
  includeHighlighting: false,
  pdfConnector: 'auto', // auto | puppeteer | system-chrome | weasyprint
});

const { normal, highlighted } = await generatePdfVersions(
  source,
  './output/agreement.pdf',
  {
    format: 'Letter',
    pdfConnector: 'weasyprint',
  }
);

const docx = await generateDocx(source, './output/agreement.docx', {
  title: 'Service Agreement',
});

const docxPair = await generateDocxVersions(source, './output/agreement.docx');

console.log(
  processed.content,
  html.length,
  pdf.length,
  normal.length,
  highlighted.length
);
console.log(docx.length, docxPair.normal.length, docxPair.highlighted.length);

PDF Backends

Supported backends:

  • puppeteer
  • system-chrome
  • weasyprint

Installation examples:

# Puppeteer browser install (if needed)
npx puppeteer browsers install chrome

# macOS
brew install weasyprint

# Ubuntu/Debian
sudo apt-get install -y weasyprint

Configuration

Configuration loading supports:

  • package.json (legalmd key)
  • .legalmdrc
  • .legalmdrc.yaml
  • .legalmdrc.json
  • legalmd.config.js
  • legalmd.config.ts

Useful env overrides:

  • LEGAL_MD_PDF_CONNECTOR
  • LEGAL_MD_VALIDATION_MODE
  • LOG_LEVEL
  • DEBUG
  • IMAGES_DIR
  • STYLES_DIR
  • DEFAULT_INPUT_DIR
  • DEFAULT_OUTPUT_DIR
  • ARCHIVE_DIR

Example:

LEGAL_MD_PDF_CONNECTOR=weasyprint legal-md input.md --pdf

Testing

# Full local suite
npm test

# CI-like run (includes PDF backend precheck)
npm run test:ci

# Backend availability check only
npm run test:pdf:backends

# Targeted suites
npm run test:unit
npm run test:integration
npm run test:e2e
npm run test:e2e:cli

test:e2e and test:ci require both PDF paths to be available:

  • Puppeteer launchable Chrome/Chromium
  • WeasyPrint executable

Documentation

Contributing

See docs/development/contributing.md.

License

MIT. See LICENSE.

Acknowledgments

Based on the original LegalMarkdown project by Casey Kuhlman.

About

Process markdown with YAML front matter, conditional clauses, cross-references, imports, and generate professional PDFs ready to be shared.

Topics

Resources

License

Stars

Watchers

Forks

Packages

 
 
 

Contributors