Files
doctate/scripts/check.sh
T
Brummel 88e469d0a1 feat: Add project integrity check script
This script automates checks for formatting, linting, building, and
testing across
all Cargo workspaces and the Wear OS Gradle build. It provides a summary
of all
stages, indicating PASS, WARN, or FAIL. The script's exit code reflects
the number
of failed stages.
2026-05-04 09:38:04 +02:00

114 lines
3.6 KiB
Bash
Executable File

#!/usr/bin/env bash
# Project integrity check after a refactor.
# Runs fmt, clippy, build and tests for every Cargo world plus the Wear OS Gradle build.
# All stages run even if earlier ones fail. A summary table is printed at the end.
# Exit code equals the number of FAIL stages (WARN stages do not count).
set -u
set -o pipefail
REPO_ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
export JAVA_HOME="/opt/android-studio/jbr"
# Colors only when stdout is a terminal
if [[ -t 1 ]]; then
C_RESET=$'\e[0m'
C_RED=$'\e[31m'
C_GREEN=$'\e[32m'
C_YELLOW=$'\e[33m'
C_BOLD=$'\e[1m'
else
C_RESET=""
C_RED=""
C_GREEN=""
C_YELLOW=""
C_BOLD=""
fi
# Stage results, parallel arrays
STAGE_NAMES=()
STAGE_STATUS=()
STAGE_SECONDS=()
FAIL_COUNT=0
# run_stage <label> <working-dir> <severity> <cmd...>
# severity = "fail" -> non-zero exit marks FAIL and increments FAIL_COUNT
# severity = "warn" -> non-zero exit marks WARN, does not affect exit code
run_stage() {
local label="$1"; shift
local workdir="$1"; shift
local severity="$1"; shift
echo
echo "${C_BOLD}=== ${label} ===${C_RESET}"
echo " dir: ${workdir}"
echo " cmd: $*"
local start=$SECONDS
local rc=0
( cd "$workdir" && "$@" ) || rc=$?
local dur=$(( SECONDS - start ))
STAGE_NAMES+=("$label")
STAGE_SECONDS+=("$dur")
if [[ $rc -eq 0 ]]; then
STAGE_STATUS+=("PASS")
echo "${C_GREEN}-> PASS${C_RESET} (${dur}s)"
elif [[ "$severity" == "warn" ]]; then
STAGE_STATUS+=("WARN")
echo "${C_YELLOW}-> WARN (rc=${rc})${C_RESET} (${dur}s) -- not counted as failure"
else
STAGE_STATUS+=("FAIL")
FAIL_COUNT=$(( FAIL_COUNT + 1 ))
echo "${C_RED}-> FAIL (rc=${rc})${C_RESET} (${dur}s)"
fi
}
# fmt is executed (not --check), so the working tree may be modified.
# clippy escalates warnings to errors per project convention.
# test uses -j 4 to avoid linker thrashing on a many-crate workspace.
cargo_world() {
local world_label="$1"
local dir="$2"
run_stage "${world_label} :: fmt" "$dir" fail cargo fmt
run_stage "${world_label} :: clippy" "$dir" fail cargo clippy --all-targets --all-features -- -D warnings
run_stage "${world_label} :: build" "$dir" fail cargo build --all-targets
run_stage "${world_label} :: test" "$dir" fail cargo test -j 4
}
cargo_world "common" "${REPO_ROOT}/common"
cargo_world "server" "${REPO_ROOT}/server"
cargo_world "clients/desktop" "${REPO_ROOT}/clients/desktop"
cargo_world "experiments" "${REPO_ROOT}/experiments"
# Wear OS (Gradle). lintDebug is WARN-only because legacy Android Lint findings
# would otherwise turn the script red regardless of the refactor under review.
# Instrumented tests are intentionally excluded (AVD MockWebServer hang, see memory).
WEAROS_DIR="${REPO_ROOT}/clients/wearos"
run_stage "wearos :: assembleDebug" "$WEAROS_DIR" fail ./gradlew assembleDebug
run_stage "wearos :: lintDebug" "$WEAROS_DIR" warn ./gradlew lintDebug
run_stage "wearos :: testDebugUnitTest" "$WEAROS_DIR" fail ./gradlew testDebugUnitTest
# Summary
echo
echo "${C_BOLD}========== SUMMARY ==========${C_RESET}"
total=0
for i in "${!STAGE_NAMES[@]}"; do
name="${STAGE_NAMES[$i]}"
status="${STAGE_STATUS[$i]}"
dur="${STAGE_SECONDS[$i]}"
total=$(( total + dur ))
case "$status" in
PASS) color="$C_GREEN" ;;
WARN) color="$C_YELLOW" ;;
FAIL) color="$C_RED" ;;
*) color="" ;;
esac
printf " %s%-4s%s %5ds %s\n" "$color" "$status" "$C_RESET" "$dur" "$name"
done
echo " ----"
printf " total: %ds across %d stages, %d failure(s)\n" "$total" "${#STAGE_NAMES[@]}" "$FAIL_COUNT"
exit "$FAIL_COUNT"