mirror of
https://github.com/cozystack/cozystack.git
synced 2026-11-05 19:47:37 +09:00
A 50MB tarball with 200 directories is opaque on first contact. summary.txt at the root surfaces 'what is broken right now' — non-Ready HRs, ImagePullBackOff pods, OOMKilled events, cert-manager state, Flux Source health, storage binding, node pressure — so triage starts with one file instead of a directory tree dive. Signed-off-by: Myasnikov Daniil <myasnikovdaniil2001@gmail.com>
67 lines
2.3 KiB
Bash
Executable File
67 lines
2.3 KiB
Bash
Executable File
#!/bin/sh
|
|
# Emit a human-readable summary of "what is broken" to a single file.
|
|
# Reads the live cluster (not the report dir) so it can use kubectl JSONPath.
|
|
# Usage: cozyreport-summary.sh > summary.txt
|
|
set -eu
|
|
|
|
echo "# Cozystack E2E Diagnostic Summary"
|
|
echo "Generated: $(date -Iseconds)"
|
|
echo
|
|
|
|
echo "## HelmReleases not Ready"
|
|
echo
|
|
kubectl get hr -A --no-headers 2>/dev/null \
|
|
| awk '$4 != "True" {printf " %s/%s — %s\n", $1, $2, $5}' \
|
|
| head -40
|
|
echo
|
|
|
|
echo "## Pods not Running/Succeeded"
|
|
echo
|
|
kubectl get pod -A --no-headers 2>/dev/null \
|
|
| awk '$4 !~ /Running|Succeeded|Completed/ {printf " %s/%s — %s (restarts=%s, age=%s)\n", $1, $2, $4, $5, $6}' \
|
|
| head -40
|
|
echo
|
|
|
|
echo "## ImagePullBackOff / ErrImagePull"
|
|
echo
|
|
kubectl get pod -A --no-headers 2>/dev/null \
|
|
| awk '$4 ~ /ImagePullBackOff|ErrImagePull/ {printf " %s/%s — %s\n", $1, $2, $4}'
|
|
echo
|
|
|
|
echo "## OOMKilled in last 30 min"
|
|
echo
|
|
kubectl get events -A --field-selector reason=OOMKilling --sort-by=.lastTimestamp 2>/dev/null \
|
|
| tail -20
|
|
echo
|
|
|
|
echo "## Recent Warning events (top 30)"
|
|
echo
|
|
kubectl get events -A --field-selector type=Warning --sort-by=.lastTimestamp 2>/dev/null \
|
|
| tail -30
|
|
echo
|
|
|
|
echo "## cert-manager: Certificates not Ready"
|
|
echo
|
|
if kubectl get crd certificates.cert-manager.io >/dev/null 2>&1; then
|
|
kubectl get certificates.cert-manager.io -A --no-headers 2>/dev/null \
|
|
| awk '$3 != "True" {printf " %s/%s — Ready=%s\n", $1, $2, $3}'
|
|
fi
|
|
echo
|
|
|
|
echo "## Flux Sources not Ready"
|
|
echo
|
|
for kind in helmrepositories.source.toolkit.fluxcd.io ocirepositories.source.toolkit.fluxcd.io gitrepositories.source.toolkit.fluxcd.io; do
|
|
kubectl get $kind -A --no-headers 2>/dev/null \
|
|
| awk -v k="${kind%%.*}" '$4 != "True" {printf " %s %s/%s — Ready=%s\n", k, $1, $2, $4}'
|
|
done
|
|
echo
|
|
|
|
echo "## Storage: PVCs not Bound, PVs not Bound"
|
|
echo
|
|
kubectl get pvc -A --no-headers 2>/dev/null | awk '$3 != "Bound" {printf " PVC %s/%s — %s\n", $1, $2, $3}'
|
|
kubectl get pv --no-headers 2>/dev/null | awk '$5 != "Bound" {printf " PV %s — %s\n", $1, $5}'
|
|
echo
|
|
|
|
echo "## Node Conditions"
|
|
kubectl get nodes -o custom-columns=NAME:.metadata.name,READY:.status.conditions[?\(@.type==\"Ready\"\)].status,DISK:.status.conditions[?\(@.type==\"DiskPressure\"\)].status,MEM:.status.conditions[?\(@.type==\"MemoryPressure\"\)].status 2>/dev/null
|