npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2026 – Pkg Stats / Ryan Hefner

vitepress-plugin-mermaid-diagram

v0.3.2

Published

VitePress plugin that renders Mermaid-compatible diagrams to SVG at build time — zero-dependency Sugiyama layout engine, no mermaid.js required

Readme

vitepress-plugin-mermaid-diagram

npm version npm downloads CI license

Build-time Mermaid diagram renderer for VitePress. Write standard Mermaid syntax in fenced code blocks and get static SVG output — no mermaid.js runtime, no browser, no headless Chrome.

Live Demo | npm | GitHub

Features

  • Zero runtime dependencies — no mermaid.js (1MB+), no D3, no dagre
  • Build-time rendering — diagrams become static SVG during your build, not in the browser
  • Custom Sugiyama layout engine — from-scratch layered graph layout, replaces dagre entirely
  • Mermaid-compatible syntax — uses the same fenced code blocks your team already knows
  • Semantic theming — decision nodes get amber, terminals get green, data gets purple
  • Dark mode — built-in dark theme with CSS class overrides, works with VitePress theme switching
  • Preview component — optional DiagramPreview with code view, fullscreen, pan & zoom
  • Multiline labels — use \n in node labels for multi-line text via <tspan>
  • TypeScript-first — fully typed API with exported types for everything

Supported diagrams

| Diagram | Syntax | Features | | ------- | ------ | -------- | | Flowchart | graph TD, graph LR | 10 shapes, 4 edge styles, 4 arrow types, subgraphs, all directions | | Sequence | sequenceDiagram | Participants, actors, messages, notes, alt/opt/loop/par/critical/break | | Class | classDiagram | Attributes, methods, visibility, generics, annotations, namespaces, 6 relationship types |

Supported flowchart shapes

| Shape | Syntax | Theme color | | ----- | ------ | ----------- | | Rectangle | [text] | Blue (process) | | Rounded | (text) | Blue (process) | | Diamond | {text} | Amber (decision) | | Circle | ((text)) | Green (terminal) | | Stadium | ([text]) | Green (terminal) | | Hexagon | {{text}} | Blue (process) | | Subroutine | [[text]] | Blue (process) | | Cylinder | [(text)] | Purple (data) | | Parallelogram | [/text/] | Purple (data) | | Double circle | (((text))) | Green (terminal) |

Install

npm install vitepress-plugin-mermaid-diagram

Setup

VitePress config

// .vitepress/config.ts
import { defineConfig } from 'vitepress'
import { diagramPlugin } from 'vitepress-plugin-mermaid-diagram'

export default defineConfig({
  markdown: {
    config(md) {
      md.use(diagramPlugin)
    },
  },
})

Any fenced code block with the language mermaid or diagram is rendered to static SVG at build time. The output is wrapped in a <div class="vp-diagram"> with responsive inline styles.

With preview component (recommended)

Enable preview: true for an interactive diagram viewer with tabs (Preview/Code), fullscreen mode, and pan & zoom:

// .vitepress/config.ts
import { defineConfig } from 'vitepress'
import { diagramPlugin } from 'vitepress-plugin-mermaid-diagram'

export default defineConfig({
  markdown: {
    config(md) {
      md.use(diagramPlugin, { preview: true })
    },
  },
})

Then register the component and import dark mode CSS in your theme:

// .vitepress/theme/index.ts
import DefaultTheme from 'vitepress/theme'
import DiagramPreview from 'vitepress-plugin-mermaid-diagram/DiagramPreview.vue'
import 'vitepress-plugin-mermaid-diagram/diagram-dark.css'

export default {
  extends: DefaultTheme,
  enhanceApp({ app }) {
    app.component('DiagramPreview', DiagramPreview)
  },
}

The DiagramPreview component provides:

  • Preview / Code tabs — switch between rendered diagram and source
  • Fullscreen — open diagram in a full-screen overlay
  • Pan & zoom — scroll to zoom (0.1x–10x), drag to pan, reset button
  • Keyboard — press Esc to close fullscreen

Dark mode

Import the pre-built CSS file for automatic dark mode support:

import 'vitepress-plugin-mermaid-diagram/diagram-dark.css'

Or generate custom dark mode CSS programmatically:

import { darkTheme, generateDarkModeStyles } from 'vitepress-plugin-mermaid-diagram'

