# ╔══════════════════════════════════════════════════════════════╗
# ║           LibrePortal - Comprehensive Test Template              ║
# ║                Tests All Tagging System Features                  ║
# ╚══════════════════════════════════════════════════════════════╝
#
# ⚠️  AUTOMATICALLY GENERATED - DO NOT EDIT MANUALLY ⚠️
# All configurations are managed by LibrePortal tagging system
#
# 🏷️ TAGGING SYSTEM EXPLANATIONS:
# =====================================
#
# 📋 SERVICE TAGS:
#
# - SERVICE_TAG_N: Identifies services for IP allocation
# - Format: #LIBREPORTAL|SERVICE_TAG_N|service_name
# - Services with IP_DATA_N tags get IP addresses allocated
# - Services without IP_DATA_N are skipped for IP allocation
#
# 🔌 PORT SYSTEM:
#
# - PORT_DATA_N: Port number placeholder (gets replaced with allocated port)
# - PORT_TAG_N: Port tracking tag (gets updated with same port number)
# - Used in: ports section, Traefik config, UFW labels
# - Global replacement: All PORT_DATA_N instances get same port
#
# 🔐 PASSWORD SYSTEM:
#
# - PASSWORD_DATA_N: Password placeholder (gets replaced with generated password)
# - PASSWORD_TAG_N: Password tracking tag (gets updated with same password)
# - Global replacement: All PASSWORD_DATA_N instances get same password
# - Shared passwords: Same PASSWORD_DATA_N used across multiple services
#
# 🌐 IP SYSTEM:
#
# - IP_DATA_N: IP address placeholder (gets replaced with allocated IP)
# - IP_TAG_N: IP tracking tag (gets updated with same IP address)
# - Only services with IP_DATA_N get IP addresses allocated
# - Database tracking: Service-to-IP mappings stored persistently
#
# 📋 STANDARD TAGS:
#
# - TIMEZONE_DATA/TIMEZONE_TAG: Timezone configuration
# - EMAIL_DATA/EMAIL_TAG: Email address configuration
# - CATEGORY_DATA/CATEGORY_TAG: App category for LibrePortal
# - TITLE_DATA/TITLE_TAG: App title for LibrePortal
# - DOMAINSUBNAME_DATA/DOMAINSUBNAME_TAG: Domain for Traefik routing
# - DOMAINNAME_DATA/DOMAINNAME_TAG: Full domain name
# - DOMAINPREFIX_DATA/DOMAINPREFIX_TAG: Domain prefix
# - PUBLICIP_DATA/PUBLICIP_TAG: Public IP address
# - SUBNET_DATA/SUBNET_TAG: Network subnet
# - GATEWAY_DATA/GATEWAY_TAG: Network gateway
# - DOCKERNETWORK_DATA/DOCKERNETWORK_TAG: Docker network name
# - MTU_DATA/MTU_TAG: Network MTU setting
#
# 🚦 TRAEFIK CONTROL:
#
# - TRAEFIK_ENABLE_DATA/TRAEFIK_ENABLE_TAG: Enable/disable Traefik
# - When false: All Traefik labels are ignored but remain valid
# - When true: Traefik processes all routing and SSL configuration
#
# ⚕️ HEALTHCHECK:
#
# - HEALTHCHECK_DATA/HEALTHCHECK_TAG: Enable/disable healthchecks
# - true: Healthcheck disabled, false: Healthcheck enabled
#
# 🔧 DOCKER INSTALLATION:
#
# - SOCKET_TAG/SOCKET_DATA: Docker socket path for rootless/rooted
# - UID_TAG/GID_TAG: User ID for rootless Docker installation
# - DOCKERINSTALLUSER_TAG: Docker installation user tracking
#
# 🌐 PORT BINDING:
#
# - PORT_BINDING tag: Controls 0.0.0.0 vs 127.0.0.1 binding
# - Private apps: 127.0.0.1 (localhost only)
# - Public apps: 0.0.0.0 (accessible externally)
#
# 🎯 EXAMPLES IN THIS TEMPLATE:
# ==========================
#
# 🔌 PORT USAGE:
#
# - PORT_DATA_1 used in 3 places: ports section, Traefik loadbalancer, UFW labels
# - All instances get replaced with same allocated port (e.g., 3123)
#
# 🔐 PASSWORD SHARING:
#
# - PASSWORD_DATA_1: Shared between webapp (ADMIN_PASSWORD) and worker (ADMIN_PASSWORD)
# - PASSWORD_DATA_2: Shared between webapp (DB_PASSWORD), database (POSTGRES_PASSWORD), worker (DB_PASSWORD)
# - PASSWORD_DATA_3: Shared between webapp (API_KEY) and redis (REDIS_PASSWORD)
#
# 🌐 IP ALLOCATION:
#
# - SERVICE_TAG_1 (webapp) → IP_DATA_1 → Gets IP allocated
# - SERVICE_TAG_2 (database) → IP_DATA_2 → Gets IP allocated  
# - SERVICE_TAG_3 (redis) → IP_DATA_3 → Gets IP allocated
# - SERVICE_TAG_4 (worker) → No IP_DATA_N → No IP allocated (internal only)
#
# 🚦 TRAEFIK INTEGRATION:
#
# - TRAEFIK_ENABLE_DATA controls if webapp is accessible via domain
# - Domain routing uses DOMAINSUBNAME_DATA for SSL certificate
# - Load balancer uses PORT_DATA_1 for internal port mapping

