Docs & Code Guide

Embed a diagram in GitLab: one image URL that works in README, wiki, issues, and MRs

GitLab renders markdown in more places than most platforms: the README, wiki pages, issues, merge request descriptions, and comments all go through the same pipeline. That pipeline strips iframes, so the interactive form of a diagram is out, and it renders images by URL, so the live form is in. Here is how that behaves on GitLab.com, what changes on self-managed, and where the built-in diagram tools stop.

7 min readFor teams whose architecture story lives in GitLab repos and wikis

See it as a diagram

Everything below, as a diagram you can edit. Describe yours and see it in seconds.

176/20003 credits left
Try:

No account needed · Editable canvas, not a picture

Where an image by URL renders in GitLab

GitLab Flavored Markdown sanitizes HTML the same way in every surface it touches. Iframes, scripts, and styles are removed from READMEs, wiki pages, issues, and merge requests alike, so there is no surface where an interactive embed page renders inline. Images are allowed everywhere, which makes one markdown line the whole integration.

That uniformity is worth using. The same URL that keeps the README current also drops into an incident issue, an MR description explaining a refactor, and the wiki page for the platform overview. Edit the diagram once and every one of those surfaces follows, because none of them stored a copy at paste time.

![Platform architecture](https://datadef.io/api/embed/my-platform-a1b2c3d4)

<!-- The same line works in README.md, wiki pages, issues, and MR descriptions.
     Optional sizing: -->
![Platform architecture](https://datadef.io/api/embed/my-platform-a1b2c3d4?width=2000&height=1200)

GitLab.com's asset proxy and what it does to update latency

On GitLab.com, external images in rendered markdown are not loaded from your origin directly. GitLab rewrites them to its asset proxy at user-content.gitlab-static.net, a Camo-style service that fetches on behalf of the reader so external servers never see reader IP addresses.

The proxy decides freshness from the origin cache headers. Datadef serves embeds with Cache-Control max-age=300 and an ETag derived from the last edit, so the proxied copy re-validates every five minutes and an edited diagram shows up across GitLab within minutes. The honest phrasing is minutes, not instantly: the first render after an edit also takes a few seconds while a headless browser produces it.

Self-managed GitLab ships with no asset proxy enabled. Admins can configure one through the application settings API, with go-camo as the recommended server. On an instance without a proxy, reader browsers fetch the origin directly and the same five minute window applies, minus the proxy hop.

Native Mermaid, PlantUML, and Kroki

GitLab renders Mermaid natively in fenced code blocks with the mermaid language tag, no server setup required. PlantUML and Kroki go further, rendering their fences through a diagram server, but that server is an instance-level integration an administrator has to configure; on an instance where nobody set it up, the fences show as code.

All three shine for small diagrams that should live in the same commit or wiki page as the prose. The ceiling is generated layout: past roughly 20 nodes, or when the diagram needs zones and column-level lineage, autolayout output stops communicating. That is the point where a deliberately laid out diagram behind a live URL is the stronger choice, with the text-based tools kept for the small flows they are good at.

The wiki is a git repository

Every GitLab wiki is backed by its own git repo, cloneable at the project path with .wiki.git appended. Pages are markdown files, so the image line above works whether the page was edited in the web UI or committed from a clone. Teams that treat the wiki as docs-as-code can review wiki changes like any other, and the diagram URL rides along untouched.

The wiki is where architecture pages rot fastest, because nothing forces them through review when the system changes. A live image removes one reason for rot, the stale screenshot, and the rest of the problem is covered in keep your internal wiki in sync.

Keeping the diagram itself current

The embed keeps GitLab faithful to the diagram; it does not keep the diagram faithful to the system. For that, Datadef ships an MCP server (registry name io.datadef/mcp) that lets a connected agent create and update diagrams from what it reads in the repository. Run it after a merge, from a scheduled pipeline, or ask the agent directly during a review. The pipeline variant is written up in a living diagram from GitLab CI.

Two boundaries, stated plainly. Datadef does not watch your repository, so nothing regenerates without an agent call or CI command. And the embed URL requires the project to be shared public; flip it private and the image 404s everywhere it was pasted. The agent needs an API key, created in settings on a paid plan.

FAQ

How do I embed a diagram in a GitLab README or wiki?

Use standard markdown image syntax with a URL that serves the current diagram, for example ![Architecture](https://datadef.io/api/embed/your-slug). The same line works in READMEs, wiki pages, issues, and merge request descriptions. GitLab strips iframes from all rendered markdown, so an image by URL is the only live embed form.

Does GitLab proxy external images in markdown?

On GitLab.com, yes: external images are rewritten to the asset proxy at user-content.gitlab-static.net, which fetches from the origin so reader IP addresses are not exposed. The proxy honors origin cache headers. Self-managed instances have no proxy by default; administrators can enable one through the application settings API.

How fast does an embedded diagram update in GitLab after an edit?

Within minutes. Datadef serves the image with a five minute cache lifetime, and both the GitLab.com asset proxy and reader browsers re-validate on that schedule. The first render after an edit takes a few extra seconds while it is produced, then it is cached.

Should I use GitLab Mermaid or PlantUML instead of an embedded image?

For small flows, yes: Mermaid renders natively in fenced blocks with no setup, and PlantUML or Kroki render if an administrator has configured the integration. Past roughly 20 nodes, or when you need zones and column-level detail, generated layout stops being readable and a deliberately laid out diagram behind a live image URL communicates better.

Can I embed a diagram from a private project in GitLab?

Not as a live embed. The image URL exists only while the source project is shared public; making it private turns the URL into a 404. The GitLab project itself can be private, since the image URL needs no credentials, but the diagram content must be publishable.