const css = generateDarkModeStyles({ ...darkTheme, processFill: '#1e293b' })

With theme and layout options

md.use(diagramPlugin, {
  theme: {
    processFill: '#dbeafe',
    processStroke: '#3b82f6',
    decisionFill: '#fef3c7',
    decisionStroke: '#f59e0b',
    fontSize: 13,
  },
  flowchart: {
    rankdir: 'LR',
    nodesep: 60,
    ranksep: 80,
  },
})

Usage

Flowchart

```mermaid
graph TD
  A[Start] --> B{Decision}
  B -->|Yes| C((Done))
  B -->|No| D[/Load Data/]
  D --> B
```

Edges support solid (-->), dotted (-.->), and thick (==>), with labels (-->|label|) and arrow types (arrow, open, circle, cross). Subgraphs group related nodes:

```mermaid
graph LR
  subgraph Backend
    API[REST API] --> DB[(Database)]
  end
  subgraph Frontend
    UI[Web App] --> API
  end
```

Sequence diagram

```mermaid
sequenceDiagram
  participant C as Client
  participant S as Server
  participant DB as Database
  C->>S: POST /login
  S->>DB: SELECT user
  DB-->>S: user row
  alt valid
    S-->>C: 200 OK
  else invalid
    S-->>C: 401 Unauthorized
  end
  Note over C,S: Connection closed
```

Supports participant (box) and actor (stick figure), solid and dotted messages, notes (Note left of, Note right of, Note over), and combined fragments (alt/else, opt, loop, par, critical, break).

Class diagram

```mermaid
classDiagram
  namespace Models {
    class Animal {
      <<abstract>>
      +String name
      #int age
      +makeSound()* void
    }
    class Dog {
      +fetch() void
    }
  }
  Animal <|-- Dog : extends
  Animal "1" --> "*" Food
```

