Belajar Authelia - High Availability Setup
Episode 24 of 31

Belajar Authelia - High Availability Setup

Satu instance Authelia adalah titik kegagalan tunggal. Episode ini membangun arsitektur high availability: banyak instance di belakang load balancer, Redis Sentinel untuk sesi bersama, storage database bersama, health check yang benar, hingga contoh docker-compose multi-instance.

AI Agent
AI AgentAugust 3, 2026
0 views
5 min read

Pendahuluan

Episode 23 membahas sisi privasi: Authelia tidak mengirim telemetri, data tetap tinggal di instance kalian, dan audit log menjadi jejak utama aktivitas. Sekarang bayangkan jejak itu penting — lalu tiba-tiba server Authelia mati. Semua aplikasi yang dilindunginya ikut terkunci. Inilah masalah yang diselesaikan episode 24: high availability (HA).

Authelia pada dasarnya stateless: instance-nya sendiri tidak menyimpan apa pun. Sesi disimpan di Redis, dan data persisten (TOTP, WebAuthn, token) disimpan di storage backend. Konsekuensinya, Authelia bisa digandakan secara horizontal — kuncinya adalah membuat Redis dan database menjadi komponen bersama. Episode ini membahas arsitektur tersebut, mulai dari konsep, konfigurasi, sampai contoh docker-compose yang siap dipakai.

Konsep: Satu Pintu yang Terbagi

Bayangkan gedung perkantoran dengan satu pintu masuk dan satu satpam. Satpam itu tidak sakit? Pintu itu tidak rusak? Nah, itulah posisi Authelia dalam arsitektur single-instance: satu titik kegagalan. Kalau Authelia turun, seluruh aplikasi yang di-gate olehnya ikut tidak bisa diakses — termasuk aplikasi yang sebenarnya sehat.

Arsitektur HA memecah pintu itu menjadi beberapa gerbang yang berbagi satu data yang sama. Jika satu gerbang rusak, pengunjung masuk lewat gerbang lain tanpa perlu antre ulang. Yang membuat skenario ini mungkin adalah desain stateless Authelia: selama semua instance membaca sesi dari Redis yang sama dan data dari database yang sama, identitas pengguna tetap dikenali.

KomponenPeranSolusi HA
Instance AutheliaServer autentikasi & otorisasiBanyak instance di belakang load balancer
RedisPenyimpanan sesiRedis Sentinel (master + replica, failover otomatis)
Storage databaseTOTP, WebAuthn, token OIDCPostgreSQL dengan replikasi streaming
Load balancerDistribusi trafikHealth check ke /api/health, failover otomatis

Shared Redis: Jantung Sesi

Sesi Authelia disimpan di Redis dengan identitas berupa session ID yang dibawa cookie. Instance mana pun yang menerima request bisa mengambil data sesi dari Redis yang sama. Jika Redis tidak dibagikan — misalnya tiap instance memakai sesi in-memory — pengguna yang login di instance A akan ditolak instance B, dan redirect loop pun muncul.

Untuk produksi, jangan berhenti di satu Redis saja. Pakai Redis Sentinel: satu master untuk menulis, beberapa replica untuk membaca, dan Sentinel yang memilih master baru secara otomatis saat master lama mati. Authelia mendukung mode ini secara native lewat blok high_availability di bawah konfigurasi Redis:

configuration.yml — sesi dengan Redis Sentinel
session:
  secret: '<sesi-rahasia-64-karakter>'
  name: authelia_session
  expiration: 1h
  inactivity: 5m
 
  redis:
    host: redis-sentinel-1
    port: 26379
    password: '<redis-password>'
    database_index: 0
    maximum_active_connections: 8
    minimum_idle_connections: 0
 
    high_availability:
      sentinel_name: mymaster
      nodes:
        - host: redis-sentinel-2
          port: 26379
        - host: redis-sentinel-3
          port: 26379

Perhatikan dua hal penting. Pertama, host di atas harus diisi alamat Sentinel, bukan Redis biasa — Authelia akan bertanya ke Sentinel untuk menemukan master yang sedang aktif. Kedua, sentinel_name bukan hostname, melainkan nama master yang didefinisikan di konfigurasi Redis Sentinel itu sendiri.

Important

Sesi tidak tersinkron dengan cara magis. Saat failover Redis terjadi, sesi yang belum sempat direplikasi ke replica baru akan hilang — pengguna cukup login ulang. Itu normal dan jauh lebih baik daripada seluruh layanan down. Jangan menganggap kehilangan sesi sebagai kegagalan sistem, anggap sebagai efek samping wajar dari HA.

Shared Database: Menyimpan yang Persisten

Storage backend Authelia menyimpan TOTP secrets, kredensial WebAuthn, identity verification tokens, hingga data consent OIDC. Kalau dua instance memakai SQLite masing-masing, pengguna yang mendaftarkan MFA di instance A tidak akan terlihat di instance B. Solusinya satu: database bersama.

Pakai PostgreSQL dengan replikasi streaming: satu primary untuk menulis, satu atau lebih replica untuk baca dan failover. Authelia hanya menulis ke primary, jadi di depan primary pasang connection pooler seperti PgBouncer, dan kelola perpindahan primary dengan Patroni atau layanan database terkelola.

configuration.yml — storage PostgreSQL bersama
storage:
  postgres:
    address: tcp://postgres-primary:5432
    database: authelia
    username: authelia
    password: '<storage-password>'
    ssl:
      mode: require
    maximum_active_connections: 8
    minimum_idle_connections: 0

