mirror of
https://github.com/fabro-sh/fabro.git
synced 2026-08-28 05:27:41 +00:00
Add Docker host preflight checks
Some checks are pending
Rust / Format (push) Waiting to run
Rust / Clippy (push) Waiting to run
Rust / Generated Docs (push) Waiting to run
Rust / Test (Linux) (push) Waiting to run
Rust / Test (macOS) (push) Waiting to run
TypeScript / Typecheck (push) Waiting to run
TypeScript / Test (push) Waiting to run
TypeScript / Build (push) Waiting to run
Some checks are pending
Rust / Format (push) Waiting to run
Rust / Clippy (push) Waiting to run
Rust / Generated Docs (push) Waiting to run
Rust / Test (Linux) (push) Waiting to run
Rust / Test (macOS) (push) Waiting to run
TypeScript / Typecheck (push) Waiting to run
TypeScript / Test (push) Waiting to run
TypeScript / Build (push) Waiting to run
This commit is contained in:
parent
ea572495f6
commit
23924eb2b4
1 changed files with 121 additions and 0 deletions
121
docker/preflight.sh
Executable file
121
docker/preflight.sh
Executable file
|
|
@ -0,0 +1,121 @@
|
|||
#!/usr/bin/env bash
|
||||
set -u
|
||||
|
||||
errors=0
|
||||
required_docker_version="${REQUIRED_DOCKER_VERSION:-24.0.0}"
|
||||
required_cores="${REQUIRED_CORES:-2}"
|
||||
required_ram_mb="${REQUIRED_RAM_MB:-4096}"
|
||||
required_disk_gb="${REQUIRED_DISK_GB:-20}"
|
||||
fabro_port="${FABRO_PORT:-32276}"
|
||||
|
||||
fail() {
|
||||
printf 'FAIL: %s\n' "$1"
|
||||
errors=$((errors + 1))
|
||||
}
|
||||
|
||||
ok() {
|
||||
printf 'OK: %s\n' "$1"
|
||||
}
|
||||
|
||||
version_ge() {
|
||||
local minimum="$1"
|
||||
local actual="$2"
|
||||
|
||||
if command -v sort >/dev/null 2>&1 && sort -V </dev/null >/dev/null 2>&1; then
|
||||
printf '%s\n%s\n' "$minimum" "$actual" | sort -V -C
|
||||
else
|
||||
[ "$minimum" = "$actual" ] || [ "$(printf '%s\n%s\n' "$minimum" "$actual" | sort | head -n1)" = "$minimum" ]
|
||||
fi
|
||||
}
|
||||
|
||||
if ! command -v docker >/dev/null 2>&1; then
|
||||
fail "Docker is not installed."
|
||||
else
|
||||
docker_version="$(docker version --format '{{.Client.Version}}' 2>/dev/null || printf '0.0.0')"
|
||||
if version_ge "$required_docker_version" "$docker_version"; then
|
||||
ok "Docker version $docker_version"
|
||||
else
|
||||
fail "Docker version $docker_version is below required minimum $required_docker_version."
|
||||
fi
|
||||
|
||||
if docker compose version >/dev/null 2>&1; then
|
||||
ok "$(docker compose version)"
|
||||
else
|
||||
fail "Docker Compose v2 is not available. Install the Docker Compose plugin."
|
||||
fi
|
||||
|
||||
if docker ps >/dev/null 2>&1; then
|
||||
ok "Docker daemon is accessible"
|
||||
else
|
||||
fail "Current user cannot access the Docker daemon."
|
||||
fi
|
||||
fi
|
||||
|
||||
available_cores="$(nproc 2>/dev/null || sysctl -n hw.ncpu 2>/dev/null || printf '0')"
|
||||
if [ "$available_cores" -lt "$required_cores" ]; then
|
||||
fail "Only $available_cores CPU core(s) available; need at least $required_cores."
|
||||
else
|
||||
ok "$available_cores CPU core(s)"
|
||||
fi
|
||||
|
||||
if [ -f /proc/meminfo ]; then
|
||||
total_ram_mb="$(awk '/MemTotal/ { print int($2 / 1024) }' /proc/meminfo)"
|
||||
elif command -v sysctl >/dev/null 2>&1; then
|
||||
total_ram_bytes="$(sysctl -n hw.memsize 2>/dev/null || printf '0')"
|
||||
total_ram_mb=$((total_ram_bytes / 1024 / 1024))
|
||||
else
|
||||
total_ram_mb=0
|
||||
fi
|
||||
|
||||
if [ "$total_ram_mb" -lt "$required_ram_mb" ]; then
|
||||
fail "Only ${total_ram_mb}MB RAM available; need at least ${required_ram_mb}MB."
|
||||
else
|
||||
ok "${total_ram_mb}MB RAM"
|
||||
fi
|
||||
|
||||
available_kb="$(df -Pk /var/lib/docker 2>/dev/null | awk 'NR == 2 { print $4 }')"
|
||||
if [ -z "$available_kb" ]; then
|
||||
available_kb="$(df -Pk / 2>/dev/null | awk 'NR == 2 { print $4 }')"
|
||||
fi
|
||||
available_gb=$((available_kb / 1024 / 1024))
|
||||
|
||||
if [ "$available_gb" -lt "$required_disk_gb" ]; then
|
||||
fail "Only ${available_gb}GB free disk space; need at least ${required_disk_gb}GB."
|
||||
else
|
||||
ok "${available_gb}GB free disk space"
|
||||
fi
|
||||
|
||||
if command -v ss >/dev/null 2>&1; then
|
||||
if ss -ltn | awk '{ print $4 }' | grep -Eq "[:.]${fabro_port}$"; then
|
||||
fail "Port ${fabro_port} is already in use."
|
||||
else
|
||||
ok "Port ${fabro_port} appears available"
|
||||
fi
|
||||
elif command -v lsof >/dev/null 2>&1; then
|
||||
if lsof -nP -iTCP:"$fabro_port" -sTCP:LISTEN >/dev/null 2>&1; then
|
||||
fail "Port ${fabro_port} is already in use."
|
||||
else
|
||||
ok "Port ${fabro_port} appears available"
|
||||
fi
|
||||
else
|
||||
ok "Skipped port availability check; neither ss nor lsof is installed"
|
||||
fi
|
||||
|
||||
if command -v curl >/dev/null 2>&1; then
|
||||
ghcr_status="$(curl -sS -o /dev/null -w '%{http_code}' --max-time 10 https://ghcr.io/v2/ 2>/dev/null || printf '000')"
|
||||
if [ "$ghcr_status" != "000" ]; then
|
||||
ok "ghcr.io is reachable"
|
||||
else
|
||||
fail "Cannot reach ghcr.io for pulling Fabro images."
|
||||
fi
|
||||
else
|
||||
fail "curl is not installed."
|
||||
fi
|
||||
|
||||
printf '\n'
|
||||
if [ "$errors" -gt 0 ]; then
|
||||
printf 'Pre-flight checks failed with %s error(s). Please fix them before deploying Fabro.\n' "$errors"
|
||||
exit 1
|
||||
fi
|
||||
|
||||
printf 'All Fabro pre-flight checks passed.\n'
|
||||
Loading…
Add table
Reference in a new issue