Post

Automate Draw.io Diagram Export with Azure DevOps

Learn how to automate exporting Draw.io diagrams into PNG images using Azure DevOps pipelines. A complete step-by-step guide using deathstar-blueprint.drawio.

Automate Draw.io Diagram Export with Azure DevOps

“Turning your Death Star blueprints into beautiful, versioned documentation”

Keeping visual documentation up-to-date in a fast-moving development workflow can be a real pain—especially when those diagrams live as .drawio files in your repository. They’re often forgotten or manually exported just before a release (or never), leading to stale or missing images in your docs.

But what if you could automate that?

In this post, you’ll learn how to automatically export your .drawio diagrams into PNG images using Azure DevOps Pipelines every time the file changes. Our example will revolve around a diagram file called deathstar-blueprint.drawio, because let’s face it—good DevOps is how the Empire should have built the Death Star.


🧩 The Objective

Whenever deathstar-blueprint.drawio is updated in your Git repository, this pipeline will:

  1. Detect the change
  2. Spin up a headless Linux environment
  3. Install Draw.io and necessary dependencies
  4. Export each diagram page as a PNG image
  5. Commit the images back to the repo

All hands-off. All automated.


🧰 Prerequisites

Make sure your repo:

  • Contains .drawio diagrams inside docs/drawio/
  • Has a configured Azure DevOps Pipeline
  • Has permissions to push changes to branches (PAT or system access)
  • Uses Git version control


🔁 Pipeline Overview

Here’s the full pipeline YAML and a breakdown of how each step works.


🚨 Trigger on Diagram Changes

1
2
3
4
trigger:
  paths:
    include:
      - docs/drawio/**

Only runs when files inside docs/drawio/ are modified.


🧪 Setup: Ubuntu Agent

1
2
pool:
  vmImage: 'ubuntu-latest'

Uses Microsoft’s ubuntu-latest hosted agent.


🧱 Install Dependencies & Prepare Draw.io

1
2
3
4
5
6
7
- script: |
    sudo apt-get update && sudo apt-get install -y xvfb libxml2-utils
    wget https://github.com/jgraph/drawio-desktop/releases/download/v26.2.2/drawio-x86_64-26.2.2.AppImage -O drawio || exit 1
    chmod +x drawio
    ./drawio --appimage-extract || exit 1
    mkdir -p docs/images/
  displayName: 'Prepare Draw.io Environment'
  • Installs Xvfb (virtual display server) and libxml2-utils
  • Downloads and extracts Draw.io Desktop
  • Prepares output folder docs/images/


📄 Count Pages in the Diagram

1
2
3
4
- script: |
    page_count=$(xmllint --xpath "count(//diagram)" docs/drawio/deathstar-blueprint.drawio)
    echo $page_count > page_count.txt
  displayName: 'Count Pages in Draw.io File'

Parses XML to count <diagram> nodes (pages).


🖼️ Export Each Page to PNG

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
- script: |
    Xvfb :99 -screen 0 1024x768x24 & 
    export DISPLAY=:99
    sleep 3

    if ! pgrep Xvfb > /dev/null; then
      echo "Xvfb failed to start"
      exit 1
    fi

    echo "Available disk space:"
    df -h
    echo "Available memory:"
    free -h

    page_count=$(cat page_count.txt)
    echo "Total pages to export: $page_count"
    for i in $(seq 0 $((page_count - 1))); do
      echo "Exporting page $i..."
      ./squashfs-root/drawio -x -f png --page-index $i -o docs/images/deathstar-blueprint-page-$i.png docs/drawio/deathstar-blueprint.drawio
      if [ $? -ne 0 ]; then
        echo "Exporting page $i failed"
        pkill Xvfb || echo "Failed to stop Xvfb"
        exit 1
      fi
    done

    pkill Xvfb || echo "Failed to stop Xvfb"
  displayName: 'Export Draw.io Pages to PNG'

Exports each page from the .drawio file as PNG images into docs/images/.


🧹 Cleanup and Push Changes

1
2
3
4
5
6
7
8
9
10
- script: |
    rm -rf squashfs-root drawio page_count.txt || echo "Cleanup failed"
    git config --global user.email "$(email)"
    git config --global user.name "$(username)"
    git fetch --all
    git add -A || echo "No files to add"
    git commit -m "Generated images from Draw.io [skip ci]" || echo "No changes to commit"
    branchName=$(echo "$BUILD_SOURCEBRANCH" | sed 's/refs\/heads\///')
    git push origin "HEAD:$branchName" || echo "Failed to push changes"
  displayName: 'Cleanup and Push Changes'
  • Cleans up temporary files
  • Commits image exports back to the same branch
  • Skips triggering another pipeline run ([skip ci])


🧠 Why Automate This?

✅ Keeps diagrams in sync with code
✅ Encourages updating diagrams regularly
✅ Eliminates manual export steps
✅ Version-controls visuals alongside source


🔄 Bonus Ideas

  • Export SVG or PDF formats using the Draw.io CLI
  • Publish images to a static site (e.g., GitHub Pages)
  • Auto-generate README previews or Confluence pages


🧨 Final Thoughts

By integrating Draw.io exports into your CI pipeline, your diagrams become as maintainable and versioned as your code. No more manual exports. No more outdated visuals.

And just like that—your deathstar-blueprint.drawio evolves into a living artifact of your software system.


Need help extending this setup? Reach out, comment, or fork this into your own DevOps Death Star ✨

This post is licensed under CC BY 4.0 by the author.