Documentation updates

This commit is contained in:
kelinfoxy
2026-01-24 21:40:51 -05:00
parent a1c9a0958b
commit a59862c988
15 changed files with 93 additions and 2026 deletions

View File

@@ -13,7 +13,7 @@ The **core stack** (`/opt/stacks/core/`) contains essential services that must r
- **Sablier**: Lazy loading service for on-demand container startup (saves resources) - **Sablier**: Lazy loading service for on-demand container startup (saves resources)
### Deployment Model ### Deployment Model
- **Two-script setup**: `setup-homelab.sh` (system prep, Docker install, secrets generation) → `deploy-homelab.sh` (automated deployment) - **Unified script setup**: `ez-homelab.sh` (system prep, secrets generation, service deployment)
- **Dockge-based management**: All stacks in `/opt/stacks/`, managed via web UI at `dockge.${DOMAIN}` - **Dockge-based management**: All stacks in `/opt/stacks/`, managed via web UI at `dockge.${DOMAIN}`
- **Automated workflows**: Scripts create directories, configure networks, deploy stacks, wait for health checks - **Automated workflows**: Scripts create directories, configure networks, deploy stacks, wait for health checks
- **Repository location**: `/home/kelin/EZ-Homelab/` (templates in `docker-compose/`, docs in `docs/`) - **Repository location**: `/home/kelin/EZ-Homelab/` (templates in `docker-compose/`, docs in `docs/`)
@@ -113,21 +113,12 @@ Proxy non-Docker services (Raspberry Pi, NAS) via Traefik file provider:
### First-Time Deployment ### First-Time Deployment
```bash ```bash
cd ~/AI-Homelab cd ~/EZ-Homelab
sudo ./scripts/setup-homelab.sh # System prep, Docker install, Authelia secrets ./ez-homelab.sh # Unified setup and deployment
# Reboot if NVIDIA drivers installed
sudo ./scripts/deploy-homelab.sh # Deploy core+infrastructure stacks, open Dockge
``` ```
### Managing Services via Scripts ### Managing Services via Scripts
- **setup-homelab.sh**: Idempotent system preparation (skips completed steps, runs on bare Debian) - **ez-homelab.sh**: Unified setup and deployment script (system prep, secrets generation, service deployment)
- Steps: Update system → Install Docker → Configure firewall → Generate Authelia secrets → Create directories/networks → NVIDIA driver detection
- Auto-generates: JWT secret (64 hex), session secret (64 hex), encryption key (64 hex), admin password hash
- Creates `homelab-network` and `traefik-network` Docker networks
- **deploy-homelab.sh**: Automated stack deployment (requires `.env` configured first)
- Steps: Validate prerequisites → Create directories → Deploy core → Deploy infrastructure → Deploy dashboards → Prepare additional stacks → Wait for Dockge
- Copies `.env` to `/opt/stacks/core/.env` and `/opt/stacks/infrastructure/.env`
- Waits for service health checks before proceeding
### Testing Changes ### Testing Changes
```bash ```bash
@@ -279,7 +270,7 @@ x-dockge:
- **Dynamic reloading**: Changes apply without container restarts - **Dynamic reloading**: Changes apply without container restarts
### Authelia Password Generation ### Authelia Password Generation
Secrets auto-generated by `setup-homelab.sh`: Secrets auto-generated by `ez-homelab.sh`:
- JWT secret: `openssl rand -hex 64` - JWT secret: `openssl rand -hex 64`
- Session secret: `openssl rand -hex 64` - Session secret: `openssl rand -hex 64`
- Encryption key: `openssl rand -hex 64` - Encryption key: `openssl rand -hex 64`

View File

@@ -30,8 +30,9 @@ You are an AI agent specialized in managing Docker-based homelab infrastructure
│ ├── proxying-external-hosts.md │ ├── proxying-external-hosts.md
│ └── troubleshooting/ │ └── troubleshooting/
├── scripts/ # Automation scripts ├── scripts/ # Automation scripts
│ ├── setup-homelab.sh # First-run setup │ ├── ez-homelab.sh # Unified setup and deployment
── deploy-homelab.sh # Automated deployment ── reset-test-environment.sh # Safe test environment cleanup
│ └── reset-ondemand-services.sh # Reload services for Sablier lazy loading
├── .env.example # Environment template ├── .env.example # Environment template
├── .env # User-created environment file (not in git) ├── .env # User-created environment file (not in git)
├── AGENT_INSTRUCTIONS.md # This file ├── AGENT_INSTRUCTIONS.md # This file
@@ -263,7 +264,7 @@ labels:
### Development Workflow ### Development Workflow
1. **Repository Maintenance** 1. **Repository Maintenance**
- Test deployment scripts: `./scripts/setup-homelab.sh`, `./scripts/deploy-homelab.sh` - Test deployment script: `./scripts/ez-homelab.sh`
- Verify compose file syntax across all stacks - Verify compose file syntax across all stacks
- Validate `.env.example` completeness - Validate `.env.example` completeness
- Check documentation accuracy - Check documentation accuracy
@@ -529,14 +530,14 @@ docker compose -f docker-compose/core.yml config
grep -v '^#' .env | grep -v '^$' grep -v '^#' .env | grep -v '^$'
# Test script syntax # Test script syntax
bash -n scripts/deploy-homelab.sh bash -n scripts/ez-homelab.sh
# Verify file permissions # Verify file permissions
ls -la ~/EZ-Homelab/ ls -la ~/EZ-Homelab/
``` ```
### Deployment Checklist ### Deployment Checklist
- [ ] Fresh system: Test `setup-homelab.sh` - [ ] Fresh system: Test `ez-homelab.sh`
- [ ] Core stack: Deploy and verify DuckDNS, Traefik, Authelia, Gluetun - [ ] Core stack: Deploy and verify DuckDNS, Traefik, Authelia, Gluetun
- [ ] Infrastructure: Deploy Dockge and verify web UI access - [ ] Infrastructure: Deploy Dockge and verify web UI access
- [ ] Additional stacks: Test individual stack deployment - [ ] Additional stacks: Test individual stack deployment

View File

@@ -33,7 +33,7 @@ With VS Code connected to your server, you can now use GitHub Copilot to guide y
### Initial Server Setup ### Initial Server Setup
- **Clone repository**: Ask Copilot "Help me clone the AI-Homelab repository" - **Clone repository**: Ask Copilot "Help me clone the AI-Homelab repository"
- **Configure environment**: "Guide me through setting up the .env file" - **Configure environment**: "Guide me through setting up the .env file"
- **Run setup scripts**: "Walk me through running the setup-homelab.sh script" - **Run setup scripts**: "Walk me through running the ez-homelab.sh script"
- **Deploy services**: "Help me run the deployment script" - **Deploy services**: "Help me run the deployment script"
### AI-Assisted Configuration ### AI-Assisted Configuration

View File

