Zero-Trust SSO Gateway

Complete Setup Guide for Beginners

Authentik Docker Home Lab
0

What Are We Building?

Understanding the big picture before we start

🔐
Single Sign-On for Your Home Lab

One login to access all your self-hosted apps. No more remembering dozens of passwords!

How It Works

👤
You
🛡️
Traefik
Guard
🔑
Authentik
ID Check
📊
Your Apps
Grafana, etc
🎯

What You'll Have When Done

  • Central login page for all your apps
  • Multi-factor authentication (MFA) protection
  • Automatic HTTPS certificates
  • Role-based access control
  • Complete audit logs of who accessed what
⏱️

Time Investment

Phase Time Difficulty
Prerequisites & Accounts 30-60 min Easy
Local Machine Setup (SSH client) 10-20 min Easy
Server Setup (Docker, Firewall) 30-45 min Medium
Core Services 45-60 min Medium
Authentik Configuration 30-45 min Medium

Total: 3-4 hours (can be split across multiple sessions)

1

Understand The Setup

Two machines, different roles

⚡ Critical: You Need TWO Things

  • Your Computer (Windows/Mac/Linux) - Where you type commands from
  • A Server (Linux) - Where Docker and all services run

Docker is installed on the SERVER, not your computer!

Your Setup Explained

💻

YOUR COMPUTER

Windows, Mac, or Linux

Install:
• SSH Client (to connect to server)
• Web Browser (to access apps)


SSH
🖥️

YOUR SERVER

Ubuntu Linux (required)

Install:
• Docker & Docker Compose
• Traefik, Authentik, etc.

What Can Be Your Server?

Option Pros Cons
Old PC/Laptop Free, good performance Uses power, takes space
Mini PC (Intel NUC, etc) Small, quiet, efficient Costs $150-400
Raspberry Pi 5 Cheap ($80), tiny Limited performance
Virtual Machine Run on existing computer Shares resources
Cloud VPS No hardware needed Monthly cost ($5-20)
🐧
Server Must Run Linux

Your server needs Ubuntu Server 24.04 LTS (or similar Linux). This is where Docker will be installed. Your personal computer (Windows/Mac) is just used to connect to it.

2

Prerequisites

What you need before starting

📋
Checklist Before You Begin

Make sure you have everything ready to avoid interruptions

🖥️

Server Hardware Requirements

Component Minimum Recommended
CPU 4 cores 8 cores
RAM 8 GB 16 GB
Storage 100 GB SSD 250 GB SSD
🌐

Network Requirements

  • Static internal IP for your server (or DHCP reservation)
  • Router access to forward ports 80 and 443
  • Internet connection for downloading software
💿

Software Downloads

For your SERVER: Ubuntu Server 24.04 LTS

⬇️ Download Ubuntu Server
🎬
New to Linux?

Search YouTube for "How to install Ubuntu Server 24.04" for step-by-step video guides. It takes about 15-20 minutes.

3

Accounts to Create

Sign up for these services first

📝
Create These Accounts First

You'll need accounts with these services. All are FREE for home use!

📌
Write Down Your Domain

Throughout this guide, we'll use homelab.dev as an example. Replace this with YOUR domain:

Your Domain: __________________ (write it down!)

4

Local Machine Setup

Setting up YOUR computer to connect to the server

💻
SSH Client Installation

Install the tool to connect to your server remotely

1
Windows 10/11: SSH is Built-In!

Good news! Modern Windows has SSH pre-installed. Just use PowerShell or Command Prompt.

💻 Connect Using PowerShell
# Open PowerShell (Press Windows key, type "PowerShell", hit Enter)

# Connect to your server (replace with your details)
ssh your-username@192.168.1.100

# Example: if your username is "riz" and server IP is 192.168.1.50
ssh riz@192.168.1.50

# First time connecting? Type "yes" when asked about fingerprint
# Then enter your server password
💡
Alternative: Windows Terminal

For a better experience, download Windows Terminal from the Microsoft Store. It's free and much nicer!

2
Alternative: PuTTY (Graphical SSH Client)

