Wizarr is a free, open-source invitation system for your media server. Instead of creating accounts by hand and talking friends and family through which app to install, you send them one link. Wizarr creates their Jellyfin account (Plex, Emby, Audiobookshelf, Komga, Kavita and Romm work too) and walks them through getting set up, step by step.
In this guide we will run Wizarr in Docker using the official image, connect it to Jellyfin, send a first invite, and get it ready to sit behind a reverse proxy so the links work from anywhere.
ghcr.io/wizarrrr/wizarr.✅ Before you start
- A Linux host with Docker and Docker Compose v2 installed (
docker compose versionshould work). - A working Jellyfin server and an admin account on it, so you can create an API key.
- One free port,
5690, for the web UI. - A domain name and a reverse proxy (Traefik, Nginx Proxy Manager...), because the people you invite need to open the link from outside your network.
STEP 1: Find your user and group IDs
Wizarr should run as a normal user, not as root. Log in to your Docker host over SSH and run:
idYou will see something like uid=1000(you) gid=1000(you). Make a note of the two numbers; they become PUID and PGID below.
STEP 2: Create the folders
I like to keep every app's data under one parent folder so backups are a single job. Wizarr only needs one folder:
mkdir -p /path/to/appdata/wizarr/dataWizarr keeps its database in a database subfolder inside it, which it creates on first start.
Finally, this guide puts the app on the shared media Docker network used by the rest of my media stack, so other containers can reach it by name. If you followed the Jellyfin guide you already have it; otherwise create it once:
docker network create mediaSTEP 3: The compose file
Create /path/to/appdata/wizarr/docker-compose.yml and paste in the following. Use the copy button in the top right corner of the block.
services:
wizarr:
image: ghcr.io/wizarrrr/wizarr:latest
container_name: wizarr
hostname: wizarr
restart: unless-stopped
environment:
- PUID=1000 # your user ID from STEP 1
- PGID=1000 # your group ID from STEP 1
- TZ=Europe/London # your time zone
- DISABLE_BUILTIN_AUTH=false # true ONLY if Authelia/Authentik protects it
volumes:
- /path/to/appdata/wizarr/data:/data
ports:
- 5690:5690 # web UI and invite pages
networks:
- media
networks:
media:
external: truedocker-compose.yml
STEP 4: The settings explained
| Setting | What it does |
|---|---|
image |
The official Wizarr image. latest follows stable releases. |
PUID / PGID |
The user and group Wizarr runs as. Its database files will belong to this user. |
TZ |
Time zone, so invite expiry times are right. List of zones. |
DISABLE_BUILTIN_AUTH |
Leave this false. Only set it to true if another login (Authelia, Authentik and so on) already protects the admin pages, otherwise anyone could manage your invites. |
/data |
Wizarr's database and settings, in /data/database. This is the folder to back up. |
5690:5690 |
The admin UI and the invite pages your guests see. |
networks |
Joins the shared media network so Wizarr can reach Jellyfin at http://jellyfin:8096. |
STEP 5: Start Wizarr
From the folder containing your compose file:
cd /path/to/appdata/wizarr
docker compose up -d
docker compose logs -fWait until the logs settle down (press Ctrl+C to stop following them; the container keeps running), then check it is up:
docker ps --filter name=wizarrAfter a minute the status should read Up ... (healthy); the image has its own health check.
STEP 6: First-run setup
First, create an API key in Jellyfin: Dashboard → API Keys → +, name it Wizarr and copy the key. Then open http://192.168.1.20:5690 in your browser (use your Docker host's IP):
- Create your admin account. Choose a username and a strong password such as
CHANGE_ME_STRONG_PASSWORD(please do change it). - Add your media server. Pick Jellyfin, enter the server URL (
http://jellyfin:8096on the shared network, orhttp://192.168.1.20:8096) and paste the API key. Wizarr checks the connection and lists your libraries. - Create an invite. On the Invitations page, create a new invite and choose which libraries the guest gets, how long the link is valid and, if you like, an expiry for the account itself.
- Send the link. Copy the invite link and send it. Your guest opens it, picks a username and password, and Wizarr creates their Jellyfin account and shows them which app to install.
The steps your guests see after signing up can be edited, so you can add your own house rules, a link to Jellyseerr for requests, or a Discord invite.
STEP 7: Put Wizarr behind a reverse proxy
Wizarr is the one app in this stack that is meant to be reached from outside, because that is where your guests are. Put it behind a reverse proxy with HTTPS on its own hostname, such as join.example.com, and keep the built-in login on. Do not forward port 5690 directly.
Option A: Traefik (Docker labels)
If Traefik runs on the same Docker host and is attached to the media network, add these labels to the wizarr service. They assume your HTTPS entry point is called websecure and your certificate resolver is called cloudflare; change them to match your Traefik config.
labels:
- traefik.enable=true
- traefik.http.routers.wizarr.rule=Host(`join.example.com`)
- traefik.http.routers.wizarr.entrypoints=websecure
- traefik.http.routers.wizarr.tls.certresolver=cloudflare
- traefik.http.services.wizarr.loadbalancer.server.port=5690docker-compose.yml (extra lines)
Option B: Traefik (file provider)
If Traefik runs on a different machine, add a router and service to your dynamic config file instead:
http:
routers:
wizarr:
rule: Host(`join.example.com`)
entryPoints:
- websecure
tls:
certResolver: cloudflare
service: wizarr
services:
wizarr:
loadBalancer:
servers:
- url: http://192.168.1.20:5690dynamic.yml
Option C: Nginx Proxy Manager
Add a Proxy Host for join.example.com with scheme http, forward hostname wizarr (if NPM is on the media network) or 192.168.1.20, and forward port 5690. Request a certificate on the SSL tab and tick Force SSL. The Wizarr docs suggest leaving Block Common Exploits off for this host.
Once the proxy works, copy invite links from Wizarr while you are browsing it on the public hostname, so the links you send out use https://join.example.com rather than your LAN IP.
Updating Wizarr
The latest tag always follows the newest stable release. To update:
cd /path/to/appdata/wizarr
docker compose pull
docker compose up -d
docker image prune -f/path/to/appdata/wizarr/data and read the release notes.Troubleshooting
Wizarr cannot connect to Jellyfin. Check the URL from Wizarr's point of view: use the container name on the shared network or the host IP, never localhost. Make sure you pasted an API key, not your Jellyfin password.
Invite links show your LAN address. You copied them while browsing Wizarr on its IP. Open Wizarr on the public hostname and copy the link again.
Permission errors in the logs on start. The PUID/PGID user cannot write to /path/to/appdata/wizarr/data. Fix it with sudo chown -R 1000:1000 /path/to/appdata/wizarr/data, using your IDs.
The container shows unhealthy. Run docker logs wizarr --tail 50. Database migrations on first start or after an upgrade can take a minute, so give it time.
port is already allocated when starting. Something else is using 5690. Change the left-hand side of the port mapping, for example 5691:5690.
That's it! No more setting up accounts by hand: just send a link and let Wizarr do the explaining. 🧙