#!/usr/bin/env bash set -euo pipefail ROOT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)" COMPOSE=(docker compose -f "$ROOT_DIR/docker-compose.yml" -f "$ROOT_DIR/docker-compose.arm.yml") services=(dark3proxy darkdns darkzil darkscale darkpihole darki2p) dns_queries=(google.com torproject.org github.com wikipedia.org example.onion example.i2p) echo "[smoke] stack status" "${COMPOSE[@]}" ps echo echo "[smoke] restart/health counters" for c in "${services[@]}"; do if [[ "$c" == "darkpihole" ]]; then docker inspect -f "$c status={{.State.Status}} health={{if .State.Health}}{{.State.Health.Status}}{{else}}none{{end}} restart={{.RestartCount}}" "$c" elif [[ "$c" == "darki2p" ]]; then docker inspect -f "$c status={{.State.Status}} health={{if .State.Health}}{{.State.Health.Status}}{{else}}none{{end}} restart={{.RestartCount}}" "$c" else docker inspect -f "$c status={{.State.Status}} restart={{.RestartCount}}" "$c" fi done echo echo "[smoke] dns timings via pihole" for pass in 1 2; do echo "-- pass $pass --" for q in "${dns_queries[@]}"; do out="$(docker exec darkpihole sh -lc "dig @127.0.0.1 +time=2 +tries=1 '$q' 2>&1" || true)" status="$(printf "%s\n" "$out" | sed -n 's/.*status: \([A-Z]*\).*/\1/p' | head -n1)" qtime="$(printf "%s\n" "$out" | sed -n 's/;; Query time: \([0-9]*\).*/\1/p' | head -n1)" [[ -n "$status" ]] || status="NO_RESPONSE" [[ -n "$qtime" ]] || qtime="-1" printf '%s status=%s query_ms=%s\n' "$q" "$status" "$qtime" done echo done echo echo "[smoke] .zil path checks via coredns" for q in brad.zil not-a-real-name-xyz12345.zil; do out="$(docker exec darkpihole sh -lc "dig @10.5.0.4 +time=8 +tries=1 '$q' TXT 2>&1" || true)" status="$(printf "%s\n" "$out" | sed -n 's/.*status: \([A-Z]*\).*/\1/p' | head -n1)" qtime="$(printf "%s\n" "$out" | sed -n 's/;; Query time: \([0-9]*\).*/\1/p' | head -n1)" answers="$(printf "%s\n" "$out" | awk '/^;; ANSWER SECTION:/{flag=1;next}/^;;/{if(flag)exit}flag' | wc -l | tr -d ' ')" [[ -n "$status" ]] || status="NO_RESPONSE" [[ -n "$qtime" ]] || qtime="-1" [[ -n "$answers" ]] || answers="0" printf '%s status=%s query_ms=%s answers=%s\n' "$q" "$status" "$qtime" "$answers" done echo "[smoke] key error scan" for c in "${services[@]}"; do echo "=== $c ===" case "$c" in darkscale) docker logs --tail 120 "$c" 2>&1 \ | grep -Ei "error|failed|not found|panic|traceback|unhealthy|refused|parse" \ | grep -Ev "tpmrm0|Tailscale is stopped" \ | tail -n 20 || echo "(no matching patterns)" ;; darkpihole) docker logs --tail 120 "$c" 2>&1 \ | grep -Ei "error|failed|not found|panic|traceback|unhealthy|refused|parse" \ | grep -Ev "refused to do a recursive query" \ | tail -n 20 || echo "(no matching patterns)" ;; darki2p) docker logs --tail 120 "$c" 2>&1 \ | grep -Ei "error|failed|not found|panic|traceback|unhealthy|refused|parse" \ | grep -Ev "SessionCreated read error: End of file|Connect error Operation canceled|Connect error Network is unreachable|RouterInfo for .* not found|RouterInfo not found, failed to send messages|NetDbReq: .* not found after 5 attempts" \ | tail -n 20 || echo "(no matching patterns)" ;; *) docker logs --tail 120 "$c" 2>&1 | grep -Ei "error|failed|not found|panic|traceback|unhealthy|refused|parse" | tail -n 20 || echo "(no matching patterns)" ;; esac echo done echo "[smoke] done"