If you prefer a GUI application:

  1. Download PuTTY from official website
  2. Install and open PuTTY
  3. Enter your server IP in "Host Name"
  4. Click "Open"
  5. Enter username and password when prompted
1
macOS: SSH is Built-In!

macOS comes with SSH pre-installed. Just use Terminal.

💻 Connect Using Terminal
# Open Terminal:
# Press Cmd + Space, type "Terminal", hit Enter

# Connect to your server (replace with your details)
ssh your-username@192.168.1.100

# Example: if your username is "riz" and server IP is 192.168.1.50
ssh riz@192.168.1.50

# First time connecting? Type "yes" when asked about fingerprint
# Then enter your server password
💡
Pro Tip: iTerm2

For a better terminal experience, download iTerm2. It's free and has many useful features!

1
Linux: SSH is Built-In!

All Linux distributions come with SSH. Just open your terminal.

💻 Connect Using Terminal
# Open your terminal application
# (Usually Ctrl + Alt + T on Ubuntu/Debian)

# Connect to your server (replace with your details)
ssh your-username@192.168.1.100

# Example: if your username is "riz" and server IP is 192.168.1.50
ssh riz@192.168.1.50

# First time connecting? Type "yes" when asked about fingerprint
# Then enter your server password
📝
Find Your Server's IP Address

On your server (with keyboard/monitor attached), run: ip addr or hostname -I

Look for an IP like 192.168.x.x or 10.0.x.x

5

Server Setup

Installing Docker on your Ubuntu Server

⚠️ Important: Run These Commands ON THE SERVER

First, SSH into your server from your computer. Then run these commands.

All commands below are run ON THE SERVER, not your local computer!

1
Update Your Server
⏱️ 5 min

First, SSH into your server, then update all packages:

🔄 System Update Commands
# Update package lists
sudo apt update

# Upgrade all packages
sudo apt upgrade -y

# Install required packages
sudo apt install -y curl git openssl ufw ca-certificates
2
Install Docker on Ubuntu Server
⏱️ 10 min

Docker runs your applications in containers. This is where Authentik and Traefik will live.

🐳 Docker Installation (Ubuntu Server)
# ============================================
# DOCKER INSTALLATION FOR UBUNTU SERVER 24.04
# Run these commands ONE BY ONE on your server
# ============================================

# Step 1: Set up Docker's apt repository
sudo apt-get update
sudo apt-get install -y ca-certificates curl

# Step 2: Add Docker's official GPG key
sudo install -m 0755 -d /etc/apt/keyrings
sudo curl -fsSL https://download.docker.com/linux/ubuntu/gpg -o /etc/apt/keyrings/docker.asc
sudo chmod a+r /etc/apt/keyrings/docker.asc

# Step 3: Add Docker repository to Apt sources
echo \
  "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/ubuntu \
  $(. /etc/os-release && echo "$VERSION_CODENAME") stable" | \
  sudo tee /etc/apt/sources.list.d/docker.list > /dev/null

# Step 4: Install Docker packages
sudo apt-get update
sudo apt-get install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin

# Step 5: Add your user to docker group (so you don't need sudo)
sudo usermod -aG docker $USER

# Step 6: IMPORTANT - Log out and log back in!
echo "Now type 'exit' to logout, then SSH back in"
⚠️
You Must Log Out!

After running these commands, type exit to disconnect, then SSH back in. This applies the docker group membership.

Verify Docker Works (After Re-login)
# After logging back in via SSH, verify Docker works
docker --version
# Should show: Docker version 24.x.x or newer

docker compose version
# Should show: Docker Compose version v2.x.x

# Test Docker (should run without sudo)
docker run hello-world
# Should show: "Hello from Docker!" message
3
Configure Firewall
⏱️ 3 min

Protect your server with UFW firewall:

🔥 Firewall Configuration
# Set default policies
sudo ufw default deny incoming
sudo ufw default allow outgoing

# Allow SSH (IMPORTANT - don't lock yourself out!)
sudo ufw allow ssh

# Allow HTTP and HTTPS for web traffic
sudo ufw allow 80/tcp
sudo ufw allow 443/tcp

# Enable the firewall
sudo ufw enable