@@ -35,39 +35,18 @@ For most users, the automated setup script handles everything from system prepar
**Note:** The `.env` file stays in the repository folder (`~/EZ-Homelab/.env`). The deploy script copies it to stack directories automatically. Authelia secrets (JWT, session, encryption key) are auto-generated by the setup script - leave them with default values for now. **Note:** The `.env` file stays in the repository folder (`~/EZ-Homelab/.env`). The deploy script copies it to stack directories automatically. Authelia secrets (JWT, session, encryption key) are auto-generated by the setup script - leave them with default values for now.
5. **Run the setup script:** 5. **Run the unified setup script:**
```bash ```bash
sudo ./scripts/setup-homelab.sh ./scripts/ez-homelab.sh
``` ```
The script will: The script will guide you through:
- Update system packages - System preparation (if needed)
- Install Docker Engine + Compose V2 (if needed) - Domain and credential configuration
- Configure user groups (docker, sudo) - Service stack selection
- Set up firewall (UFW) - Authelia secrets generation
- Enable SSH server - SSL certificate setup
- **Generate Authelia secrets** (JWT, session, encryption key) - Service deployment
- **Prompt for admin username, password, and email**
- **Generate argon2id password hash** (30-60 seconds)
- Create `/opt/stacks/` directory structure
- Set up Docker networks (homelab, traefik, dockerproxy, media)
- Detect NVIDIA GPU and offer driver installation
**Important:** If NVIDIA drivers were installed, reboot your system now before continuing.
6. **Deploy homelab**:
```bash
sudo ./scripts/deploy-homelab.sh
```
**The deploy script automatically:**
- Creates Docker networks
- Configures Traefik with your email and domain
- **Obtains wildcard SSL certificate** (*.yourdomain.duckdns.org) via DNS challenge
- Deploys core stack (DuckDNS, Traefik, Authelia, Gluetun)
- Deploys infrastructure stack (Dockge, Pi-hole, monitoring)
- Deploys dashboards stack (Homepage, Homarr)
- Opens Dockge in your browser
**Note:** Certificate generation may take 2-5 minutes. All services will use the wildcard certificate automatically. **Note:** Certificate generation may take 2-5 minutes. All services will use the wildcard certificate automatically.
@@ -78,11 +57,11 @@ For most users, the automated setup script handles everything from system prepar
**That's it!** Your homelab is ready. **That's it!** Your homelab is ready.
**Access Dockge at `https://dockge.yourdomain.duckdns.org`** **Access Dockge at `https://dockge.yourdomain.duckdns.org`**
## What the Setup Script Does ## What the Unified Setup Script Does
The `setup-homelab.sh` script is a comprehensive first-run configuration tool: The `ez-homelab.sh` script is a comprehensive guided setup and deployment tool:
**System Preparation:** **System Preparation (when needed):**
- ✅ Pre-flight checks (internet connectivity, disk space 50GB+) - ✅ Pre-flight checks (internet connectivity, disk space 50GB+)
- ✅ Updates system packages - ✅ Updates system packages
- ✅ Installs required packages (git, curl, etc.) - ✅ Installs required packages (git, curl, etc.)
@@ -91,22 +70,25 @@ The `setup-homelab.sh` script is a comprehensive first-run configuration tool:
- ✅ Sets up firewall (UFW with SSH, HTTP, HTTPS) - ✅ Sets up firewall (UFW with SSH, HTTP, HTTPS)
- ✅ Enables SSH server - ✅ Enables SSH server
**Authelia Configuration (Interactive):** **Interactive Configuration:**
- ✅ Guides through domain setup (DuckDNS)
- ✅ Prompts for admin username, email, and password
- ✅ Generates three cryptographic secrets (JWT, session, encryption) - ✅ Generates three cryptographic secrets (JWT, session, encryption)
- ✅ Prompts for admin username (default: admin)
- ✅ Prompts for secure password with confirmation
- ✅ Prompts for admin email address
- ✅ Generates argon2id password hash using Docker (30-60s process) - ✅ Generates argon2id password hash using Docker (30-60s process)
- ✅ Validates Docker is available before password operations - ✅ Allows service stack selection
- ✅ Saves credentials securely for deployment script - ✅ Validates Docker is available before operations
**Infrastructure Setup:** **Infrastructure Setup & Deployment:**
- ✅ Creates directory structure (`/opt/stacks/`) - ✅ Creates directory structure (`/opt/stacks/`)
- ✅ Sets up Docker networks (homelab, traefik, dockerproxy, media) - ✅ Sets up Docker networks (homelab, traefik, dockerproxy, media)
- ✅ Deploys selected service stacks
- ✅ Obtains wildcard SSL certificate (*.yourdomain.duckdns.org)
- ✅ Detects NVIDIA GPU and offers driver installation - ✅ Detects NVIDIA GPU and offers driver installation
- ✅ Opens Dockge when ready
**Safety Features:** **Safety Features:**
- Skips completed steps (safe to re-run) - Interactive guidance with clear prompts
- Timeout handling (60s for Docker operations) - Timeout handling (60s for Docker operations)
- Comprehensive error messages with troubleshooting hints - Comprehensive error messages with troubleshooting hints
- Exit on critical failures with clear next steps - Safe to re-run (idempotent operations)
- Confirmation prompts for destructive actions

View File

@@ -110,9 +110,9 @@ Set your timezone. Common options:
### 4. Authelia Secrets ### 4. Authelia Secrets
**⚠️ IMPORTANT:** These are auto-generated by the setup script. Do NOT set them manually. **⚠️ IMPORTANT:** These are auto-generated by the unified setup script. Do NOT set them manually.
The `setup-homelab.sh` script will generate secure random secrets for: The `ez-homelab.sh` script will generate secure random secrets for:
- JWT Secret (64 hex characters) - JWT Secret (64 hex characters)
- Session Secret (64 hex characters) - Session Secret (64 hex characters)
- Storage Encryption Key (64 hex characters) - Storage Encryption Key (64 hex characters)

View File

@@ -6,9 +6,7 @@ Welcome to your AI-powered homelab! This guide will walk you through setting up
- [ ] Clone this repository to your home folder - [ ] Clone this repository to your home folder
- [ ] Configure `.env` file with your domain and tokens ([see prerequisites](env-configuration.md)) - [ ] Configure `.env` file with your domain and tokens ([see prerequisites](env-configuration.md))
- [ ] Forward ports 80 and 443 from your router to your server - [ ] Forward ports 80 and 443 from your router to your server
- [ ] Run setup script (generates Authelia secrets and admin user) ([setup-homelab.sh](../scripts/setup-homelab.sh)) - [ ] Run unified setup script (generates Authelia secrets and admin user, deploys services) ([ez-homelab.sh](../scripts/ez-homelab.sh))
- [ ] Log out and back in for Docker group permissions
- [ ] Run deployment script (deploys all core, infrastructure & dashboard services) ([deploy-homelab.sh](../scripts/deploy-homelab.sh))
- [ ] Access Dockge web UI (`https://dockge.${DOMAIN}`) - [ ] Access Dockge web UI (`https://dockge.${DOMAIN}`)
- [ ] Set up 2FA with Authelia ([Authelia setup guide](service-docs/authelia.md)) - [ ] Set up 2FA with Authelia ([Authelia setup guide](service-docs/authelia.md))
- [ ] (optional) Deploy additional stacks as needed via Dockge ([services overview](services-overview.md)) - [ ] (optional) Deploy additional stacks as needed via Dockge ([services overview](services-overview.md))

View File

@@ -205,12 +205,12 @@ docker network create network-name
## Switching to Automated ## Switching to Automated
If manual setup works, you can switch to the automated scripts for future updates: If manual setup works, you can switch to the unified automated script for future updates:
```bash ```bash
# Just run the deploy script # Just run the unified setup script
cd ~/AI-Homelab cd ~/EZ-Homelab
sudo ./scripts/deploy-homelab.sh ./scripts/ez-homelab.sh
``` ```
The deploy script is idempotent - it won't break existing configurations. The unified script is idempotent - it won't break existing configurations.

View File