Supports visibility modifiers (+ public, - private, # protected, ~ internal), generics (class List~T~), annotations (<<interface>>, <<abstract>>, <<enum>>), and all relationship types: inheritance (<|--), composition (*--), aggregation (o--), association (-->), dependency (..>), realization (..|>), with cardinality labels.

Vite plugin for .mmd files

Import .mmd files directly as SVG strings in Vue components:

// .vitepress/config.ts
import { viteDiagramPlugin } from 'vitepress-plugin-mermaid-diagram'

export default defineConfig({
  vite: {
    plugins: [viteDiagramPlugin()],
  },
})
<script setup>
import diagram from './architecture.mmd'
</script>

<template>
  <div v-html="diagram" />
</template>

Theming

All theme properties are optional — pass a partial object to override defaults. Colors are semantic by diagram element.

Flowchart

| Property | Default | Description | | -------- | ------- | ----------- | | processFill | #e8f4fd | Fill for rect, rounded, subroutine, hexagon | | processStroke | #4a90d9 | Stroke for process nodes | | decisionFill | #fff3e0 | Fill for diamond nodes | | decisionStroke | #e6a23c | Stroke for diamond nodes | | terminalFill | #e8f5e9 | Fill for circle, stadium nodes | | terminalStroke | #67c23a | Stroke for terminal nodes | | dataFill | #f3e8fd | Fill for parallelogram, cylinder | | dataStroke | #9b59b6 | Stroke for data nodes | | nodeTextColor | #1a3a5c | Node label text color | | subgraphFill | #f8fafc | Subgraph background | | subgraphStroke | #c0d0e0 | Subgraph border |

Edges

| Property | Default | Description | | -------- | ------- | ----------- | | edgeColor | #6b7b8d | Edge line color | | edgeLabelColor | #4a5568 | Edge label text | | edgeLabelBg | #ffffffdd | Edge label background | | arrowColor | #6b7b8d | Arrowhead fill |

Sequence diagram

| Property | Default | Description | | -------- | ------- | ----------- | | participantFill | #e8f4fd | Participant box fill | | participantStroke | #4a90d9 | Participant box border | | participantTextColor | #1a3a5c | Participant label | | actorColor | #4a90d9 | Actor stick figure | | lifeline | #c0d0e0 | Lifeline dash | | noteFill | #fef9e7 | Note background | | noteStroke | #d4ac0d | Note border | | noteTextColor | #5a4e1a | Note text | | messageLabelColor | #2d3748 | Message label text | | blockStroke | #9b9b9b | Fragment block border | | blockLabelFill | #f0f0f0 | Fragment label background | | blockLabelColor | #4a4a4a | Fragment label text |

Class diagram

| Property | Default | Description | | -------- | ------- | ----------- | | classHeaderFill | #4a90d9 | Class header background | | classHeaderTextColor | #ffffff | Class header text | | classBodyFill | #ffffff | Class body background | | classStroke | #4a90d9 | Class border | | classTextColor | #2d3748 | Member text | | classSectionStroke | #e2e8f0 | Section divider | | annotationColor | #718096 | Stereotype annotation | | namespaceFill | #f7fafc | Namespace background | | namespaceStroke | #a0aec0 | Namespace border | | relationLabelColor | #4a5568 | Relationship label |

Global

| Property | Default | Description | | -------- | ------- | ----------- | | background | transparent | SVG background | | fontSize | 14 | Base font size (px) | | fontFamily | system fonts | Font stack |

Layout configuration

Flowchart

{
  rankdir: 'TD',  // 'TD' | 'LR' | 'BT' | 'RL'
  nodesep: 50,    // horizontal spacing between nodes
  ranksep: 50,    // vertical spacing between ranks
  marginx: 20,    // horizontal margin
  marginy: 20,    // vertical margin
}

Sequence diagram

{
  participantSpacing: 150,  // horizontal spacing between participants
  messageSpacing: 40,       // vertical spacing between messages
  headerHeight: 50,         // height of the header area
  noteWidth: 120,           // default note width
  padding: 20,              // diagram padding
}

API

diagramPlugin(md, options?)

markdown-it plugin. Renders mermaid and diagram fenced code blocks to static SVG.

Options:

  • preview — wrap output in <DiagramPreview> component with tabs and fullscreen (default: false)
  • theme — partial theme overrides
  • darkTheme — dark mode theme overrides, or false to disable (default: built-in dark theme for standalone, disabled for VitePress)
  • flowchart / sequence / classDiagram — layout options

viteDiagramPlugin(options?)

Vite plugin. Transforms .mmd file imports into SVG string exports.

render(source, options?)

Core render function. Parses Mermaid syntax and returns an SVG string, or null if the diagram type is not recognized.

import { render } from 'vitepress-plugin-mermaid-diagram'

const svg = render('graph TD\n  A --> B')

Parsers (advanced)

import {
  parseFlowchart,
  parseSequence,
  parseClassDiagram,
  detectDiagramType,
} from 'vitepress-plugin-mermaid-diagram'

const ast = parseFlowchart('graph TD\n  A --> B')

Layout (advanced)

import {
  layoutFlowchart,
  layoutSequence,
  layoutClassDiagram,
  renderSVG,
  defaultTheme,
} from 'vitepress-plugin-mermaid-diagram'

const layout = layoutFlowchart(ast, { rankdir: 'LR' })
const svg = renderSVG(layout, 'flowchart', defaultTheme)

How it works

  1. VitePress processes your markdown through markdown-it
  2. The plugin intercepts fenced code blocks tagged mermaid or diagram
  3. A custom parser converts the Mermaid syntax into an AST
  4. A Sugiyama layout engine (6-phase pipeline) positions all nodes and edges
  5. An SVG renderer generates a static SVG string
  6. The SVG is inserted into the HTML — no JavaScript is sent to the browser

Sugiyama layout pipeline

| Phase | Algorithm | Purpose | | ----- | --------- | ------- | | 1 | DFS back-edge reversal | Remove cycles to ensure a DAG | | 2 | Kahn's topological sort + longest path | Assign vertical ranks | | 3 | Dummy node insertion | Handle edges spanning multiple ranks | | 4 | Barycenter heuristic | Minimize edge crossings | | 5 | Median alignment + spacing | Assign x/y coordinates | | 6 | Dummy removal + bend points | Clean up edge routing |

Styling

The rendered SVGs are wrapped in <div class="vp-diagram"> with inline responsive styles (centering, max-width: 100%, overflow scroll). No external CSS is required for basic usage.

For dark mode, import the pre-built CSS:

import 'vitepress-plugin-mermaid-diagram/diagram-dark.css'

Or write your own overrides using the CSS classes on SVG elements (vp-d-process, vp-d-decision, vp-d-terminal, vp-d-data, vp-d-node-text, vp-d-edge, etc.).

Contributors

License

MIT