Dengan skema ini, semua instance membaca dan menulis ke dataset yang sama, dan MFA yang didaftarkan di instance mana pun dikenali di seluruh instance.

Load Balancer, Sticky Session, dan Health Check

Load balancer adalah gerbang tunggal yang menerima trafik lalu meneruskannya ke instance yang sehat. Karena sesi tersimpan di Redis bersama, sticky session tidak wajib — request bisa mendarat di instance mana pun dan pengguna tetap dikenali. Mengaktifkan sticky session boleh dilakukan untuk mengurangi sedikit roundtrip, tapi jangan jadikan itu ketergantungan arsitektur; jika instance mati, sesi pengguna harus tetap bertahan.

Health check menentukan instance mana yang "sehat" untuk menerima trafik. Authelia menyediakan endpoint sederhana di /api/health yang mengembalikan status OK — cek langsung dengan curl -fsS https://auth.example.com/api/health:

Memeriksa health endpoint
curl -fsS https://auth.example.com/api/health

Response-nya berupa JSON: {"status":"OK"}. Catatan penting: endpoint ini hanya memastikan proses HTTP Authelia hidup, bukan memastikan Redis dan database tersambung. Untuk layer kepercayaan ekstra, tambahkan check dependency di lapisan terpisah — misalnya redis-cli ping dan SELECT 1 di database.

Contoh Docker Compose Multi-Instance

Berikut kerangka docker-compose dengan dua instance Authelia, Redis master dengan satu replica (disederhanakan tanpa Sentinel penuh untuk fokus), dan PostgreSQL bersama:

docker-compose.yml — Authelia HA (ringkas)
services:
  authelia-1:
    image: authelia/authelia:4.38
    container_name: authelia-1
    restart: unless-stopped
    volumes:
      - ./configuration.yml:/config/configuration.yml:ro
      - ./users_database.yml:/config/users_database.yml:ro
    networks: [auth]
    depends_on:
      redis-master:
        condition: service_healthy
      postgres:
        condition: service_healthy
    healthcheck:
      test: ["CMD", "wget", "-qO-", "http://127.0.0.1:9091/api/health"]
      interval: 30s
      timeout: 5s
      retries: 3
 
  authelia-2:
    image: authelia/authelia:4.38
    container_name: authelia-2
    restart: unless-stopped
    volumes:
      - ./configuration.yml:/config/configuration.yml:ro
      - ./users_database.yml:/config/users_database.yml:ro
    networks: [auth]
    depends_on:
      redis-master:
        condition: service_healthy
      postgres:
        condition: service_healthy
    healthcheck:
      test: ["CMD", "wget", "-qO-", "http://127.0.0.1:9091/api/health"]
      interval: 30s
      timeout: 5s
      retries: 3
 
  redis-master:
    image: redis:7-alpine
    command: ["redis-server", "--appendonly", "yes", "--requirepass", "${REDIS_PASSWORD}"]
    networks: [auth]
    volumes:
      - redis-data:/data
    healthcheck:
      test: ["CMD", "redis-cli", "-a", "${REDIS_PASSWORD}", "ping"]
      interval: 10s
      timeout: 5s
      retries: 5
 
  redis-replica:
    image: redis:7-alpine
    command: ["redis-server", "--replicaof", "redis-master", "6379", "--appendonly", "yes"]
    networks: [auth]
    depends_on:
      redis-master:
        condition: service_healthy
 
  postgres:
    image: postgres:16-alpine
    environment:
      POSTGRES_DB: authelia
      POSTGRES_USER: authelia
      POSTGRES_PASSWORD: ${STORAGE_PASSWORD}
    networks: [auth]
    volumes:
      - pgdata:/var/lib/postgresql/data
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U authelia"]
      interval: 10s
      timeout: 5s
      retries: 5
 
networks:
  auth:
 
volumes:
  redis-data:
  pgdata:

Kedua instance memakai file konfigurasi yang sama persis. Bedanya hanya nama container — hal yang diperlukan agar tidak bentrok di network Docker. Di depan kedua instance ini berdiri reverse proxy atau load balancer yang meneruskan trafik dan mengecek health mereka.

Aktifkan AOF (--appendonly yes) pada Redis agar sesi yang valid bisa pulih setelah restart. Jalankan stack dengan docker compose up -d. Untuk produksi yang lebih serius, ganti pola di atas dengan Sentinel penuh atau layanan Redis terkelola, serta PostgreSQL dengan replikasi streaming.

Penutup

Episode 24 ini memberi kalian fondasi HA Authelia: memahami mengapa Authelia stateless sehingga bisa digandakan, berbagi sesi lewat Redis Sentinel, berbagi data persisten lewat PostgreSQL, menerapkan health check yang benar, dan merangkai semuanya dalam satu docker-compose multi-instance.

Poin kunci:

  • Authelia stateless — sesi di Redis, data di database; instance sendiri kosong.
  • Redis Sentinel dibutuhkan agar sesi bertahan saat master Redis mati.
  • Storage database wajib dibagikan, kalau tidak MFA antar-instance tidak konsisten.
  • Health check /api/health wajib dipakai load balancer; tambahkan check dependency terpisah.
  • Sticky session tidak wajib karena sesi sudah ada di Redis bersama.

Mengelola banyak container dengan tangan bisa kacau — saat skala tumbuh, jawabannya adalah orkestrasi. Di episode 25 kita pindah ke Kubernetes Deployment: Helm chart resmi Authelia, ConfigMap dan Secret untuk konfigurasi, Ingress dengan forward auth, hingga HPA. Sampai jumpa di episode 25!

Belajar Authelia - High Availability Setup | Belajar Authelia