@@ -26,8 +26,7 @@ Your homelab uses separate stacks for organization:
For detailed information about the deployment scripts, their features, and usage, see [scripts/README.md](../scripts/README.md). For detailed information about the deployment scripts, their features, and usage, see [scripts/README.md](../scripts/README.md).
**Quick summary:** **Quick summary:**
- `setup-homelab.sh` - First-run system setup and Authelia configuration - `ez-homelab.sh` - Unified setup and deployment script (system prep, secrets generation, service deployment)
- `deploy-homelab.sh` - Deploy all core services and prepare additional stacks
- `reset-test-environment.sh` - Testing/development only - removes all deployed services - `reset-test-environment.sh` - Testing/development only - removes all deployed services
- `reset-ondemand-services.sh` - Reload services for Sablier lazy loading - `reset-ondemand-services.sh` - Reload services for Sablier lazy loading
@@ -530,15 +529,10 @@ deploy:
### Minimal setup ### Minimal setup
```bash ```bash
# Clone and configure # Clone and configure
git clone https://github.com/kelinfoxy/AI-Homelab.git git clone https://github.com/kelinfoxy/EZ-Homelab.git
cd AI-Homelab cd EZ-Homelab
sudo ./scripts/setup-homelab.sh ./scripts/ez-homelab.sh
cp .env.example .env ```
nano .env
# Deploy core only
mkdir -p /opt/stacks/core
cp docker-compose/core/docker-compose.yml /opt/stacks/core/docker-compose.yml
cp -r config-templates/traefik /opt/stacks/core/ cp -r config-templates/traefik /opt/stacks/core/
cp -r config-templates/authelia /opt/stacks/core/ cp -r config-templates/authelia /opt/stacks/core/
cp .env /opt/stacks/core/ cp .env /opt/stacks/core/

View File

@@ -95,8 +95,8 @@ docker compose up -d
**Solution:** **Solution:**
```bash ```bash
# Re-run deployment script (safe - won't affect running services) # Re-run unified setup script (safe - won't affect running services)
sudo ./scripts/deploy-homelab.sh ./scripts/ez-homelab.sh
# Or manually fix: # Or manually fix:
cd /opt/stacks/dashboards/homepage cd /opt/stacks/dashboards/homepage
@@ -181,8 +181,8 @@ sudo systemctl stop systemd-resolved
# Check what exists # Check what exists
ls -la /opt/stacks/ ls -la /opt/stacks/
# Re-run deployment to copy stacks # Re-run unified setup script to copy stacks
sudo ./scripts/deploy-homelab.sh ./scripts/ez-homelab.sh
``` ```
## Performance Issues ## Performance Issues
@@ -233,9 +233,8 @@ sudo docker logs authelia
# Use the safe reset script # Use the safe reset script
sudo ./scripts/reset-test-environment.sh sudo ./scripts/reset-test-environment.sh
# Then re-run setup and deploy # Then re-run unified setup script
sudo ./scripts/setup-homelab.sh ./scripts/ez-homelab.sh
sudo ./scripts/deploy-homelab.sh
``` ```
### Partial Reset (Single Stack) ### Partial Reset (Single Stack)

View File

@@ -1,20 +1,18 @@
# AI-Homelab Setup Scripts # EZ-Homelab Setup Scripts
This directory contains scripts for automated AI-Homelab deployment and management: This directory contains scripts for automated EZ-Homelab deployment and management:
1. **setup-homelab.sh** - System preparation 1. **ez-homelab.sh** - Unified setup and deployment script
2. **deploy-homelab.sh** - Core infrastructure deployment 2. **reset-test-environment.sh** - Safe test environment cleanup
3. **reset-test-environment.sh** - Safe test environment cleanup 3. **reset-ondemand-services.sh** - Reload services for Sablier lazy loading
4. **reset-ondemand-services.sh** - Reload services for Sablier lazy loading
## setup-homelab.sh ## ez-homelab.sh
Automated first-run setup script for preparing a fresh Debian installation for AI-Homelab deployment. Unified guided setup and deployment script that handles both system preparation and service deployment in a single interactive session.
> You can skip this if you have the following completed already.
Or run it to verify.
### What It Does ### What It Does
**System Preparation (when needed):**
1. **System Update** - Updates all system packages 1. **System Update** - Updates all system packages
2. **Install Dependencies** - Installs required packages (curl, git, etc.) 2. **Install Dependencies** - Installs required packages (curl, git, etc.)
3. **Install Docker** - Adds Docker repository and installs Docker Engine with Compose V2 3. **Install Docker** - Adds Docker repository and installs Docker Engine with Compose V2
@@ -24,23 +22,40 @@ Or run it to verify.
7. **Create Directories** - Sets up `/opt/stacks`, `/opt/dockge`, `/mnt/media`, `/mnt/downloads` 7. **Create Directories** - Sets up `/opt/stacks`, `/opt/dockge`, `/mnt/media`, `/mnt/downloads`
8. **Create Docker Networks** - Creates homelab-network, traefik-network, and media-network 8. **Create Docker Networks** - Creates homelab-network, traefik-network, and media-network
**Configuration & Deployment:**
1. **Interactive Setup** - Guides you through domain, admin credentials, and service selection
2. **Authelia Secrets Generation** - Generates JWT, session, and encryption keys
3. **Admin User Creation** - Prompts for admin username, email, and password
4. **Service Deployment** - Deploys selected stacks based on your choices
5. **SSL Certificate Setup** - Obtains wildcard certificate via DNS challenge
6. **Dockge Access** - Opens Dockge web UI when ready
### Usage ### Usage
```bash ```bash
cd ~/AI-Homelab cd ~/EZ-Homelab
# Make the script executable (if needed) # Make the script executable (if needed)
chmod +x scripts/setup-homelab.sh chmod +x scripts/ez-homelab.sh
# Run with sudo # Run the script (will use sudo when needed)
sudo ./scripts/setup-homelab.sh ./scripts/ez-homelab.sh
``` ```
### Interactive Options
The script will prompt you to:
- Enter your domain (e.g., yourdomain.duckdns.org)
- Provide DuckDNS token
- Set admin credentials for Authelia
- Choose which service stacks to deploy
- Configure additional settings as needed
### After Running ### After Running
1. Log out and log back in for group changes to take effect 1. Access Dockge at `https://dockge.yourdomain.duckdns.org`
2. Edit `.env` file with your configuration 2. Log in with your configured Authelia credentials
3. Run `deploy-homelab.sh` to deploy core infrastructure and Dockge 3. Deploy additional stacks through Dockge's web UI
### NVIDIA GPU Support ### NVIDIA GPU Support
@@ -61,14 +76,16 @@ This manual approach avoids driver conflicts that often occur with automated ins
### Requirements ### Requirements
- Fresh Debian installation (Debian 11 or 12) - Fresh Debian/Ubuntu installation (or existing system)
- Root access (via sudo) - Root access (via sudo)
- Internet connection - Internet connection
- Ports 80 and 443 forwarded to your server
### Tested On ### Tested On
- Debian 11 (Bullseye) - Debian 11 (Bullseye)
- Debian 12 (Bookworm) - Debian 12 (Bookworm)
- Ubuntu 20.04/22.04
### Notes ### Notes
@@ -80,117 +97,6 @@ This manual approach avoids driver conflicts that often occur with automated ins
--- ---
## deploy-homelab.sh
Automated deployment script that deploys the core infrastructure and Dockge. Run this after editing your `.env` file.
### What It Does
1. **Validate Prerequisites** - Checks for Docker, .env file, and proper configuration
2. **Create Directories** - Sets up `/opt/stacks/core` and `/opt/stacks/infrastructure`
3. **Create Docker Networks** - Ensures homelab-network, traefik-network, and media-network exist
4. **Deploy Core Stack** - Deploys DuckDNS, Traefik, and Authelia
5. **Deploy Infrastructure Stack** - Deploys Dockge, Portainer, Pi-hole, and monitoring tools
6. **Wait for Dockge** - Waits for Dockge web UI to become accessible
7. **Open Browser** - Automatically opens Dockge in your default browser
### Usage
```bash
# From the AI-Homelab directory
cd AI-Homelab
# Ensure .env is configured
cp .env.example .env
nano .env # Edit with your values
# Make the script executable (if needed)
chmod +x scripts/deploy-homelab.sh
# Run WITHOUT sudo (run as your regular user)
./scripts/deploy-homelab.sh
```
### After Running
The script will automatically open `https://dockge.yourdomain.duckdns.org` in your browser when Dockge is ready.
1. Log in to Dockge using your Authelia credentials (configured in `/opt/stacks/core/authelia/users_database.yml`)
2. Deploy additional stacks through Dockge's web UI:
- `dashboards.yml` - Homepage and Homarr
- `media.yml` - Plex, Jellyfin, Sonarr, Radarr, etc.
- `media-extended.yml` - Readarr, Lidarr, etc.
- `homeassistant.yml` - Home Assistant and accessories
- `productivity.yml` - Nextcloud, Gitea, wikis
- `monitoring.yml` - Grafana, Prometheus
- `utilities.yml` - Backups, password manager
### Requirements
- Docker and Docker Compose installed
- `.env` file configured with your domain and credentials
- User must be in docker group (handled by setup-homelab.sh)
### Browser Detection
The script will attempt to open Dockge using:
- `xdg-open` (default on most Linux desktops)
- `gnome-open` (GNOME desktop)
- `firefox` or `google-chrome` (direct browser launch)
If no browser is detected, it will display the URL for manual access.
### Manual Deployment Alternative
If you prefer to deploy manually instead of using the script:
```bash
# Deploy core stack
mkdir -p /opt/stacks/core
cp docker-compose/core.yml /opt/stacks/core/docker-compose.yml
cp -r config-templates/traefik /opt/stacks/core/
cp -r config-templates/authelia /opt/stacks/core/
cp .env /opt/stacks/core/
cd /opt/stacks/core && docker compose up -d
# Deploy infrastructure stack
mkdir -p /opt/stacks/infrastructure
cp docker-compose/infrastructure.yml /opt/stacks/infrastructure/docker-compose.yml
cp .env /opt/stacks/infrastructure/
cd /opt/stacks/infrastructure && docker compose up -d
# Manually open: https://dockge.yourdomain.duckdns.org
```
### Troubleshooting
**Script says "Docker daemon is not running":**
- Run: `sudo systemctl start docker`
- Or log out and back in if you just added yourself to docker group
**Script says ".env file not found":**
- Run: `cp .env.example .env` and edit with your values
**Dockge doesn't open automatically:**
- The script will display the URL to open manually
- Wait a minute for services to fully start
- Check logs: `docker compose -f /opt/stacks/infrastructure/docker-compose.yml logs dockge`
**Traefik SSL certificate errors:**
- Initial certificate generation can take a few minutes
- Check DuckDNS token is correct in .env
- Verify your domain is accessible from the internet
### Notes
- Run as regular user (NOT with sudo)
- Validates .env configuration before deployment
- Waits up to 60 seconds for Dockge to become ready
- Automatically copies .env to stack directories
- Safe to run multiple times (idempotent)
---
## reset-test-environment.sh ## reset-test-environment.sh
Safe cleanup script for testing environments. Completely removes all deployed services, data, and configurations while preserving the underlying system setup. Intended for development and testing scenarios only. Safe cleanup script for testing environments. Completely removes all deployed services, data, and configurations while preserving the underlying system setup. Intended for development and testing scenarios only.
@@ -231,8 +137,7 @@ sudo ./scripts/reset-test-environment.sh
The system will be returned to a clean state ready for re-deployment: The system will be returned to a clean state ready for re-deployment:
1. Ensure `.env` file is properly configured 1. Ensure `.env` file is properly configured
2. Run: `sudo ./scripts/setup-homelab.sh` (if needed) 2. Run: `./scripts/ez-homelab.sh`
3. Run: `./scripts/deploy-homelab.sh`
### Requirements ### Requirements

View File

