Add homelab dependency map command
This commit is contained in:
parent
41498150ea
commit
7efa7a0452
|
|
@ -275,6 +275,7 @@ Run a read-only health snapshot from the Debian server with:
|
|||
./jeannie gitops-status
|
||||
./jeannie cert-check
|
||||
./jeannie release-snapshot
|
||||
./jeannie map
|
||||
```
|
||||
|
||||
It reports host memory/disk, systemd services, Docker Compose stacks,
|
||||
|
|
@ -314,6 +315,10 @@ HTTP status, and DuckDNS-to-OCI edge IP drift from the canonical inventory.
|
|||
state directory with Git state, Kubernetes/Argo CD/Helm state, workload images,
|
||||
public URL status, and pointers to the latest Gitea/OpenTofu backups.
|
||||
|
||||
`map` prints a dependency map from the canonical inventory, covering public
|
||||
entry, GitOps automation, cluster foundation, DNS, observability, and security
|
||||
learning paths. `./jeannie map --dot` emits Graphviz DOT.
|
||||
|
||||
Focused doctor commands run narrower read-only checks and print the most likely
|
||||
next step:
|
||||
|
||||
|
|
|
|||
|
|
@ -275,6 +275,7 @@ Run a read-only health snapshot from the Debian server with:
|
|||
./{{ main_script }} gitops-status
|
||||
./{{ main_script }} cert-check
|
||||
./{{ main_script }} release-snapshot
|
||||
./{{ main_script }} map
|
||||
```
|
||||
|
||||
It reports host memory/disk, systemd services, Docker Compose stacks,
|
||||
|
|
@ -314,6 +315,10 @@ HTTP status, and DuckDNS-to-OCI edge IP drift from the canonical inventory.
|
|||
state directory with Git state, Kubernetes/Argo CD/Helm state, workload images,
|
||||
public URL status, and pointers to the latest Gitea/OpenTofu backups.
|
||||
|
||||
`map` prints a dependency map from the canonical inventory, covering public
|
||||
entry, GitOps automation, cluster foundation, DNS, observability, and security
|
||||
learning paths. `./{{ main_script }} map --dot` emits Graphviz DOT.
|
||||
|
||||
Focused doctor commands run narrower read-only checks and print the most likely
|
||||
next step:
|
||||
|
||||
|
|
|
|||
|
|
@ -76,6 +76,10 @@ and DuckDNS-to-OCI edge IP drift from the canonical inventory.
|
|||
state, workload images, public URL status, and latest Gitea/OpenTofu backup
|
||||
pointers.
|
||||
|
||||
`map`
|
||||
: Print a dependency map from the canonical inventory. Use `map --dot` for a
|
||||
Graphviz DOT graph.
|
||||
|
||||
Prometheus alerts
|
||||
: High-signal alert rules are managed as the `apps/homelab-alerts` GitOps app.
|
||||
They cover node readiness, restart storms, unavailable deployments, storage
|
||||
|
|
|
|||
9
jeannie
9
jeannie
|
|
@ -5986,6 +5986,10 @@ release_snapshot() {
|
|||
"${REPO_ROOT}/scripts/release-snapshot"
|
||||
}
|
||||
|
||||
homelab_map() {
|
||||
"${REPO_ROOT}/scripts/homelab-map" "${@:2}"
|
||||
}
|
||||
|
||||
case "${1:-}" in
|
||||
up)
|
||||
up
|
||||
|
|
@ -6020,6 +6024,9 @@ case "${1:-}" in
|
|||
release-snapshot)
|
||||
release_snapshot
|
||||
;;
|
||||
map)
|
||||
homelab_map "$@"
|
||||
;;
|
||||
validate)
|
||||
validate_homelab
|
||||
;;
|
||||
|
|
@ -6164,7 +6171,7 @@ case "${1:-}" in
|
|||
echo "Log: ${JEANNIE_LOG_FILE}"
|
||||
;;
|
||||
*)
|
||||
echo "Usage: $0 {up|plan [all|provisioning|cluster|platform|apps|edge]|rebuild-cluster|stop-cluster|start-cluster|status|capacity|recover-plan|gitops-status|cert-check|release-snapshot|validate|access-audit|kubeconfig-readonly|apps|website-translation-model|website-ollama-listen|ollama-setup|deploy-gitea|rpi-services|bootstrap-gitea-repo|backup-gitea|drill-restore|drill-gitea-restore|drill-pihole-restore|install-gitea-runner|move-prometheus-stack-workers|doctor-versions|doctor-edge|doctor-gitea|doctor-rpi|doctor-cluster|preflight|doctor-preapply|inventory-check|state-backup|fix-debian-docker-root|secrets-init|secrets-check|tailnet-policy-check|ai-index|ai-check|security-scan|security-prepare|security-zap|security-k8s|security-host|security-trivy|security-secrets|security-nuclei|security-web|security-logs|security-runtime|security-attack-path|openwrt|nuke}"
|
||||
echo "Usage: $0 {up|plan [all|provisioning|cluster|platform|apps|edge]|rebuild-cluster|stop-cluster|start-cluster|status|capacity|recover-plan|gitops-status|cert-check|release-snapshot|map [--dot]|validate|access-audit|kubeconfig-readonly|apps|website-translation-model|website-ollama-listen|ollama-setup|deploy-gitea|rpi-services|bootstrap-gitea-repo|backup-gitea|drill-restore|drill-gitea-restore|drill-pihole-restore|install-gitea-runner|move-prometheus-stack-workers|doctor-versions|doctor-edge|doctor-gitea|doctor-rpi|doctor-cluster|preflight|doctor-preapply|inventory-check|state-backup|fix-debian-docker-root|secrets-init|secrets-check|tailnet-policy-check|ai-index|ai-check|security-scan|security-prepare|security-zap|security-k8s|security-host|security-trivy|security-secrets|security-nuclei|security-web|security-logs|security-runtime|security-attack-path|openwrt|nuke}"
|
||||
exit 1
|
||||
;;
|
||||
esac
|
||||
|
|
|
|||
|
|
@ -0,0 +1,132 @@
|
|||
#!/usr/bin/env bash
|
||||
set -euo pipefail
|
||||
|
||||
REPO_ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
|
||||
INVENTORY_FILE="${HOMELAB_INVENTORY_FILE:-${REPO_ROOT}/homelab.yml}"
|
||||
FORMAT="${1:-text}"
|
||||
|
||||
inventory() {
|
||||
local path="$1"
|
||||
local fallback="$2"
|
||||
|
||||
if command -v ruby >/dev/null 2>&1 && [ -f "$INVENTORY_FILE" ]; then
|
||||
value="$(
|
||||
ruby -ryaml -e '
|
||||
data = YAML.load_file(ARGV[0])
|
||||
value = ARGV[1].split(".").reduce(data) { |memo, key| memo.respond_to?(:[]) ? memo[key] : nil }
|
||||
puts value if value.is_a?(String) || value.is_a?(Integer)
|
||||
' "$INVENTORY_FILE" "$path" 2>/dev/null || true
|
||||
)"
|
||||
if [ -n "$value" ]; then
|
||||
printf '%s\n' "$value"
|
||||
return 0
|
||||
fi
|
||||
fi
|
||||
|
||||
printf '%s\n' "$fallback"
|
||||
}
|
||||
|
||||
domain="$(inventory domain.base lab2025.duckdns.org)"
|
||||
debian="$(inventory hosts.debian.lan_ip 192.168.100.73)"
|
||||
debian_ts="$(inventory hosts.debian.tailscale_ip 100.85.138.30)"
|
||||
rpi="$(inventory hosts.rpi4.lan_ip 192.168.100.89)"
|
||||
oci="$(inventory hosts.oci_edge.public_ip 132.145.170.74)"
|
||||
oci_ts="$(inventory hosts.oci_edge.tailscale_ip 100.118.255.19)"
|
||||
pimox="$(inventory hosts.opi5_pimox.lan_ip 192.168.100.80)"
|
||||
traefik="$(inventory network.metallb.traefik_ip 192.168.100.240)"
|
||||
registry="$(inventory services.local_registry.endpoint 192.168.100.73:30500)"
|
||||
gitea_http="$(inventory services.gitea.http_port 3000)"
|
||||
gitea_ssh="$(inventory services.gitea.ssh_port 32222)"
|
||||
pihole_web="$(inventory services.rpi_dns.pihole_web_port 8081)"
|
||||
kuma="$(inventory services.rpi_dns.uptime_kuma_port 3001)"
|
||||
|
||||
if [ "$FORMAT" = "--dot" ] || [ "$FORMAT" = "dot" ]; then
|
||||
cat <<EOF
|
||||
digraph homelab {
|
||||
rankdir=LR;
|
||||
"Internet" -> "OCI edge ${oci}";
|
||||
"OCI edge ${oci}" -> "Traefik ${traefik}";
|
||||
"OCI edge ${oci}" -> "Debian Tailscale ${debian_ts}";
|
||||
"Debian ${debian}" -> "Gitea :${gitea_http}/git";
|
||||
"Debian ${debian}" -> "Local registry ${registry}";
|
||||
"Debian ${debian}" -> "Kubernetes control plane";
|
||||
"Debian ${debian}" -> "Pimox ${pimox}";
|
||||
"Pimox ${pimox}" -> "Worker VMs";
|
||||
"Worker VMs" -> "Kubernetes apps";
|
||||
"Kubernetes apps" -> "Traefik ${traefik}";
|
||||
"Gitea :${gitea_http}/git" -> "Argo CD";
|
||||
"Argo CD" -> "Kubernetes apps";
|
||||
"Clients" -> "Pi-hole ${rpi}:53";
|
||||
"Pi-hole ${rpi}:53" -> "Unbound";
|
||||
"Pi-hole ${rpi}:53" -> "Public DNS fallback";
|
||||
"Uptime Kuma ${rpi}:${kuma}" -> "Public URLs";
|
||||
"Uptime Kuma ${rpi}:${kuma}" -> "LAN services";
|
||||
}
|
||||
EOF
|
||||
exit 0
|
||||
fi
|
||||
|
||||
cat <<EOF
|
||||
Homelab dependency map
|
||||
======================
|
||||
|
||||
Public entry
|
||||
Internet
|
||||
-> ${domain}
|
||||
-> OCI edge ${oci} / tailscale ${oci_ts}
|
||||
-> Traefik LoadBalancer ${traefik}
|
||||
-> Kubernetes ingress routes
|
||||
-> website, demos, Heimdall, observability, Argo CD, arr routes
|
||||
|
||||
Git and automation
|
||||
Debian ${debian}
|
||||
-> Gitea HTTP :${gitea_http}/git and SSH :${gitea_ssh}
|
||||
-> Gitea Actions runner
|
||||
-> local registry ${registry}
|
||||
-> jeannie orchestration
|
||||
Gitea repository
|
||||
-> Argo CD applications
|
||||
-> Kubernetes manifests under apps/
|
||||
-> edge/provisioning/cluster/platform Terraform stacks
|
||||
|
||||
Cluster foundation
|
||||
Debian ${debian}
|
||||
-> kubeadm control plane
|
||||
-> container registry
|
||||
-> provisioning HTTP/TFTP
|
||||
Orange Pi Pimox ${pimox}
|
||||
-> worker VM template
|
||||
-> worker VM clones
|
||||
-> Kubernetes worker capacity
|
||||
|
||||
DNS and always-on health
|
||||
Clients and lab hosts
|
||||
-> RPi4 Pi-hole ${rpi}:53
|
||||
-> Unbound resolver
|
||||
-> public fallback DNS if Unbound is unhealthy
|
||||
RPi4
|
||||
-> Pi-hole web ${rpi}:${pihole_web}
|
||||
-> Uptime Kuma ${rpi}:${kuma}
|
||||
-> monitors public URLs, LAN services, DNS, Traefik, Gitea, arr
|
||||
|
||||
Observability and operations
|
||||
Prometheus stack
|
||||
-> nodes, pods, Traefik, website probes, Gitea/Pi-hole scrape coverage
|
||||
-> homelab-alerts
|
||||
-> Grafana dashboards
|
||||
jeannie status
|
||||
-> host/bootstrap checks
|
||||
-> local services
|
||||
-> RPi DNS and Kuma
|
||||
-> Pimox and Kubernetes
|
||||
-> platform/apps
|
||||
-> edge/public URLs
|
||||
|
||||
Security learning loop
|
||||
security-lab namespace
|
||||
-> isolated OWASP practice targets
|
||||
-> ZAP/nuclei/trivy/lynis helper commands
|
||||
-> report-only findings before manual fixes
|
||||
|
||||
Use './jeannie map --dot' to emit a Graphviz DOT version.
|
||||
EOF
|
||||
Loading…
Reference in New Issue