# Type 'y' when asked to proceed

# Check status
sudo ufw status
4
Create Project Directory
⏱️ 1 min
📁 Create Directory Structure
# Create main project directory
mkdir -p ~/homelab-iam

# Create subdirectories
mkdir -p ~/homelab-iam/traefik/{dynamic,acme}
mkdir -p ~/homelab-iam/authentik
mkdir -p ~/homelab-iam/apps

# Navigate to the project
cd ~/homelab-iam

# Verify structure
ls -la
5
Router Port Forwarding
⏱️ 10 min

Forward ports 80 and 443 from your router to your server:

  1. Find your router's IP - Usually 192.168.1.1 or 192.168.0.1
  2. Open your router's admin page in a browser
  3. Find "Port Forwarding" (might be under Advanced, NAT, or Firewall)
  4. Add two rules:
    External Port Internal IP Internal Port Protocol
    80 Your server IP 80 TCP
    443 Your server IP 443 TCP
Server is Ready!

Docker is installed and running. Now let's deploy the actual services!

6

Deploy Core Services

Setting up Traefik and Authentik

🚀
The Heart of Your System

Traefik handles web traffic. Authentik handles identity. Together, they secure your apps.

1
Create Environment File
⏱️ 5 min

This file stores your secrets. Run this on your SERVER:

🔐 Create .env File
# Navigate to project directory
cd ~/homelab-iam

# Generate random passwords automatically
POSTGRES_PASS=$(openssl rand -base64 32 | tr -d '\n')
REDIS_PASS=$(openssl rand -base64 32 | tr -d '\n')
AUTHENTIK_KEY=$(openssl rand -base64 50 | tr -d '\n')

# Create the .env file with your secrets
cat > .env << EOF
# ============================================
# HOMELAB IAM CONFIGURATION
# ============================================

# IMPORTANT: Replace these with YOUR values!
DOMAIN=yourdomain.com
ACME_EMAIL=your-email@example.com

# Database passwords (auto-generated - don't change)
POSTGRES_PASSWORD=${POSTGRES_PASS}
REDIS_PASSWORD=${REDIS_PASS}
AUTHENTIK_SECRET_KEY=${AUTHENTIK_KEY}
EOF

# Protect the file
chmod 600 .env

# Show the file contents
cat .env
✏️
Edit Required!

You MUST edit the .env file to add your real domain and email:

nano ~/homelab-iam/.env

Change yourdomain.com to your actual domain.

Press Ctrl+O to save, Ctrl+X to exit.

2
Create Traefik Configuration
⏱️ 3 min
🛡️ traefik.yml - Main Configuration
cat > ~/homelab-iam/traefik/traefik.yml << 'EOF'
# Traefik Configuration
api:
  dashboard: true

log:
  level: INFO

entryPoints:
  web:
    address: ":80"
    http:
      redirections:
        entryPoint:
          to: websecure
          scheme: https
  websecure:
    address: ":443"

certificatesResolvers:
  letsencrypt:
    acme:
      email: ${ACME_EMAIL}
      storage: /etc/traefik/acme/acme.json
      httpChallenge:
        entryPoint: web

providers:
  docker:
    endpoint: "unix:///var/run/docker.sock"
    exposedByDefault: false
    network: traefik-public
  file:
    directory: /etc/traefik/dynamic
    watch: true
EOF
⚙️ middlewares.yml
cat > ~/homelab-iam/traefik/dynamic/middlewares.yml << 'EOF'
http:
  middlewares:
    authentik-auth:
      forwardAuth:
        address: "http://authentik-server:9000/outpost.goauthentik.io/auth/traefik"
        trustForwardHeader: true
        authResponseHeaders:
          - X-authentik-username
          - X-authentik-groups
          - X-authentik-email
          - X-authentik-name
          - X-authentik-uid

    security-headers:
      headers:
        frameDeny: true
        contentTypeNosniff: true
        browserXssFilter: true
        stsSeconds: 31536000
        stsIncludeSubdomains: true