@@ -1,465 +0,0 @@
#!/bin/bash
# EZ-Homelab Deployment Script
# This script deploys homelab services with flexible options
# Run after: 1) setup-homelab.sh and 2) editing .env file
# Run as: ./deploy-homelab.sh
set -e # Exit on error
# Colors for output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
NC='\033[0m' # No Color
# Log functions
log_info() {
echo -e "${BLUE}[INFO]${NC} $1"
}
log_success() {
echo -e "${GREEN}[SUCCESS]${NC} $1"
}
log_warning() {
echo -e "${YELLOW}[WARNING]${NC} $1"
}
log_error() {
echo -e "${RED}[ERROR]${NC} $1"
}
# Check if running as root
if [ "$EUID" -eq 0 ]; then
log_error "Please do NOT run this script as root or with sudo"
log_info "Run as: ./deploy-homelab.sh"
exit 1
fi
# Get script directory (EZ-Homelab/scripts)
SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
REPO_DIR="$( cd "$SCRIPT_DIR/.." && pwd )"
log_info "EZ-Homelab Deployment Script"
echo ""
# Check if .env file exists
if [ ! -f "$REPO_DIR/.env" ]; then
log_error ".env file not found!"
log_info "Please create and configure your .env file first:"
echo " cd $REPO_DIR"
echo " cp .env.example .env"
echo " nano .env"
exit 1
fi
# Check if Docker is installed and running
if ! command -v docker &> /dev/null; then
log_error "Docker is not installed. Please run setup-homelab.sh first."
exit 1
fi
if ! docker info &> /dev/null; then
log_error "Docker daemon is not running or you don't have permission."
log_info "Try: sudo systemctl start docker"
log_info "Or log out and log back in for group changes to take effect"
exit 1
fi
log_success "Docker is available and running"
echo ""
# Load environment variables for domain check
source "$REPO_DIR/.env"
if [ -z "$DOMAIN" ]; then
log_error "DOMAIN is not set in .env file"
log_info "Please edit .env and set your DuckDNS domain"
exit 1
fi
log_info "Using domain: $DOMAIN"
echo ""
# Deployment options menu
echo "=========================================="
echo " EZ-HOMELAB DEPLOYMENT OPTIONS"
echo "=========================================="
echo ""
echo "Choose your deployment scenario:"
echo ""
echo "1) Full deployment (recommended for new servers)"
echo " - Deploy core infrastructure (Traefik, Authelia, etc.)"
echo " - Deploy infrastructure stack (Dockge, Pi-hole, etc.)"
echo " - Deploy dashboards (Homepage, Homarr)"
echo " - Setup all remaining stacks for Dockge"
echo ""
echo "2) Skip core stack (for existing homelab servers)"
echo " - Skip core infrastructure deployment"
echo " - Deploy infrastructure stack (Dockge, Pi-hole, etc.)"
echo " - Deploy dashboards (Homepage, Homarr)"
echo " - Setup all remaining stacks for Dockge"
echo ""
echo "3) Setup stacks only (no deployment)"
echo " - Setup all stacks in Dockge without deploying any"
echo " - Useful for preparing stacks for manual deployment"
echo ""
read -p "Enter your choice (1-3): " DEPLOY_CHOICE
case $DEPLOY_CHOICE in
1)
DEPLOY_CORE=true
DEPLOY_INFRASTRUCTURE=true
DEPLOY_DASHBOARDS=true
SETUP_STACKS=true
log_info "Selected: Full deployment"
;;
2)
DEPLOY_CORE=false
DEPLOY_INFRASTRUCTURE=true
DEPLOY_DASHBOARDS=true
SETUP_STACKS=true
log_info "Selected: Skip core stack"
;;
3)
DEPLOY_CORE=false
DEPLOY_INFRASTRUCTURE=false
DEPLOY_DASHBOARDS=false
SETUP_STACKS=true
log_info "Selected: Setup stacks only"
;;
*)
log_error "Invalid choice. Please run the script again."
exit 1
;;
esac
echo ""
# Function to replace environment variables in config files
replace_env_vars() {
local config_dir="$1"
local env_file="$2"
log_info "Processing environment variables in $config_dir..."
# Find all files in the config directory
find "$config_dir" -type f \( -name "*.yml" -o -name "*.yaml" -o -name "*.conf" -o -name "*.json" \) | while read -r file; do
# Extract all ${VAR_NAME} patterns from the file
vars_found=$(grep -o '\${[^}]*}' "$file" | sed 's/\${//' | sed 's/}//' | sort | uniq)
if [ -n "$vars_found" ]; then
log_info "Processing file: $(basename "$file")"
for var in $vars_found; do
# Check if variable exists in .env file
if grep -q "^${var}=" "$env_file" 2>/dev/null; then
# Get the value from .env file
value=$(grep "^${var}=" "$env_file" | cut -d'=' -f2- | sed 's/^"//' | sed 's/"$//')
# Escape special characters for sed
escaped_value=$(printf '%s\n' "$value" | sed 's/[[\.*^$()+?{|]/\\&/g')
# Replace in file
sed -i "s|\${${var}}|${escaped_value}|g" "$file"
log_info " ✓ Replaced \${$var}"
else
log_warning " ⚠ Variable \${$var} not found in .env file - leaving as-is"
fi
done
fi
done
}
# Function to setup stacks without deploying them
setup_stacks_for_dockge() {
log_info "Setting up all stacks for Dockge..."
# List of stacks to setup
STACKS=("vpn" "media" "media-management" "monitoring" "productivity" "utilities" "alternatives" "homeassistant" "nextcloud")
for stack in "${STACKS[@]}"; do
STACK_DIR="/opt/stacks/$stack"
REPO_STACK_DIR="$REPO_DIR/docker-compose/$stack"
if [ -d "$REPO_STACK_DIR" ]; then
log_info "Setting up $stack stack..."
# Create stack directory
mkdir -p "$STACK_DIR"
# Copy docker-compose.yml
if [ -f "$REPO_STACK_DIR/docker-compose.yml" ]; then
cp "$REPO_STACK_DIR/docker-compose.yml" "$STACK_DIR/"
cp "$REPO_DIR/.env" "$STACK_DIR/.env"
# Copy any additional config directories
for config_dir in "$REPO_STACK_DIR"/*/; do
if [ -d "$config_dir" ] && [ "$(basename "$config_dir")" != "." ]; then
cp -r "$config_dir" "$STACK_DIR/"
fi
done
# Replace environment variables in the stack configuration
replace_env_vars "$STACK_DIR" "$STACK_DIR/.env"
log_success "$stack stack prepared for Dockge"
else
log_warning "$stack stack docker-compose.yml not found, skipping..."
fi
else
log_warning "$stack stack directory not found in repo, skipping..."
fi
done
log_success "All stacks prepared for Dockge deployment"
echo ""
}
# Step 1: Create required directories
log_info "Step 1: Creating required directories..."
mkdir -p /opt/stacks/core
mkdir -p /opt/stacks/infrastructure
mkdir -p /opt/dockge/data
log_success "Directories created"
echo ""
# Step 2: Create Docker networks (if they don't exist)
log_info "Step 2: Creating Docker networks..."
docker network create homelab-network 2>/dev/null && log_success "Created homelab-network" || log_info "homelab-network already exists"
docker network create traefik-network 2>/dev/null && log_success "Created traefik-network" || log_info "traefik-network already exists"
docker network create media-network 2>/dev/null && log_success "Created media-network" || log_info "media-network already exists"
echo ""
# Step 3: Deploy core infrastructure (DuckDNS, Traefik, Authelia, Gluetun)
if [ "$DEPLOY_CORE" = true ]; then
log_info "Step 3: Deploying core infrastructure stack..."
log_info " - DuckDNS (Dynamic DNS)"
log_info " - Traefik (Reverse Proxy with SSL)"
log_info " - Authelia (Single Sign-On)"
log_info " - Gluetun (VPN Client)"
echo ""
# Copy core stack files with overwrite checks
if [ -f "/opt/stacks/core/docker-compose.yml" ]; then
log_warning "docker-compose.yml already exists in /opt/stacks/core/"
log_info "Creating backup: docker-compose.yml.backup.$(date +%Y%m%d_%H%M%S)"
cp /opt/stacks/core/docker-compose.yml /opt/stacks/core/docker-compose.yml.backup.$(date +%Y%m%d_%H%M%S)
fi
cp "$REPO_DIR/docker-compose/core/docker-compose.yml" /opt/stacks/core/docker-compose.yml
if [ -d "/opt/stacks/core/traefik" ]; then
log_warning "Traefik configuration already exists in /opt/stacks/core/"
log_info "Creating backup: traefik.backup.$(date +%Y%m%d_%H%M%S)"
mv /opt/stacks/core/traefik /opt/stacks/core/traefik.backup.$(date +%Y%m%d_%H%M%S)
fi
cp -r "$REPO_DIR/config-templates/traefik" /opt/stacks/core/
# Detect server hostname and update configuration
log_info "Detecting server hostname..."
DETECTED_HOSTNAME=$(hostname)
if [ -n "$DETECTED_HOSTNAME" ] && [ "$DETECTED_HOSTNAME" != "debian" ]; then
log_info "Detected hostname: $DETECTED_HOSTNAME"
# Update SERVER_HOSTNAME in the copied .env file
sed -i "s/SERVER_HOSTNAME=.*/SERVER_HOSTNAME=$DETECTED_HOSTNAME/" /opt/stacks/core/.env
# Update SERVER_HOSTNAME in the source .env file for future deployments
sed -i "s/SERVER_HOSTNAME=.*/SERVER_HOSTNAME=$DETECTED_HOSTNAME/" "$REPO_DIR/.env"
# Update sablier.yml with detected hostname
sed -i "s/debian-/$DETECTED_HOSTNAME-/g" /opt/stacks/core/traefik/dynamic/sablier.yml
log_success "Updated configuration with detected hostname: $DETECTED_HOSTNAME"
else
log_info "Using default hostname 'debian' (hostname detection failed or returned default)"
fi
echo ""
if [ -d "/opt/stacks/core/authelia" ]; then
log_warning "Authelia configuration already exists in /opt/stacks/core/"
log_info "Creating backup: authelia.backup.$(date +%Y%m%d_%H%M%S)"
mv /opt/stacks/core/authelia /opt/stacks/core/authelia.backup.$(date +%Y%m%d_%H%M%S)
fi
cp -r "$REPO_DIR/config-templates/authelia" /opt/stacks/core/
# Replace domain placeholders in Authelia config (legacy hardcoded replacement)
sed -i "s/your-domain.duckdns.org/${DOMAIN}/g" /opt/stacks/core/authelia/configuration.yml
if [ -f "/opt/stacks/core/.env" ]; then
log_warning ".env already exists in /opt/stacks/core/"
log_info "Creating backup: .env.backup.$(date +%Y%m%d_%H%M%S)"
cp /opt/stacks/core/.env /opt/stacks/core/.env.backup.$(date +%Y%m%d_%H%M%S)
fi
cp "$REPO_DIR/.env" /opt/stacks/core/.env
# Automatically replace all environment variables in config files
replace_env_vars "/opt/stacks/core" "/opt/stacks/core/.env"
# Legacy hardcoded replacements (keeping for backward compatibility)
# These will be overridden by the automatic replacement above if variables exist
sed -i "s/admin/${AUTHELIA_ADMIN_USER}/g" /opt/stacks/core/authelia/users_database.yml
sed -i "s/admin@example.com/${AUTHELIA_ADMIN_EMAIL}/g" /opt/stacks/core/authelia/users_database.yml
sed -i "s|\$argon2id\$v=19\$m=65536,t=3,p=4\$CHANGEME|${AUTHELIA_ADMIN_PASSWORD}|g" /opt/stacks/core/authelia/users_database.yml
# Deploy core stack
cd /opt/stacks/core
docker compose up -d
log_success "Core infrastructure deployed"
echo ""
# Wait for Traefik to be ready
log_info "Waiting for Traefik to initialize..."
sleep 10
# Check if Traefik is healthy
if docker ps | grep -q "traefik.*Up"; then
log_success "Traefik is running"
else
log_warning "Traefik container check inconclusive, continuing..."
fi
echo ""
else
log_info "Skipping core infrastructure deployment"
echo ""
fi
# Step 4: Deploy infrastructure stack (Dockge and monitoring tools)
if [ "$DEPLOY_INFRASTRUCTURE" = true ]; then
log_info "Step 4: Deploying infrastructure stack..."
log_info " - Dockge (Docker Compose Manager)"
log_info " - Pi-hole (DNS Ad Blocker)"
log_info " - Watchtower (Container Updates)"
log_info " - Dozzle (Log Viewer)"
log_info " - Glances (System Monitor)"
log_info " - Docker Proxy (Security)"
echo ""
# Copy infrastructure stack
cp "$REPO_DIR/docker-compose/infrastructure/docker-compose.yml" /opt/stacks/infrastructure/docker-compose.yml
cp "$REPO_DIR/.env" /opt/stacks/infrastructure/.env
# Deploy infrastructure stack
cd /opt/stacks/infrastructure
docker compose up -d
log_success "Infrastructure stack deployed"
echo ""
else
log_info "Skipping infrastructure stack deployment"
echo ""
fi
# Step 5: Deploy dashboard stack
if [ "$DEPLOY_DASHBOARDS" = true ]; then
log_info "Step 5: Deploying dashboard stack..."
log_info " - Homepage (Application Dashboard)"
log_info " - Homarr (Modern Dashboard)"
echo ""
# Create dashboards directory
mkdir -p /opt/stacks/dashboards
# Copy dashboards compose file
cp "$REPO_DIR/docker-compose/dashboards/docker-compose.yml" /opt/stacks/dashboards/docker-compose.yml
cp "$REPO_DIR/.env" /opt/stacks/dashboards/.env
# Copy homepage config
if [ -d "$REPO_DIR/docker-compose/dashboards/homepage" ]; then
cp -r "$REPO_DIR/docker-compose/dashboards/homepage" /opt/stacks/dashboards/
fi
# Deploy dashboards stack
cd /opt/stacks/dashboards
docker compose up -d
log_success "Dashboard stack deployed"
echo ""
else
log_info "Skipping dashboard stack deployment"
echo ""
fi
# Step 6: Deploy Dokuwiki
log_info "Step 6: Deploying Dokuwiki wiki platform..."
log_info " - DokuWiki (File-based wiki with pre-configured content)"
echo ""
# Create Dokuwiki directory
mkdir -p /opt/stacks/dokuwiki/config
# Copy Dokuwiki compose file
cp "$REPO_DIR/config-templates/dokuwiki/docker-compose.yml" /opt/stacks/dokuwiki/docker-compose.yml
# Copy pre-configured Dokuwiki config, content, and keys
if [ -d "$REPO_DIR/config-templates/dokuwiki/conf" ]; then
cp -r "$REPO_DIR/config-templates/dokuwiki/conf" /opt/stacks/dokuwiki/config/
else
log_warning "Dokuwiki conf directory not found, skipping..."
fi
if [ -d "$REPO_DIR/config-templates/dokuwiki/data" ]; then
cp -r "$REPO_DIR/config-templates/dokuwiki/data" /opt/stacks/dokuwiki/config/
else
log_warning "Dokuwiki data directory not found, skipping..."
fi
if [ -d "$REPO_DIR/config-templates/dokuwiki/keys" ]; then
cp -r "$REPO_DIR/config-templates/dokuwiki/keys" /opt/stacks/dokuwiki/config/
else
log_warning "Dokuwiki keys directory not found, skipping..."
fi
# Set proper ownership for Dokuwiki config
sudo chown -R 1000:1000 /opt/stacks/dokuwiki/config
# Deploy Dokuwiki
cd /opt/stacks/dokuwiki
docker compose up -d
log_success "Dokuwiki deployed with pre-configured content"
echo ""
# Step 7: Setup stacks for Dockge (if requested)
if [ "$SETUP_STACKS" = true ]; then
setup_stacks_for_dockge
fi
# Deployment completed
echo ""
echo "=========================================="
log_success "Deployment completed successfully!"
echo "=========================================="
echo ""
log_info "Access your services:"
echo ""
echo " 🚀 Dockge: $DOCKGE_URL"
echo " 📊 Homepage: https://home.${DOMAIN}"
echo " 🎯 Homarr: https://homarr.${DOMAIN}"
echo " 📖 Wiki: https://wiki.${DOMAIN}"
echo " 🔒 Authelia: https://auth.${DOMAIN}"
echo " 🔀 Traefik: https://traefik.${DOMAIN}"
echo ""
log_info "Next steps:"
echo ""
echo " 1. Log in to Dockge using your Authelia credentials"
echo " (configured in /opt/stacks/core/authelia/users_database.yml)"
echo ""
echo " 2. Access your dashboards:"
echo " - Homepage: https://home.${DOMAIN} (AI-configurable dashboard)"
echo " - Homarr: https://homarr.${DOMAIN} (Modern dashboard)"
echo ""
echo " 3. Access your pre-deployed Dokuwiki at https://wiki.${DOMAIN}"
echo " (admin/admin credentials)"
echo ""
echo " 4. Deploy additional stacks through Dockge's web UI:"
echo " - media.yml (Plex, Jellyfin, Sonarr, Radarr, etc.)"
echo " - media-extended.yml (Readarr, Lidarr, etc.)"
echo " - homeassistant.yml (Home Assistant and accessories)"
echo " - productivity.yml (Nextcloud, Gitea, additional wikis)"
echo " - monitoring.yml (Grafana, Prometheus, etc.)"
echo " - utilities.yml (Backups, code editors, etc.)"
echo ""
echo " 5. Configure services via the AI assistant in VS Code"
echo ""
echo "=========================================="
echo ""
log_info "For documentation, see: $REPO_DIR/docs/"
log_info "For troubleshooting, see: $REPO_DIR/docs/quick-reference.md"
echo ""

View File

@@ -649,9 +649,7 @@ main() {
echo " 🚀 Dockge: https://dockge.${DOMAIN}" echo " 🚀 Dockge: https://dockge.${DOMAIN}"
[ "$DEPLOY_CORE" = true ] && echo " 🔒 Authelia: https://auth.${DOMAIN}" [ "$DEPLOY_CORE" = true ] && echo " 🔒 Authelia: https://auth.${DOMAIN}"
[ "$DEPLOY_CORE" = true ] && echo " 🔀 Traefik: https://traefik.${DOMAIN}" [ "$DEPLOY_CORE" = true ] && echo " 🔀 Traefik: https://traefik.${DOMAIN}"
echo " 📊 Homepage: https://home.${DOMAIN}" echo " 📊 Homepage: https://homepage.${DOMAIN}"
echo " 🎯 Homarr: https://homarr.${DOMAIN}"
echo " 📖 Wiki: https://wiki.${DOMAIN}"
echo "" echo ""
fi fi

View File

@@ -163,8 +163,7 @@ log_info "System is ready for next round of testing"
echo "" echo ""
log_info "Next steps:" log_info "Next steps:"
echo " 1. Ensure .env file is properly configured" echo " 1. Ensure .env file is properly configured"
echo " 2. Run: sudo ./setup-homelab.sh" echo " 2. Run: ./ez-homelab.sh"
echo " 3. Run: sudo ./deploy-homelab.sh"
echo "" echo ""
log_info "Note: Docker and system packages are NOT removed" log_info "Note: Docker and system packages are NOT removed"
log_info "User groups and firewall settings are preserved" log_info "User groups and firewall settings are preserved"

View File

@@ -1,434 +0,0 @@
#!/bin/bash
# AI-Homelab First-Run Setup Script
# This script prepares a fresh Debian installation for homelab deployment
# Run as: sudo ./setup-homelab.sh
set -e # Exit on error
# Colors for output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
BLUE='\033[0;34m'
NC='\033[0m' # No Color
# Log functions
log_info() {
echo -e "${BLUE}[INFO]${NC} $1"
}
log_success() {
echo -e "${GREEN}[SUCCESS]${NC} $1"
}
log_warning() {
echo -e "${YELLOW}[WARNING]${NC} $1"
}
log_error() {
echo -e "${RED}[ERROR]${NC} $1"
}
# Check if running as root
if [ "$EUID" -ne 0 ]; then
log_error "Please run as root (use: sudo ./setup-homelab.sh)"
exit 1
fi
# Get the actual user who invoked sudo
ACTUAL_USER=${SUDO_USER:-$USER}
# Get script directory and repo directory
SCRIPT_DIR="$( cd "$( dirname "${BASH_SOURCE[0]}" )" && pwd )"
REPO_DIR="$( cd "$SCRIPT_DIR/.." && pwd )"
# Step 1: System Update
log_info "Step 1/10: Updating system packages..."
apt-get update && apt-get upgrade -y
log_success "System updated successfully"
echo ""
# Step 2: Install Required Packages
log_info "Step 2/10: Installing required packages..."
# Update package list first to avoid issues
apt-get update
# Install packages with error handling
if ! apt-get install -y \
apt-transport-https \
ca-certificates \
curl \
gnupg \
lsb-release \
git \
openssh-server \
sudo \
pciutils \
net-tools \
ufw; then
log_warning "Some packages may have failed to install. Attempting software-properties-common separately..."
apt-get install -y software-properties-common || log_warning "software-properties-common installation failed - may need manual intervention"
else
# Try to install software-properties-common separately as it sometimes causes issues
apt-get install -y software-properties-common || log_warning "software-properties-common installation failed - continuing anyway"
fi
log_success "Required packages installed"
echo ""
# Step 3: Install Docker
log_info "Step 3/10: Installing Docker..."
if command -v docker &> /dev/null && docker --version &> /dev/null; then
log_success "Docker is already installed ($(docker --version))"
# Check if Docker service is running
if ! systemctl is-active --quiet docker; then
log_warning "Docker service is not running, starting it..."
systemctl start docker
systemctl enable docker
log_success "Docker service started and enabled"
else
log_info "Docker service is already running"
fi
else
# Add Docker's official GPG key
install -m 0755 -d /etc/apt/keyrings
curl -fsSL https://download.docker.com/linux/debian/gpg -o /etc/apt/keyrings/docker.asc
chmod a+r /etc/apt/keyrings/docker.asc
# Add the repository to Apt sources
echo \
"deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/debian \
$(. /etc/os-release && echo "$VERSION_CODENAME") stable" | \
tee /etc/apt/sources.list.d/docker.list > /dev/null
# Update and install Docker
apt-get update
apt-get install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin
# Start and enable Docker service
systemctl start docker
systemctl enable docker
log_success "Docker installed and service started ($(docker --version))"
fi
echo ""
# Step 4: Configure User Groups
log_info "Step 4/10: Configuring user groups..."
# Add user to sudo group if not already
if groups "$ACTUAL_USER" | grep -q '\bsudo\b'; then
log_warning "User $ACTUAL_USER is already in sudo group"
else
usermod -aG sudo "$ACTUAL_USER"
log_success "User $ACTUAL_USER added to sudo group"
fi
# Add user to docker group
if groups "$ACTUAL_USER" | grep -q '\bdocker\b'; then
log_warning "User $ACTUAL_USER is already in docker group"
else
usermod -aG docker "$ACTUAL_USER"
log_success "User $ACTUAL_USER added to docker group"
fi
echo ""
# Step 5: Configure Firewall
log_info "Step 5/10: Configuring firewall..."
# Enable UFW if not already enabled
if ufw status | grep -q "Status: active"; then
log_warning "Firewall is already active"
else
ufw --force enable
log_success "Firewall enabled"
fi
# Allow SSH if not already allowed
if ufw status | grep -q "22/tcp"; then
log_warning "SSH port 22 is already allowed"
else
ufw allow ssh
log_success "SSH port allowed in firewall"
fi
# Allow HTTP/HTTPS for web services
ufw allow 80/tcp
ufw allow 443/tcp
log_success "HTTP/HTTPS ports allowed in firewall"
echo ""
# Step 6: Configure SSH
log_info "Step 6/10: Configuring SSH server..."
systemctl enable ssh
systemctl start ssh
# Check if SSH is running
if systemctl is-active --quiet ssh; then
SSH_PORT=$(grep "^Port" /etc/ssh/sshd_config | awk '{print $2}')
SSH_PORT=${SSH_PORT:-22}
log_success "SSH server is running on port $SSH_PORT"
else
log_warning "SSH server failed to start, check configuration"
fi
echo ""
# Step 7: Detect and Install NVIDIA Drivers (if applicable)
log_info "Step 7/10: Checking for NVIDIA GPU..."
# Detect NVIDIA GPU
if lspci | grep -i nvidia > /dev/null; then
log_info "NVIDIA GPU detected:"
lspci | grep -i nvidia
echo ""
# Check if NVIDIA drivers are already installed
if nvidia-smi &> /dev/null; then
log_warning "NVIDIA drivers are already installed"
NVIDIA_INSTALLED=true
else
log_info "Installing NVIDIA drivers..."
# Install kernel headers first (required for NVIDIA driver)
apt-get install -y linux-headers-amd64
# Install NVIDIA driver (non-interactive)
if apt-get install -y nvidia-driver; then
log_success "NVIDIA drivers installed"
NVIDIA_INSTALLED=false
else
log_warning "NVIDIA driver installation failed. You may need to install manually after reboot."
log_info "Try: sudo apt update && sudo apt install nvidia-driver"
NVIDIA_INSTALLED=false # Still set to false to trigger reboot reminder
fi
fi
# Check if NVIDIA Container Toolkit is installed
if command -v nvidia-container-runtime &> /dev/null; then
log_warning "NVIDIA Container Toolkit is already installed"
else
log_info "Installing NVIDIA Container Toolkit..."
# Install NVIDIA Container Toolkit
curl -fsSL https://nvidia.github.io/libnvidia-container/gpgkey | gpg --dearmor -o /usr/share/keyrings/nvidia-container-toolkit-keyring.gpg
curl -s -L https://nvidia.github.io/libnvidia-container/stable/deb/nvidia-container-toolkit.list | \
sed 's#deb https://#deb [signed-by=/usr/share/keyrings/nvidia-container-toolkit-keyring.gpg] https://#g' | \
tee /etc/apt/sources.list.d/nvidia-container-toolkit.list
apt-get update
apt-get install -y nvidia-container-toolkit
# Configure Docker to use NVIDIA runtime
nvidia-ctk runtime configure --runtime=docker
systemctl restart docker
log_success "NVIDIA Container Toolkit installed and configured"
fi
if [ "$NVIDIA_INSTALLED" = false ]; then
log_warning "NVIDIA drivers were installed. A reboot may be required for changes to take effect."
fi
echo ""
else
log_info "No NVIDIA GPU detected, skipping driver installation"
echo ""
fi
# Step 8: Create Directory Structure
log_info "Step 8/10: Creating directory structure..."
mkdir -p /opt/stacks
mkdir -p /opt/dockge/data
mkdir -p /mnt/media/{movies,tv,music,books,photos}
mkdir -p /mnt/downloads/{complete,incomplete}
mkdir -p /mnt/backups
mkdir -p /mnt/surveillance
mkdir -p /mnt/git
# Set ownership with error handling
log_info "Setting directory ownership to user: $ACTUAL_USER..."
if ! chown -R "$ACTUAL_USER:$ACTUAL_USER" /opt/stacks 2>/dev/null; then
log_warning "Failed to set ownership for /opt/stacks - you may need to run: sudo chown -R $ACTUAL_USER:$ACTUAL_USER /opt/stacks"
fi
if ! chown -R "$ACTUAL_USER:$ACTUAL_USER" /opt/dockge 2>/dev/null; then
log_warning "Failed to set ownership for /opt/dockge - you may need to run: sudo chown -R $ACTUAL_USER:$ACTUAL_USER /opt/dockge"
fi
if ! chown -R "$ACTUAL_USER:$ACTUAL_USER" /mnt/media 2>/dev/null; then
log_warning "Failed to set ownership for /mnt/media - you may need to run: sudo chown -R $ACTUAL_USER:$ACTUAL_USER /mnt/media"
fi
if ! chown -R "$ACTUAL_USER:$ACTUAL_USER" /mnt/downloads 2>/dev/null; then
log_warning "Failed to set ownership for /mnt/downloads - you may need to run: sudo chown -R $ACTUAL_USER:$ACTUAL_USER /mnt/downloads"
fi
if ! chown -R "$ACTUAL_USER:$ACTUAL_USER" /mnt/backups 2>/dev/null; then
log_warning "Failed to set ownership for /mnt/backups - you may need to run: sudo chown -R $ACTUAL_USER:$ACTUAL_USER /mnt/backups"
fi
if ! chown -R "$ACTUAL_USER:$ACTUAL_USER" /mnt/surveillance 2>/dev/null; then
log_warning "Failed to set ownership for /mnt/surveillance - you may need to run: sudo chown -R $ACTUAL_USER:$ACTUAL_USER /mnt/surveillance"
fi
if ! chown -R "$ACTUAL_USER:$ACTUAL_USER" /mnt/git 2>/dev/null; then
log_warning "Failed to set ownership for /mnt/git - you may need to run: sudo chown -R $ACTUAL_USER:$ACTUAL_USER /mnt/git"
fi
log_success "Directory structure created"
echo ""
# Step 9: Create Docker Networks
log_info "Step 9/10: Creating Docker networks..."
su - "$ACTUAL_USER" -c "docker network create homelab-network 2>/dev/null || true"
su - "$ACTUAL_USER" -c "docker network create traefik-network 2>/dev/null || true"
su - "$ACTUAL_USER" -c "docker network create media-network 2>/dev/null || true"
su - "$ACTUAL_USER" -c "docker network create dockerproxy-network 2>/dev/null || true"
log_success "Docker networks created"
echo ""
# Step 10: Generate Authelia Secrets
log_info "Step 10/10: Generating Authelia secrets..."
# Check if .env file exists, create from example if needed
if [ ! -f "$REPO_DIR/.env" ]; then
if [ -f "$REPO_DIR/.env.example" ]; then
cp "$REPO_DIR/.env.example" "$REPO_DIR/.env"
log_info ".env file created from .env.example"
else
log_error ".env and .env.example files not found in $REPO_DIR"
exit 1
fi
fi
# Generate cryptographic secrets
log_info "Generating Authelia JWT secret..."
AUTHELIA_JWT_SECRET=$(openssl rand -hex 64)
log_info "Generating Authelia session secret..."
AUTHELIA_SESSION_SECRET=$(openssl rand -hex 64)
log_info "Generating Authelia storage encryption key..."
AUTHELIA_STORAGE_ENCRYPTION_KEY=$(openssl rand -hex 64)
# Check for existing default credentials in .env
source "$REPO_DIR/.env"
USE_DEFAULTS=false
if [ -n "$DEFAULT_USER" ] && [ -n "$DEFAULT_PASSWORD" ] && [ -n "$DEFAULT_EMAIL" ]; then
echo ""
echo "Found existing default credentials in .env:"
echo " User: $DEFAULT_USER"
echo " Email: $DEFAULT_EMAIL"
echo " Password: [hidden]"
echo ""
read -p "Use these for Authelia admin? (Y/n): " USE_DEFAULT
USE_DEFAULT=${USE_DEFAULT:-y}
if [[ "$USE_DEFAULT" =~ ^[Yy]$ ]]; then
USE_DEFAULTS=true
ADMIN_USER=$DEFAULT_USER
ADMIN_EMAIL=$DEFAULT_EMAIL
ADMIN_PASSWORD=$DEFAULT_PASSWORD
fi
fi
if [ "$USE_DEFAULTS" = false ]; then
# Prompt for admin credentials
log_info "Configuring Authelia admin user..."
echo ""
echo "Authelia Admin Configuration:"
echo "=============================="
read -p "Admin username (default: admin): " ADMIN_USER
ADMIN_USER=${ADMIN_USER:-admin}
read -p "Admin email: " ADMIN_EMAIL
while [ -z "$ADMIN_EMAIL" ]; do
log_error "Email is required"
read -p "Admin email: " ADMIN_EMAIL
done
# Prompt for password with confirmation
while true; do
read -s -p "Admin password: " ADMIN_PASSWORD
echo ""
read -s -p "Confirm password: " ADMIN_PASSWORD_CONFIRM
echo ""
if [ "$ADMIN_PASSWORD" = "$ADMIN_PASSWORD_CONFIRM" ]; then
break
else
log_error "Passwords do not match. Please try again."
fi
done
fi
# Generate password hash using Authelia Docker image
log_info "Generating password hash (this may take 30-60 seconds)..."
# Check if Docker is running
if ! docker info > /dev/null 2>&1; then
log_error "Docker is not running. Please check Docker installation."
exit 1
fi
# Pull the Authelia image first
log_info "Pulling Authelia image..."
if ! docker pull authelia/authelia:latest > /dev/null 2>&1; then
log_error "Failed to pull Authelia image. Please check internet connectivity."
exit 1
fi
# Generate the hash
ADMIN_PASSWORD_HASH=$(docker run --rm authelia/authelia:latest authelia crypto hash generate argon2 --password "$ADMIN_PASSWORD" 2>&1 | grep -o '"[^"]*"' | tr -d '"')
if [ -z "$ADMIN_PASSWORD_HASH" ]; then
log_error "Failed to generate password hash. Please check Docker connectivity."
log_info "Debug: Trying manual hash generation..."
# Fallback: generate a basic hash using openssl (not recommended for production)
ADMIN_PASSWORD_HASH=$(echo -n "$ADMIN_PASSWORD" | openssl dgst -sha256 | cut -d' ' -f2)
if [ -n "$ADMIN_PASSWORD_HASH" ]; then
log_warning "Using fallback hash method. Please regenerate with proper Authelia hash later."
else
exit 1
fi
fi
# Update .env file with generated values
log_info "Updating .env file with generated secrets..."
# Use sed to replace the placeholder values
sed -i "s/AUTHELIA_JWT_SECRET=.*/AUTHELIA_JWT_SECRET=$AUTHELIA_JWT_SECRET/" "$REPO_DIR/.env"
sed -i "s/AUTHELIA_SESSION_SECRET=.*/AUTHELIA_SESSION_SECRET=$AUTHELIA_SESSION_SECRET/" "$REPO_DIR/.env"
sed -i "s/AUTHELIA_STORAGE_ENCRYPTION_KEY=.*/AUTHELIA_STORAGE_ENCRYPTION_KEY=$AUTHELIA_STORAGE_ENCRYPTION_KEY/" "$REPO_DIR/.env"
# Uncomment and set admin credentials
sed -i "s/# AUTHELIA_ADMIN_USER=.*/AUTHELIA_ADMIN_USER=$ADMIN_USER/" "$REPO_DIR/.env"
sed -i "s/# AUTHELIA_ADMIN_EMAIL=.*/AUTHELIA_ADMIN_EMAIL=$ADMIN_EMAIL/" "$REPO_DIR/.env"
sed -i "s/# AUTHELIA_ADMIN_PASSWORD=.*/AUTHELIA_ADMIN_PASSWORD=$ADMIN_PASSWORD_HASH/" "$REPO_DIR/.env"
log_success "Authelia secrets and admin credentials generated"
echo ""
# Final Summary
echo ""
echo "=========================================="
log_success "AI-Homelab setup completed successfully!"
echo "=========================================="
echo ""
log_info "Next steps:"
echo ""
echo " 1. Log out and log back in for group changes to take effect"
echo " (or run: newgrp docker)"
echo ""
echo " 2. Navigate to your EZ-Homelab repository:"
echo " cd ~/EZ-Homelab"
echo ""
echo " 3. Edit the .env file with your configuration:"
echo " cp .env.example .env"
echo " nano .env"
echo ""
echo " 4. Run the deployment script:"
echo " ./scripts/deploy-homelab.sh"
echo ""
echo " 5. Access Dockge at: https://dockge.yourdomain.duckdns.org"
echo " (Use your configured domain and Authelia credentials)"
echo ""
echo "=========================================="
if lspci | grep -i nvidia > /dev/null && [ "$NVIDIA_INSTALLED" = false ]; then
echo ""
log_warning "REMINDER: Reboot required for NVIDIA driver changes"
echo " Run: sudo reboot"
echo "=========================================="
fi
echo ""
log_info "Setup complete! Please log out and log back in."

View File

@@ -1,901 +0,0 @@
This file contains the current configuration for Traefik & Sablier on the server jarvis (192.168.4.4)
This configuration was working in a previous test round.
external-host-jarvis.yml
```yaml
http:
routers:
backrest-jarvis:
rule: "Host(`backrest.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: backrest-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-backrest@file
- authelia@docker
bookstack-jarvis:
rule: "Host(`bookstack.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: bookstack-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-bookstack@file
- authelia@docker
bitwarden-jarvis:
rule: "Host(`bitwarden.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: bitwarden-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-bitwarden@file
- authelia@docker
calibre-web-jarvis:
rule: "Host(`calibre.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: calibre-web-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-calibre-web@file
- authelia@docker
code-jarvis:
rule: "Host(`code.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: code-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-code-server@file
- authelia@docker
dockge-jarvis:
rule: "Host(`jarvis.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: dockge-jarvis
tls:
certResolver: letsencrypt
middlewares:
- authelia@docker
dockhand-jarvis:
rule: "Host(`dockhand.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: dockhand-jarvis
tls:
certResolver: letsencrypt
middlewares:
- authelia@docker
dokuwiki-jarvis:
rule: "Host(`wiki.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: dokuwiki-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-dokuwiki@file
- authelia@docker
dozzle-jarvis:
rule: "Host(`dozzle.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: dozzle-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-dozzle@file
- authelia@docker
duplicati-jarvis:
rule: "Host(`duplicati.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: duplicati-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-duplicati@file
- authelia@docker
formio-jarvis:
rule: "Host(`formio.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: formio-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-formio@file
- authelia@docker
gitea-jarvis:
rule: "Host(`gitea.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: gitea-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-gitea@file
- authelia@docker
glances-jarvis:
rule: "Host(`glances.jarvis.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: glances-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-glances@file
- authelia@docker
homepage-jarvis:
rule: "Host(`homepage.jarvis.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: homepage-jarvis
tls:
certResolver: letsencrypt
middlewares:
- authelia@docker
homarr-jarvis:
rule: "Host(`homarr.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: homarr-jarvis
tls:
certResolver: letsencrypt
middlewares:
- authelia@docker
- sablier-jarvis-homarr@file
jellyfin-jarvis:
rule: "Host(`jellyfin.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: jellyfin-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-jellyfin@file
# No authelia middleware for media apps
kopia-jarvis:
rule: "Host(`kopia.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: kopia-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-kopia@file
- authelia@docker
mealie-jarvis:
rule: "Host(`mealie.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: mealie-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-mealie@file
- authelia@docker
motioneye-jarvis:
rule: "Host(`motioneye.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: motioneye-jarvis
tls:
certResolver: letsencrypt
middlewares:
- authelia@docker
mediawiki-jarvis:
rule: "Host(`mediawiki.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: mediawiki-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-mediawiki@file
- authelia@docker
nextcloud-jarvis:
rule: "Host(`nextcloud.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: nextcloud-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-nextcloud@file
- authelia@docker
openkm-jarvis:
rule: "Host(`openkm.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: openkm-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-openkm@file
- authelia@docker
openwebui-jarvis:
rule: "Host(`openwebui.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: openwebui-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-openwebui@file
- authelia@docker
qbittorrent-jarvis:
rule: "Host(`torrents.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: qbittorrent-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-arr@file
- authelia@docker
tdarr-jarvis:
rule: "Host(`tdarr.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: tdarr-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-arr@file
- authelia@docker
unmanic-jarvis:
rule: "Host(`unmanic.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: unmanic-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-unmanic@file
- authelia@docker
wordpress-jarvis:
rule: "Host(`knot-u.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: wordpress-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-wordpress@file
- authelia@file
# Arr Services (no SSO for media apps)
jellyseerr-jarvis:
rule: "Host(`jellyseerr.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: jellyseerr-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-arr@file
- authelia@docker
prowlarr-jarvis:
rule: "Host(`prowlarr.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: prowlarr-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-arr@file
- authelia@docker
radarr-jarvis:
rule: "Host(`radarr.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: radarr-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-arr@file
- authelia@docker
sonarr-jarvis:
rule: "Host(`sonarr.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: sonarr-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-arr@file
- authelia@docker
lidarr-jarvis:
rule: "Host(`lidarr.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: lidarr-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-arr@file
- authelia@docker
readarr-jarvis:
rule: "Host(`readarr.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: readarr-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-arr@file
- authelia@docker
mylar3-jarvis:
rule: "Host(`mylar3.kelinreij.duckdns.org`)"
entryPoints:
- websecure
service: mylar3-jarvis
tls:
certResolver: letsencrypt
middlewares:
- sablier-jarvis-arr@file
- authelia@docker
services:
backrest-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:9898"
passHostHeader: true
bitwarden-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8000"
passHostHeader: true
bookstack-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:6875"
passHostHeader: true
calibre-web-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8083"
passHostHeader: true
code-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8079"
passHostHeader: true
dockge-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:5001"
passHostHeader: true
dockhand-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:3003"
passHostHeader: true
dokuwiki-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8087"
passHostHeader: true
dozzle-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8085"
passHostHeader: true
duplicati-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8200"
passHostHeader: true
formio-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:3002"
passHostHeader: true
gitea-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:3010"
passHostHeader: true
glances-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:61208"
passHostHeader: true
homarr-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:7575"
passHostHeader: true
homepage-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:3000"
passHostHeader: true
jellyfin-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8096"
passHostHeader: true
kopia-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:51515"
passHostHeader: true
mealie-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:9000"
passHostHeader: true
mediawiki-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8084"
passHostHeader: true
motioneye-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8081"
passHostHeader: true
nextcloud-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8089"
passHostHeader: true
openkm-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:18080"
passHostHeader: true
openwebui-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:3004"
passHostHeader: true
qbittorrent-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8080"
passHostHeader: true
tdarr-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8265"
passHostHeader: true
unmanic-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8888"
passHostHeader: true
wordpress-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8088"
passHostHeader: true
# Arr Services
jellyseerr-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:5055"
passHostHeader: true
prowlarr-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:9696"
passHostHeader: true
radarr-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:7878"
passHostHeader: true
sonarr-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8989"
passHostHeader: true
lidarr-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8686"
passHostHeader: true
readarr-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8787"
passHostHeader: true
mylar3-jarvis:
loadBalancer:
servers:
- url: "http://192.168.4.11:8090"
passHostHeader: true
```
sablier.yml
```yaml
http:
middlewares:
sablier-jarvis-arr:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-arr
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Arr Apps
theme: ghost
show-details-by-default: true
sablier-jarvis-backrest:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-backrest
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Backrest
theme: ghost
show-details-by-default: true
sablier-jarvis-bookstack:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-bookstack
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Bookstack
theme: ghost
show-details-by-default: true
sablier-jarvis-jellyfin:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-jellyfin
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Jellyfin
theme: ghost
show-details-by-default: true
sablier-jarvis-calibre-web:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-calibre-web
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Calibre Web
theme: ghost
show-details-by-default: true
sablier-jarvis-code-server:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-code-server
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Code Server
theme: ghost
show-details-by-default: true
sablier-jarvis-bitwarden:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-bitwarden
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: bitwarden
theme: ghost
show-details-by-default: true
sablier-jarvis-wordpress:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-wordpress
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: wordpress
theme: ghost
show-details-by-default: true
sablier-jarvis-nextcloud:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-nextcloud
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: NextCloud
theme: ghost
show-details-by-default: true
sablier-jarvis-mediawiki:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-mediawiki
sessionDuration: 2m
ignoreUserAgent: curl
dynamic:
displayName: mediawiki
theme: ghost
show-details-by-default: true
sablier-jarvis-mealie:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-mealie
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Mealie
theme: ghost
show-details-by-default: true
sablier-jarvis-gitea:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-gitea
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Gitea
theme: ghost
show-details-by-default: true
sablier-jarvis-formio:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-formio
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: FormIO
theme: ghost
show-details-by-default: true
sablier-jarvis-dozzle:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-dozzle
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: dozzle
theme: ghost
show-details-by-default: true
sablier-jarvis-duplicati:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-duplicati
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Duplicati
theme: ghost
show-details-by-default: true
sablier-jarvis-glances:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-glances
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Glances
theme: ghost
show-details-by-default: true
sablier-jarvis-homarr:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-homarr
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Homarr
theme: ghost
show-details-by-default: true
sablier-jarvis-komodo:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-komodo
sessionDuration: 2m
ignoreUserAgent: curl
dynamic:
displayName: Komodo
theme: ghost
show-details-by-default: true
sablier-jarvis-kopia:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-kopia
sessionDuration: 2m
ignoreUserAgent: curl
dynamic:
displayName: Kopia
theme: ghost
show-details-by-default: true
sablier-jarvis-openkm:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-openkm
sessionDuration: 2m
ignoreUserAgent: curl
dynamic:
displayName: OpenKM
theme: ghost
show-details-by-default: true
sablier-jarvis-openwebui:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: openwebui-jarvis
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: OpenWebUI
theme: ghost
show-details-by-default: true
sablier-jarvis-pulse:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-pulse
sessionDuration: 2m
ignoreUserAgent: curl
dynamic:
displayName: Pulse
theme: ghost
show-details-by-default: true
sablier-jarvis-tdarr:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-tdarr
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Tdarr
theme: ghost
show-details-by-default: true
sablier-jarvis-unmanic:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-unmanic
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: Unmanic
theme: ghost
show-details-by-default: true
sablier-jarvis-dokuwiki:
plugin:
sablier:
sablierUrl: http://sablier-service:10000
group: jarvis-dokuwiki
sessionDuration: 30m
ignoreUserAgent: curl
dynamic:
displayName: DokuWiki
theme: ghost
show-details-by-default: true
authelia:
forwardauth:
address: http://authelia:9091/api/verify?rd=https://auth.kelinreij.duckdns.org/
authResponseHeaders:
- X-Secret
trustForwardHeader: true
```