Skip to content

Servarr Stack

Stack complet et isolé pour la gestion automatisée des médias, entièrement routé via VPN.

Architecture

flowchart TB
    subgraph Internet
        PROTON[ProtonVPN LU<br/>WireGuard]
    end

    subgraph Gluetun[gluetun - VPN Container]
        TRANS[Transmission<br/>localhost:9091]
        PROWLARR[Prowlarr<br/>localhost:9696]
        RADARR[Radarr<br/>localhost:7878]
        SONARR[Sonarr<br/>localhost:8989]
    end

    subgraph Caddy[Reverse Proxy]
        CADDY[Caddy + Authelia SSO]
    end

    subgraph Storage[/mnt/mediaserver/servarr]
        TORRENTS[torrents/]
        MEDIA[media/]
    end

    PROTON <--> Gluetun
    CADDY -->|gluetun:*| Gluetun
    TRANS --> TORRENTS
    PROWLARR --> TRANS
    RADARR --> TRANS
    SONARR --> TRANS
    RADARR --> MEDIA
    SONARR --> MEDIA

Kill Switch Intégré

Tous les services partagent le namespace réseau de gluetun via network_mode: service:gluetun. Si le VPN tombe, aucun service n'a accès à Internet.

Services

Service Port interne Fonction URL
Gluetun 8000 (control) VPN container (ProtonVPN LU) -
Transmission 9091 Client BitTorrent transmission.talloires.tailfd281f.ts.net
Prowlarr 9696 Gestionnaire d'indexeurs prowlarr.talloires.tailfd281f.ts.net
Radarr 7878 Gestion des films radarr.talloires.tailfd281f.ts.net
Sonarr 8989 Gestion des séries sonarr.talloires.tailfd281f.ts.net

Accès LAN également disponible

  • prowlarr.talloires.local
  • sonarr.talloires.local
  • radarr.talloires.local
  • transmission.talloires.localbloqué (Tailscale uniquement)

Structure des données

/mnt/mediaserver/servarr/
├── torrents/
│   ├── incomplete/     # Downloads en cours
│   └── complete/       # Downloads terminés
└── media/
    ├── movies/         # Films (Radarr → Jellyfin)
    └── tv/             # Séries (Sonarr → Jellyfin)

Hardlinks

Tous les services voient /data/ qui pointe vers /mnt/mediaserver/servarr/. Cela permet les hardlinks — pas de copie, déplacement instantané.

Configuration réseau

network_mode: service:gluetun

Tous les services utilisent network_mode: "service:gluetun", ce qui signifie :

  • Ils partagent le même namespace réseau que gluetun
  • Ils communiquent entre eux via localhost
  • Les ports sont exposés uniquement par gluetun
  • Pas d'accès direct au réseau Docker
# Exemple de configuration
services:
  gluetun:
    ports:
      - "9091:9091"   # Transmission
      - "9696:9696"   # Prowlarr
      - "7878:7878"   # Radarr
      - "8989:8989"   # Sonarr
    environment:
      - FIREWALL_OUTBOUND_SUBNETS=192.168.0.0/16,100.64.0.0/10

  prowlarr:
    network_mode: "service:gluetun"
    depends_on:
      gluetun:
        condition: service_healthy

Configuration interne des apps

App Setting Valeur
Prowlarr Download Client → Transmission localhost:9091
Prowlarr Apps → Sonarr localhost:8989
Prowlarr Apps → Radarr localhost:7878
Sonarr Download Client → Transmission localhost:9091
Radarr Download Client → Transmission localhost:9091

Important

Ne pas utiliser les noms de containers (prowlarr, sonarr, etc.) car ils ne sont pas résolvables dans ce mode réseau.

VPN Configuration

ProtonVPN WireGuard

# Vérifier l'IP VPN
docker exec gluetun wget -qO- https://ipinfo.io/ip
# Doit retourner une IP ProtonVPN Luxembourg (5.253.204.x)
Paramètre Valeur
Provider ProtonVPN
Type WireGuard
Serveur Luxembourg (LU#9)
Peer Port 51413 (Transmission)

Firewall

environment:
  # Autorise accès depuis LAN et Tailscale
  - FIREWALL_OUTBOUND_SUBNETS=192.168.0.0/16,100.64.0.0/10
  # Port forwarding pour seeding
  - FIREWALL_VPN_INPUT_PORTS=51413

Caddy / Reverse Proxy

Les services sont exposés via Caddy avec Authelia SSO :

prowlarr.talloires.local, prowlarr.talloires.tailfd281f.ts.net {
    @api path /api/*
    handle @api {
        reverse_proxy gluetun:9696
    }
    handle {
        import authelia
        reverse_proxy gluetun:9696
    }
    import internal_tls
}

API sans auth

Les endpoints /api/* sont accessibles sans Authelia pour permettre la communication inter-apps.

Vérifications

VPN actif

docker exec gluetun wget -qO- https://ipinfo.io

Doit afficher une IP ProtonVPN (M247/Datacamp), pas ton IP réelle.

Connectivité interne

# Depuis gluetun, tester tous les services
docker exec gluetun sh -c 'wget -qO- http://localhost:9696/ping'  # Prowlarr
docker exec gluetun sh -c 'wget -qO- http://localhost:8989/ping'  # Sonarr
docker exec gluetun sh -c 'wget -qO- http://localhost:7878/ping'  # Radarr

Statut des containers

cd ~/lake/servarr && docker compose ps

Health check gluetun

docker inspect gluetun --format='{{.State.Health.Status}}'
# Doit retourner: healthy

Fichiers

Fichier Chemin
Docker Compose ~/lake/servarr/docker-compose.yml
Environment ~/lake/servarr/.env
Backup ~/lake/servarr/docker-compose.yml.bak
Données /mnt/mediaserver/servarr/

Historique

  • 2026-01-12 : Migration complète — tous les services via VPN (network_mode: service:gluetun)
  • 2026-01-08 : Déploiement initial avec Gluetun, Transmission, Prowlarr, Radarr, Sonarr