EOF
📄 Create ACME Storage File
# Create certificate storage file
touch ~/homelab-iam/traefik/acme/acme.json
chmod 600 ~/homelab-iam/traefik/acme/acme.json
3
Create Docker Compose File
⏱️ 5 min
🐳 docker-compose.yml - Complete Stack
cat > ~/homelab-iam/docker-compose.yml << 'EOF'
services:
  # TRAEFIK - Reverse Proxy
  traefik:
    image: traefik:v3.0
    container_name: traefik
    restart: unless-stopped
    ports:
      - "80:80"
      - "443:443"
    volumes:
      - /var/run/docker.sock:/var/run/docker.sock:ro
      - ./traefik/traefik.yml:/etc/traefik/traefik.yml:ro
      - ./traefik/dynamic:/etc/traefik/dynamic:ro
      - ./traefik/acme:/etc/traefik/acme
    environment:
      - ACME_EMAIL=${ACME_EMAIL}
    networks:
      - traefik-public
    labels:
      - "traefik.enable=true"
      - "traefik.http.routers.traefik.rule=Host(\`traefik.${DOMAIN}\`)"
      - "traefik.http.routers.traefik.entrypoints=websecure"
      - "traefik.http.routers.traefik.tls.certresolver=letsencrypt"
      - "traefik.http.routers.traefik.service=api@internal"

  # POSTGRESQL - Database
  postgres:
    image: postgres:16-alpine
    container_name: postgres
    restart: unless-stopped
    environment:
      POSTGRES_USER: authentik
      POSTGRES_PASSWORD: ${POSTGRES_PASSWORD}
      POSTGRES_DB: authentik
    volumes:
      - postgres_data:/var/lib/postgresql/data
    networks:
      - authentik-internal
    healthcheck:
      test: ["CMD-SHELL", "pg_isready -U authentik"]
      interval: 10s
      timeout: 5s
      retries: 5

  # REDIS - Session Cache
  redis:
    image: redis:7-alpine
    container_name: redis
    restart: unless-stopped
    command: redis-server --requirepass ${REDIS_PASSWORD}
    volumes:
      - redis_data:/data
    networks:
      - authentik-internal
    healthcheck:
      test: ["CMD", "redis-cli", "-a", "${REDIS_PASSWORD}", "ping"]
      interval: 10s
      timeout: 5s
      retries: 5

  # AUTHENTIK SERVER
  authentik-server:
    image: ghcr.io/goauthentik/server:2024.4.2
    container_name: authentik-server
    restart: unless-stopped
    command: server
    environment:
      AUTHENTIK_POSTGRESQL__HOST: postgres
      AUTHENTIK_POSTGRESQL__USER: authentik
      AUTHENTIK_POSTGRESQL__PASSWORD: ${POSTGRES_PASSWORD}
      AUTHENTIK_POSTGRESQL__NAME: authentik
      AUTHENTIK_REDIS__HOST: redis
      AUTHENTIK_REDIS__PASSWORD: ${REDIS_PASSWORD}
      AUTHENTIK_SECRET_KEY: ${AUTHENTIK_SECRET_KEY}
      AUTHENTIK_ERROR_REPORTING__ENABLED: false
    volumes:
      - authentik_media:/media
      - authentik_templates:/templates
    networks:
      - traefik-public
      - authentik-internal
    depends_on:
      postgres:
        condition: service_healthy
      redis:
        condition: service_healthy
    labels:
      - "traefik.enable=true"
      - "traefik.http.routers.authentik.rule=Host(\`authentik.${DOMAIN}\`)"
      - "traefik.http.routers.authentik.entrypoints=websecure"
      - "traefik.http.routers.authentik.tls.certresolver=letsencrypt"
      - "traefik.http.services.authentik.loadbalancer.server.port=9000"

  # AUTHENTIK WORKER
  authentik-worker:
    image: ghcr.io/goauthentik/server:2024.4.2
    container_name: authentik-worker
    restart: unless-stopped
    command: worker
    environment:
      AUTHENTIK_POSTGRESQL__HOST: postgres
      AUTHENTIK_POSTGRESQL__USER: authentik
      AUTHENTIK_POSTGRESQL__PASSWORD: ${POSTGRES_PASSWORD}
      AUTHENTIK_POSTGRESQL__NAME: authentik
      AUTHENTIK_REDIS__HOST: redis
      AUTHENTIK_REDIS__PASSWORD: ${REDIS_PASSWORD}
      AUTHENTIK_SECRET_KEY: ${AUTHENTIK_SECRET_KEY}
    volumes:
      - authentik_media:/media
      - authentik_templates:/templates
    networks:
      - authentik-internal
    depends_on:
      postgres:
        condition: service_healthy
      redis:
        condition: service_healthy

