feat(docs): add Coolify deployment guide and integrate into setup documentation
feat(scripts): add environment verification scripts for deployment checks
This commit is contained in:
1 parent
474da7418e
commit
9f60087a4c
4 files changed
+574
No files matched your search
@@ -0,0 +1,137 @@
|
||||
#!/usr/bin/env pwsh
|
||||
# check-env.ps1 — Verify the deployment environment for Linear Void.
|
||||
#
|
||||
# Checks, against the target Docker host (default test lab 192.168.88.40):
|
||||
# 1. Docker Engine reachability over the TCP socket (port 2375).
|
||||
# 2. Coolify helper stack (proxy/Traefik, sentinel, cloudflared).
|
||||
# 3. Linear Void containers (playout, chat, nginx, redis, db, prometheus, grafana).
|
||||
# 4. Public endpoints (app, HLS manifest, admin).
|
||||
# 5. Health endpoints exposed by the services.
|
||||
#
|
||||
# Usage:
|
||||
# ./scripts/check-env.ps1
|
||||
# ./scripts/check-env.ps1 -Target 192.168.88.40
|
||||
# ./scripts/check-env.ps1 -Target 192.168.88.40 -DockerPort 2375 -OnlyContainers
|
||||
#
|
||||
# Exit code is 0 when all required checks pass, 1 otherwise.
|
||||
|
||||
param(
|
||||
[string]$Target = '192.168.88.40',
|
||||
[int]$DockerPort = 2375,
|
||||
[switch]$OnlyContainers,
|
||||
[switch]$OnlyEndpoints,
|
||||
[int]$TimeoutSec = 10
|
||||
)
|
||||
|
||||
$ErrorActionPreference = 'Stop'
|
||||
$target = $Target
|
||||
$dockerHost = "tcp://${target}:${DockerPort}"
|
||||
|
||||
$failed = $false
|
||||
function Fail([string]$msg) { Write-Host " [FAIL] $msg" -ForegroundColor Red; $script:failed = $true }
|
||||
function Ok([string]$msg) { Write-Host " [OK] $msg" -ForegroundColor Green }
|
||||
function Warn([string]$msg) { Write-Host " [WARN] $msg" -ForegroundColor Yellow }
|
||||
|
||||
Write-Host "== Linear Void environment check ==" -ForegroundColor Cyan
|
||||
Write-Host "Target Docker host : $dockerHost"
|
||||
Write-Host ("Date : " + (Get-Date -Format s))
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# 1. Docker Engine reachability
|
||||
# ---------------------------------------------------------------------------
|
||||
if (-not $OnlyEndpoints) {
|
||||
Write-Host "`n-- Docker Engine (${target}:${DockerPort}) --" -ForegroundColor Cyan
|
||||
$env:DOCKER_HOST = $dockerHost
|
||||
try {
|
||||
$ver = docker version --format '{{.Server.Version}}' 2>&1
|
||||
if ($LASTEXITCODE -eq 0 -and $ver -match '\d') {
|
||||
Ok "Docker Engine reachable (server version $ver)"
|
||||
} else {
|
||||
Fail "Docker Engine not reachable: $($ver -join ' ')"
|
||||
}
|
||||
} catch {
|
||||
Fail "Docker Engine error: $($_.Exception.Message)"
|
||||
}
|
||||
|
||||
# -----------------------------------------------------------------------
|
||||
# 2. Coolify helper stack
|
||||
# -----------------------------------------------------------------------
|
||||
Write-Host "`n-- Coolify managed-server helpers --" -ForegroundColor Cyan
|
||||
foreach ($c in @('coolify-proxy', 'coolify-sentinel', 'coolify-cloudflared')) {
|
||||
try {
|
||||
$state = docker inspect $c --format '{{.State.Status}} ({{.State.Health.Status}})' 2>&1
|
||||
if ($LASTEXITCODE -eq 0) {
|
||||
if ($state -match 'running.*(healthy|^running \(running\))') { Ok "coolify helper: $c -> $state" }
|
||||
else { Warn "coolify helper: $c -> $state" }
|
||||
} else {
|
||||
Warn "coolify helper: $c -> NOT FOUND (is this a Coolify-managed server?)"
|
||||
}
|
||||
} catch { Warn "coolify helper: $c -> error $($_.Exception.Message)" }
|
||||
}
|
||||
|
||||
# -----------------------------------------------------------------------
|
||||
# 3. Linear Void containers
|
||||
# -----------------------------------------------------------------------
|
||||
Write-Host "`n-- Linear Void containers --" -ForegroundColor Cyan
|
||||
$required = @('linearvoid-playout', 'linearvoid-chat', 'linearvoid-nginx',
|
||||
'linearvoid-redis', 'linearvoid-db', 'linearvoid-prometheus', 'linearvoid-grafana')
|
||||
try {
|
||||
$running = @(docker ps --format '{{.Names}}' 2>&1)
|
||||
$all = @(docker ps -a --format '{{.Names}}\t{{.Status}}' 2>&1)
|
||||
foreach ($name in $required) {
|
||||
if ($running -contains $name) {
|
||||
Ok "container: $name is running"
|
||||
} elseif (($all | Where-Object { $_ -match "^$name\s" })) {
|
||||
$status = ($all | Where-Object { $_ -match "^$name\s" } | Select-Object -First 1)
|
||||
Fail "container: $name EXISTS but not running -> $status"
|
||||
} else {
|
||||
Fail "container: $name MISSING"
|
||||
}
|
||||
}
|
||||
} catch { Fail "container listing error: $($_.Exception.Message)" }
|
||||
}
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
# 4. Health endpoints (via Docker host)
|
||||
# ---------------------------------------------------------------------------
|
||||
if (-not $OnlyContainers) {
|
||||
Write-Host "`n-- Health endpoints --" -ForegroundColor Cyan
|
||||
$checks = @(
|
||||
@{ Name = 'chat /health'; Url = "http://${target}:3000/health" },
|
||||
@{ Name = 'nginx /health'; Url = "http://${target}:8081/health" },
|
||||
@{ Name = 'prometheus'; Url = "http://${target}:9090/-/healthy" },
|
||||
@{ Name = 'grafana /api/health'; Url = "http://${target}:3001/api/health" }
|
||||
)
|
||||
foreach ($c in $checks) {
|
||||
try {
|
||||
$r = Invoke-WebRequest -Uri $c.Url -TimeoutSec $TimeoutSec -UseBasicParsing -ErrorAction Stop
|
||||
if ($r.StatusCode -eq 200) { Ok "$($c.Name) -> 200" } else { Warn "$($c.Name) -> $($r.StatusCode)" }
|
||||
} catch {
|
||||
Fail "$($c.Name) -> $($_.Exception.Response.StatusCode.value__)"
|
||||
}
|
||||
}
|
||||
|
||||
# -----------------------------------------------------------------------
|
||||
# 5. Public endpoints (routed through the Docker host for reliable TLS)
|
||||
# -----------------------------------------------------------------------
|
||||
Write-Host "`n-- Public endpoints (via Docker host) --" -ForegroundColor Cyan
|
||||
$pub = @(
|
||||
@{ Name = 'linearvoid.tv app'; Url = 'https://linearvoid.tv/' },
|
||||
@{ Name = 'media HLS manifest'; Url = 'https://media.linearvoid.tv/hls/playlist.m3u8' },
|
||||
@{ Name = 'coolify dashboard'; Url = 'https://coolify.allucanget.biz/' }
|
||||
)
|
||||
foreach ($c in $pub) {
|
||||
try {
|
||||
$code = (& docker run --rm curlimages/curl:latest -sS -o /dev/null -w '%{http_code}' --max-time $TimeoutSec -L $c.Url 2>&1 | Out-String).Trim()
|
||||
if ($code -match '^\d{3}$') { Ok "$($c.Name) -> HTTP $code" }
|
||||
else { Warn "$($c.Name) -> $code" }
|
||||
} catch {
|
||||
Warn "$($c.Name) -> error $($_.Exception.Message.Split("`n")[0])"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
# ---------------------------------------------------------------------------
|
||||
Write-Host ""
|
||||
if ($failed) { Write-Host "RESULT: FAILED" -ForegroundColor Red; exit 1 }
|
||||
Write-Host "RESULT: OK" -ForegroundColor Green; exit 0
|
||||
Reference in new issue
Block a user