Skip to content

MusicBrainz mirror

Raphael Vael edited this page Aug 11, 2026 · 2 revisions

Local MusicBrainz mirror

PMDA works out of the box against the public MusicBrainz API, but that API is rate-limited to about one request per second. On a large or messy library, identification spends most of its time waiting. A local mirror removes the limit entirely: on the reference production setup, lookups answer in 30-70 ms and the scanner runs at full speed. PMDA uses the mirror for both direct lookups and search, so the search index (Solr) is required — a database-only mirror is not enough.

The easy way: let PMDA build it (recommended)

PMDA has a one-click installer. Go to Settings > Metadata sources > MusicBrainz (local) — or take the mirror step of the first-run wizard on a fresh install — and press Set up a mirror. You give it:

  • this server's LAN address (not localhost) and a port,
  • where the mirror lives (~170 GB, permanent — put it on your fastest disk),
  • where the downloads go (~75 GB, deletable after the install),
  • an optional free MetaBrainz replication token (without it the mirror works but stays frozen at install-day data),
  • your commercial/non-commercial declaration to MetaBrainz.

It then runs unattended for about two hours (download, import, search indexing), keeps going if you close the page, resumes where it stopped if interrupted, and points PMDA at itself automatically when everything (search, lookups, replication) has been verified. Once a mirror is ready, this offer disappears from Settings and is replaced by a "your mirror is live" confirmation — that is expected.

Requirements for the one-click route: the PMDA container must be able to reach Docker on the host (the docker socket mount). If it cannot, the button is disabled with an explanation — use the manual route below instead. Plan 170 GB + 75 GB of disk and 16 GB of RAM either way. If your PMDA version does not show the "Set up a mirror" button yet, update to the current :beta/:latest image.

The manual way: run the official stack yourself

This is the exact topology PMDA's own production setup runs — use it when PMDA has no Docker access, or when you want the mirror on a different machine.

Requirements

Resource What to plan
Storage ~200 GB on fast storage (SSD/NVMe strongly recommended). A loaded mirror is ~60 GB of PostgreSQL plus ~110 GB of Solr index, and it grows slowly.
RAM 8 GB minimum for the mirror stack, 16 GB comfortable (PostgreSQL shared buffers + Solr).
Software Docker with the compose plugin, git.
Time The initial import runs for several hours — overnight is realistic. It is a one-time cost.
Network ~50-75 GB of downloads for the initial data dumps.

Storage placement matters. Put the mirror's data on a real disk path you chose, never inside Docker's own image file (docker.img on Unraid): the mirror will fill it. On Unraid, use a cache (NVMe) path such as /mnt/cache/musicbrainz-mirror.

Step 1 — install the official MusicBrainz stack

git clone https://github.com/metabrainz/musicbrainz-docker.git
cd musicbrainz-docker
admin/configure add live-indexing-search publishing-all-ports

The live-indexing-search option is required by PMDA (search index).

Step 2 — put the data on the storage you chose

Create a compose override so the volumes are real bind mounts instead of anonymous Docker volumes. Save this as local/compose/data-bind-mounts.yml (adapt the roots to your paths):

volumes:
  pgdata:
    driver: local
    driver_opts: {type: none, o: bind, device: /srv/pmda/musicbrainz-mirror/pgdata}
  solrdata:
    driver: local
    driver_opts: {type: none, o: bind, device: /srv/pmda/musicbrainz-mirror/solrdata}
  dbdump:
    driver: local
    driver_opts: {type: none, o: bind, device: /srv/pmda/musicbrainz-mirror/dbdump}
  solrdump:
    driver: local
    driver_opts: {type: none, o: bind, device: /srv/pmda/musicbrainz-mirror/solrdump}
mkdir -p /srv/pmda/musicbrainz-mirror/{pgdata,solrdata,dbdump,solrdump}
admin/configure add local/compose/data-bind-mounts.yml

Step 3 — import the data and start

sudo docker compose build
sudo docker compose run --rm musicbrainz createdb.sh -fetch
sudo docker compose up -d

createdb.sh -fetch downloads the current data dumps and imports them — this is the hours-long part. Then load the search indexes from the pre-built dumps (the fast route):

sudo docker compose run --rm musicbrainz fetch-dump.sh search
sudo docker compose run --rm search load-search-indexes.sh

(Command names can move between musicbrainz-docker releases — if either is not found, follow the "Search indexes" section of the README you cloned; the live sir reindex route works too, just much slower.)

When it finishes, http://YOUR_SERVER_IP:5000 shows a working MusicBrainz web page served from your own copy. Replication (keeping the mirror current) is optional — see replication-cron in the musicbrainz-docker README.

Step 4 — point PMDA at it

  • Existing install: Settings > Metadata sources > MusicBrainz (local) > enable it, set the URL to http://YOUR_SERVER_IP:5000, give it a name.
  • Fresh install: finish the first-run wizard, then do the same in Settings. The mirror can be added at any time — before, during or after your first scan.

PMDA probes the mirror and reports "MusicBrainz mirror reachable" with the measured latency when everything is right, and falls back to the public API automatically whenever the mirror is down — enabling the mirror can never break matching.

Verifying it works

  • The MusicBrainz (local) panel in Settings shows the mirror enabled with your URL (or the one-click panel shows "your mirror is live").
  • The System / runtime page reports the mirror healthy with a latency in the tens of milliseconds.
  • Scans stop pacing at ~1 lookup per second.

Troubleshooting

  • PMDA says the mirror is unreachable: check the URL is reachable from INSIDE the PMDA container (docker exec pmda curl -s http://IP:5000), not just from your desktop. Use the server's LAN IP, not localhost.
  • Search returns nothing while lookups work: the Solr index has not been built (or the live-indexing-search option is missing). Re-run step 3's index loading.
  • The one-click button is greyed out: PMDA cannot reach Docker on the host — the panel says why. Either add the docker socket mount to the PMDA container or use the manual route.
  • Disk filled up: the data landed inside Docker's image file instead of your bind mounts — re-check step 2 (the override must be added BEFORE the first docker compose up).

Clone this wiki locally