Overview
AdventureTube runs on a 3-node Raspberry Pi cluster with Nginx reverse proxy, Jenkins CI/CD, and domain-based access via *.adventuretube.net.
Pi Cluster
Pi1 — 192.168.1.199 (Storage + Monitoring + Tooling)
Databases: Kafka + Zookeeper, PostgreSQL + pgAdmin, MongoDB + mongo-express
Monitoring: Zipkin (:9411), Grafana (:3000), Prometheus, cAdvisor, node_exporter, kafka-exporter
Tooling: Jenkins master (:8443), Nginx Proxy Manager (:81), n8n (:5678), WordPress, Whisper AI (:8000), Portainer (:9443)
Pi2 — 192.168.1.105 (Spring Cloud + Build Agent)
Spring Cloud: Config (:9297), Eureka (:8761), Gateway (:8030)
Build: jenkins-agent2 (shares Docker runtime — builds deploy here)
Other: Whisper AI (:8000), Portainer, cAdvisor, node_exporter
Pi3 — 192.168.1.141 (Additional Services)
Portainer, YouTube service (:3010), jenkins-agent3
In production: business services run on 192.168.1.102 (geospatial:8060, member:8070, web:8040)
Deployment Modes
Development (Mac + Pi)
Pi1: databases + Kafka + monitoring
Pi2: Eureka + Config + Gateway (Docker)
Mac (IntelliJ): auth, member, geospatial, web services (Java runtime)
→ Services register to Eureka on Pi2, connect to DBs/Kafka on Pi1
→ Access: localhost:{port} or gateway at 192.168.1.105:8030
Production (Pi cluster only)
Client → Gateway (Pi2:8030) → Business Services (Pi2 Docker) → DBs/Kafka (Pi1)
Dual-instance mode
After Jenkins deploy, Eureka may show 2 instances per service (Mac + Pi2 Docker). Gateway load-balances between them.
CI/CD Pipeline
Flow
Mac → git push → GitHub (strider73) → Jenkins webhook
→ jenkins-agent2 (Pi2) pulls code
→ reads env.pi/env.pi2 from Jenkins Credential Store
→ Dockerfile.pi builds image (bakes env files into image)
→ docker-compose deploys new containers on Pi2
Jenkins Jobs
| Job | Agent | What it deploys |
|---|---|---|
| adventuretube-clouds | agent2 (Pi2) | Spring Cloud services → Pi2 |
| adventuretube-microservice | agent2 (Pi2) | Business services → Pi2 |
| GarminConnector-Yehwan | agent3 (Pi3) | Garmin integration → Pi3 |
Jenkins Agents
| Agent | Host | Status |
|---|---|---|
| jenkins-agent | Pi1 | Offline |
| jenkins-agent2 | Pi2 | Active (2 executors) |
| jenkins-agent3 | Pi3 | Active (1 executor) |
Env File Flow (Important)
- Env files (
env.pi,env.pi2) come from Jenkins Credential Store (NOT GitHub) Dockerfile.pi COPY env.pi env.pi2 ./bakes them into the Docker imageDotenvEnvironmentPostProcessorreadsENV_TARGETat runtime to pick the right file- To update env vars: Jenkins → Credentials → Replace → upload new file → rebuild
Domain Names
All via Nginx Proxy Manager on Pi1, SSL with Let’s Encrypt.
Core
| Domain | Target | Purpose |
|---|---|---|
| adventuretube.net | Pi1:8020 | Main site |
| api.adventuretube.net | Pi2:8030 | API Gateway |
| gateway.adventuretube.net | Pi2:8030 | Gateway (alias) |
| eureka.adventuretube.net | Pi2:8761 | Service discovery UI |
| config.adventuretube.net | Pi2:9297 | Config server |
Monitoring & Admin
| Domain | Target | Purpose |
|---|---|---|
| grafana.adventuretube.net | Pi1:3000 | Dashboards |
| zipkin.adventuretube.net | Pi1:9411 | Distributed tracing |
| pgadmin.adventuretube.net | Pi1:5050 | PostgreSQL admin |
| jenkins.adventuretube.net | Pi1:8443 | CI/CD |
| portainer.adventuretube.net | Pi1:9443 | Docker mgmt (Pi1) |
| portainer2.adventuretube.net | Pi2:9443 | Docker mgmt (Pi2) |
| portainer3.adventuretube.net | Pi3:9443 | Docker mgmt (Pi3) |
Other
| Domain | Target | Purpose |
|---|---|---|
| n8n.adventuretube.net | Pi1:5678 | Workflow automation |
| whisper.adventuretube.net | Pi1:8000 | Whisper AI |
| whisper2.adventuretube.net | Pi2:8000 | Whisper AI (2nd) |
| youtube.adventuretube.net | Pi3:3010 | YouTube service |
| home.adventuretube.net | Pi2:8123 | Home dashboard |
Network Diagram
Internet
│
Nginx Proxy Manager (Pi1:81)
*.adventuretube.net (SSL)
│
┌──────────────┼──────────────┐
│ │ │
Pi1 (199) Pi2 (105) Pi3 (141)
Storage & Spring Cloud Additional
Monitoring + Build Agent Services
│ │
Kafka, PG, Eureka, Config,
Mongo, Zipkin Gateway, Business
Grafana, etc Services (Docker)