networks:
  traefik-public:
    name: traefik-public
  authentik-internal:
    name: authentik-internal

volumes:
  postgres_data:
  redis_data:
  authentik_media:
  authentik_templates:
EOF
4
Start All Services
⏱️ 5 min
🚀 Start Services
# Navigate to project directory
cd ~/homelab-iam

# Pull all images first
docker compose pull

# Start all services
docker compose up -d

# Check status
docker compose ps
Wait 2-3 Minutes

Let's Encrypt needs time to issue your HTTPS certificates. If you get certificate errors, wait and try again.

7

Configure Authentik

Setting up your Identity Provider

🔑
Your Identity Command Center

Authentik is where you manage users, groups, and application access

1
Initial Admin Setup
⏱️ 5 min
  1. Open your browser and go to:
    https://authentik.yourdomain.com/if/flow/initial-setup/
  2. Create your admin account:
    • Email: Your email address
    • Password: A strong password
  3. Click "Create Account"
🔐
Save Your Credentials!

Write down your admin username and password. This is your master key!

2
Create User Groups
⏱️ 5 min
  1. Navigate to: DirectoryGroupsCreate
  2. Create these groups:
    Group Name Purpose Is Superuser?
    users All authenticated users No
    admins Full system administrators Yes ✅
  3. Add yourself to the admins group
3
Enable Multi-Factor Authentication
⏱️ 5 min
  1. Click your username (top right) → User Settings
  2. Go to MFA Devices tab
  3. Click "Enroll" next to TOTP
  4. Scan QR code with authenticator app (Google Authenticator, Authy, etc.)
  5. Enter 6-digit code to confirm
Authentik is Ready!

You now have a working Identity Provider with MFA enabled!

8

Testing Your Setup

Verify everything works correctly

🧪
Test Checklist

Let's verify every component is working

✅ Test Checklist

  • Traefik Dashboard: https://traefik.yourdomain.com
  • Authentik Login: https://authentik.yourdomain.com
  • MFA Working: Login requires authenticator code
  • HTTPS Working: Green padlock in browser
Quick Health Checks (Run on Server)
🔍 Diagnostic Commands
# Check all containers are running
docker compose ps

# Check for any errors
docker compose logs --tail=20

# Check Authentik specifically
docker logs authentik-server --tail=20

# Check Traefik
docker logs traefik --tail=20
🔧

Common Issues

🔴 Certificate Error / "Not Secure"

Cause: Let's Encrypt hasn't issued certificates yet

Solutions:
• Wait 5-10 minutes
• Check DNS: nslookup authentik.yourdomain.com
• Check Traefik logs: docker logs traefik
• Verify ports 80/443 are forwarded correctly

🔴 "502 Bad Gateway" Error

Cause: Backend service isn't running

Solutions:
• Check services: docker compose ps
• Restart: docker compose restart
• Check logs: docker compose logs

🔴 Can't Connect to Server

Cause: SSH or network issue

Solutions:
• Verify server is on: check with monitor/keyboard
• Check IP address: run ip addr on server
• Check firewall: sudo ufw status
• Ensure SSH is allowed: sudo ufw allow ssh

🎉

Congratulations!

Your Zero-Trust SSO Gateway is running!

🏆
What You've Accomplished

You now have enterprise-grade identity management in your home lab!

🚀

Next Steps

  • Add applications (Grafana, Gitea, Nextcloud) with OIDC
  • Create additional users for family/friends
  • Set up monitoring and logging (Loki + Grafana)
  • Configure backup procedures
  • Add Project B: HashiCorp Vault for secrets management