Skip to main content

Docker

Building a Safe Auto-Update System for Docker After a 2 AM Outage

The 2 AM Wake-Up Call # I woke up to find my CI/CD platform had been down for 8 hours. Semaphore, the Ansible automation engine that manages my entire homelab, was stuck in a crash loop: 1 2 3 /usr/local/bin/server-wrapper: line 295: syntax error: unexpected "&&" /usr/local/bin/server-wrapper: line 295: syntax error: unexpected "&&" /usr/local/bin/server-wrapper: line 295: syntax error: unexpected "&&" The same error, repeating every few seconds. The container would start, hit the broken entrypoint script, crash, and restart. Endlessly.

Architecture: Prometheus + Grafana on a Dedicated LXC

Overview # Migrated the Prometheus + Grafana monitoring stack from a shared Docker VM to a dedicated LXC container. The shared VM hosted multiple stacks (pgAdmin, Portainer, monitoring) which created resource contention and made lifecycle management messy. Moving monitoring to its own LXC follows the homelab pattern of one service per container for cleaner isolation, backups, and management.

Building a Homelab XDR: Wazuh, Graylog, and Monitoring AI Agents

Why an XDR in a Homelab? # When I first started building out my homelab infrastructure, I fell into the same trap that catches most homelab enthusiasts: I assumed that being behind a firewall made me safe. After all, I wasn’t running a Fortune 500 network. I had VLANs, I had a next-generation firewall doing deep packet inspection, and I kept my systems patched. What more did I need?

Lesson Learned: Why I Replaced Watchtower with WUD Across My Homelab

The Problem # Watchtower had been my go-to for automatic Docker container updates across 8+ services. It worked… mostly. But I kept running into issues: Opt-out model is dangerous - Watchtower watches ALL containers by default. I had to remember to add com.centurylinklabs.watchtower.enable=false to containers I didn’t want updated. Forgetting meant surprise updates. No visibility - Updates happened silently at 4 AM. I only knew something updated when it broke. No dashboard, no easy way to see pending updates.

Deploying Wazuh XDR with Graylog Integration

The Challenge # I needed a unified security monitoring solution that could: Provide endpoint detection and response (XDR) capabilities Integrate with my existing Graylog centralized logging infrastructure Scale from a single-node deployment to multi-node if needed Work with my existing OpenClaw threat intelligence feeds The Solution # Wazuh Single-Node Stack # Deployed Wazuh as a Docker-based single-node stack. The single-node architecture includes:

Graylog JVM Heap Optimization

·113 words
What Changed # Pinned Graylog’s JVM heap to 1GB by adding explicit GRAYLOG_SERVER_JAVA_OPTS to docker-compose.yml: 1 GRAYLOG_SERVER_JAVA_OPTS: "-Xms1g -Xmx1g -XX:NewRatio=1 -server -XX:+UseG1GC" Why # Noticed high memory usage on the Graylog VM. JVM ergonomics was auto-allocating ~2GB for Graylog, leaving insufficient RAM for OS filesystem cache. OpenSearch query performance suffers without cache headroom.

Graylog Upgrade to 7.0.3 + MongoDB 7.0

·108 words
What Changed # Upgraded the Graylog logging stack: Graylog: 6.x → 7.0.3 MongoDB: 6.x → 7.0 Why # Graylog 7 brings improved dashboard performance, better pipeline rule debugging, and updated API. MongoDB 7.0 is the new LTS release with better aggregation performance. Details # Service: Graylog (Log-Server VM) Method: Updated version tags in docker-compose.yml, deployed via Portainer Downtime: ~5 minutes during container recreation Key changes in Graylog 7:

Watchtower Discord Embed Notifications

What Changed # Upgraded Watchtower notifications from plain text to Discord embeds using Shoutrrr URL parameters: Added colored sidebar (green for updates) Suppressed noisy startup messages Cleaner, more readable notifications Why # Plain text Watchtower notifications were hard to scan in busy Discord channels. Embeds provide visual structure and color-coding.