# GitHub Images

Embed Ondine diagrams in READMEs and other Markdown that cannot run scripts or load styles.

## Overview

GitHub draws ` ```mermaid ` fences with its own renderer. To show an Ondine diagram, a README links an image from the image Worker. On each request, the Worker compiles the diagram that the URL encodes.

```mermaid
sequenceDiagram
  participant README
  participant Worker as Image Worker
  README->>Worker: GET /<payload>.svg
  Worker-->>README: image/svg+xml
```

## Walkthrough

The steps below encode a diagram, then embed it with light and dark variants.

### Encode the Source

The payload is the source as UTF-8, compressed with zlib deflate, then encoded as base64url. Kroki uses the same encoding.

```ts title="encode.ts"
import * as Zlib from 'node:zlib'

// Produces the path segment for one diagram
const payload = Zlib.deflateSync('flowchart LR\n  A --> B').toString('base64url')
```

Markdown written by hand or by an agent can omit the compression. The `/svg` path reads percent-encoded source from its `source` query parameter.

```md title="README.md"
<!-- Encodes the same diagram with encodeURIComponent -->

![Request flow](https://ondine.sh/svg?source=flowchart%20LR%0A%20%20A%20--%3E%20B)
```

### Embed the Image

If the URL has no `scheme` parameter, the image uses the light scheme. Add `?scheme=auto` to follow the color scheme of the viewer through `prefers-color-scheme`.

```md title="README.md"
<!-- Follows the reader's color scheme -->

![Request flow](https://ondine.sh/eJxLy8kvT85ILCpR8AniUlBwVNDVtVNwAgBUvQYu.svg?scheme=auto)
```

### Pin Each Scheme

GitHub draws images in a page, and the scheme of that page can be different from the system scheme. A `<picture>` with pinned variants follows the scheme that GitHub selects.

```html title="README.md"
<!-- Chooses the variant that matches GitHub's theme -->
<picture>
  <source
    media="(prefers-color-scheme: dark)"
    srcset="https://ondine.sh/<payload>.svg?scheme=dark"
  />
  <img alt="Request flow" src="https://ondine.sh/<payload>.svg?scheme=light" />
</picture>
```

## Recipes

### Rewrite a README

The [CLI](/docs/guides/cli#render-markdown) rewrites each ` ```mermaid ` fence in a Markdown file to the `<picture>` above. The source stays in the block, so later runs render it again.

```sh
# Rewrites the fences in README.md, then fails CI when the file is out of date
npx ondine README.md
npx ondine README.md --check
```

The `--worker` option links a different deployment. The `--svg` option writes SVG files and links them instead of the Worker.

### Read Errors

For invalid source, the Worker returns status 400 with an SVG card that shows the error. Thus, the README shows the error in place of the broken diagram.

### Stay Under Limits

The Worker rejects paths longer than 4,096 characters and sources larger than 64 KiB after inflation. The GitHub image proxy rejects URLs longer than about 8 kB. If a diagram is too long, split it into smaller diagrams.

### Deploy a Worker

The image Worker is part of the documentation site in `site/`. It serves requests at `https://ondine.sh`.

```sh
# Builds the site with the image route and deploys it with Wrangler
pnpm --dir site run deploy
```

## More

- [Image Worker](/docs/api/worker): Request format, responses, headers, and limits.

- [Theming](/docs/guides/theming): See the properties each scheme sets.

- [CLI](/docs/guides/cli): Commit rendered SVG files instead.