networks:
  vpn:
    external: true

services:
  # Main web application service
  # SERVICE_TAG_1: This service needs IP allocation (has IP_DATA_1)
  webapp: #LIBREPORTAL|SERVICE_TAG_1|webapp
    container_name: test-webapp
    image: nginx:alpine
    ports:
      # PORT_EXTERNAL_1: External port mapping (gets allocated port like 3123)
      # Used in 3 places: here, Traefik loadbalancer, UFW labels
      - "PORT_DATA_1:3000" #LIBREPORTAL|PORT_TAG_1|PORT_DATA_1
    volumes:
      - ./data:/app/data
      - ./config:/app/config:ro
    env_file:
      - .env
    environment:
      # Standard LibrePortal configuration tags
      TZ: TIMEZONE_DATA #LIBREPORTAL|TIMEZONE_TAG|TIMEZONE_DATA
      EMAIL: EMAIL_DATA #LIBREPORTAL|EMAIL_TAG|EMAIL_DATA
      
      # Password placeholders for testing
      # PASSWORD_DATA_1: Shared with worker service (same password everywhere)
      ADMIN_PASSWORD: PASSWORD_DATA_1 #LIBREPORTAL|PASSWORD_TAG_1|PASSWORD_DATA_1
      # PASSWORD_DATA_2: Shared with database and worker services
      DB_PASSWORD: PASSWORD_DATA_2 #LIBREPORTAL|PASSWORD_TAG_2|PASSWORD_DATA_2
      # PASSWORD_DATA_3: Shared with redis service
      API_KEY: PASSWORD_DATA_3 #LIBREPORTAL|PASSWORD_TAG_3|PASSWORD_DATA_3
      
      # Application configuration
      APP_NAME: "Test Application"
      DEBUG: "true"
      LOG_LEVEL: "info"
    labels:
      # LibrePortal application metadata
      libreportal.category: "CATEGORY_DATA" #LIBREPORTAL|CATEGORY_TAG|CATEGORY_DATA
      libreportal.title: "TITLE_DATA" #LIBREPORTAL|TITLE_TAG|TITLE_DATA
      # UFW integration uses same port as external mapping
      libreportal.ufw-ports: "UFW_PORT_DATA_1" #LIBREPORTAL|UFW_PORTS_TAG|UFW_PORT_DATA_1
      libreportal.description: "Comprehensive test template for LibrePortal tagging system"
      
      # Traefik reverse proxy configuration
      # TRAEFIK_ENABLE_DATA: Controls if this app is accessible via domain
      traefik.enable: TRAEFIK_ENABLE_DATA #LIBREPORTAL|TRAEFIK_ENABLE_TAG|TRAEFIK_ENABLE_DATA
      traefik.http.routers.webapp.entrypoints: web,websecure
      # DOMAINSUBNAME_DATA: Domain name for SSL certificate and routing
      traefik.http.routers.webapp.rule: Host(`DOMAINSUBNAME_DATA`) #LIBREPORTAL|DOMAINSUBNAME_TAG|DOMAINSUBNAME_DATA
      traefik.http.routers.webapp.tls: true
      traefik.http.routers.webapp.tls.certresolver: production
      # PORT_DATA_1: Internal port for Traefik load balancer (same as external)
      traefik.http.services.webapp.loadbalancer.server.port: 3000
      traefik.http.routers.webapp.middlewares:
      # DOCKERNETWORK_DATA: Docker network for Traefik communication
      traefik.docker.network: DOCKERNETWORK_DATA #LIBREPORTAL|DOCKERNETWORK_TAG|DOCKERNETWORK_DATA
    healthcheck:
      # HEALTHCHECK_DATA: Enable/disable healthcheck (true=disabled, false=enabled)
      disable: HEALTHCHECK_DATA #LIBREPORTAL|HEALTHCHECK_TAG|HEALTHCHECK_DATA
    networks:
      vpn:
        # IP_DATA_1: This service gets IP address allocated
        ipv4_address: IP_DATA_1 #LIBREPORTAL|IP_TAG_1|IP_DATA_1

  # Database service (no external ports, only internal communication)
  # SERVICE_TAG_2: This service needs IP allocation (has IP_DATA_2)
  database: #LIBREPORTAL|SERVICE_TAG_2|database
    container_name: test-database
    image: postgres:13
    ports:
      # No external port mapping - internal only communication
    volumes:
      - ./db_data:/var/lib/postgresql/data
    environment:
      # Database configuration
      POSTGRES_DB: testdb
      POSTGRES_USER: admin
      # PASSWORD_DATA_2: Same password as webapp DB_PASSWORD and worker DB_PASSWORD
      POSTGRES_PASSWORD: PASSWORD_DATA_2 #LIBREPORTAL|PASSWORD_TAG_2|PASSWORD_DATA_2
      # TIMEZONE_DATA: Same timezone as all other services
      TZ: TIMEZONE_DATA #LIBREPORTAL|TIMEZONE_TAG|TIMEZONE_DATA
    labels:
      libreportal.category: "database"
      libreportal.description: "PostgreSQL database service"
      libreportal.internal: "true"
    healthcheck:
      disable: false
    networks:
      vpn:
        # IP_DATA_2: This service gets IP address allocated
        ipv4_address: IP_DATA_2 #LIBREPORTAL|IP_TAG_2|IP_DATA_2

  # Redis cache service (no external ports, internal only)
  # SERVICE_TAG_3: This service needs IP allocation (has IP_DATA_3)
  redis: #LIBREPORTAL|SERVICE_TAG_3|redis
    container_name: test-redis
    image: redis:alpine
    ports:
      # No external port mapping - internal only communication
    volumes:
      - ./redis_data:/data
    environment:
      # Redis configuration
      # PASSWORD_DATA_3: Same password as webapp API_KEY
      REDIS_PASSWORD: PASSWORD_DATA_3 #LIBREPORTAL|PASSWORD_TAG_3|PASSWORD_DATA_3
      # TIMEZONE_DATA: Same timezone as all other services
      TZ: TIMEZONE_DATA #LIBREPORTAL|TIMEZONE_TAG|TIMEZONE_DATA
    # Redis uses environment variable for password
    command: redis-server --requirepass $REDIS_PASSWORD
    labels:
      libreportal.category: "cache"
      libreportal.description: "Redis cache service"
      libreportal.internal: "true"
    healthcheck:
      disable: false
    networks:
      vpn:
        # IP_DATA_3: This service gets IP address allocated
        ipv4_address: IP_DATA_3 #LIBREPORTAL|IP_TAG_3|IP_DATA_3

  # Background worker service (no IP needed, internal processing only)
  # SERVICE_TAG_4: This service does NOT need IP allocation (no IP_DATA_N)
  worker: #LIBREPORTAL|SERVICE_TAG_4|worker
    container_name: test-worker
    image: python:alpine
    volumes:
      - ./worker:/app
    environment:
      # Worker configuration with shared passwords
      # PASSWORD_DATA_1: Same password as webapp ADMIN_PASSWORD
      ADMIN_PASSWORD: PASSWORD_DATA_1 #LIBREPORTAL|PASSWORD_TAG_1|PASSWORD_DATA_1
      # PASSWORD_DATA_2: Same password as webapp DB_PASSWORD and database POSTGRES_PASSWORD
      DB_PASSWORD: PASSWORD_DATA_2 #LIBREPORTAL|PASSWORD_TAG_2|PASSWORD_DATA_2
      # TIMEZONE_DATA: Same timezone as all other services
      TZ: TIMEZONE_DATA #LIBREPORTAL|TIMEZONE_TAG|TIMEZONE_DATA
    command: python /app/worker.py
    labels:
      libreportal.category: "worker"
      libreportal.description: "Background worker service"
      libreportal.internal: "true"
    networks:
      vpn:
        # No IP allocation for worker service (internal only, no IP_DATA_N)