File size: 2,857 Bytes
9e89154 | 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 | #!/usr/bin/env bash
# Start local dev stack: Flask API + Next.js (default) or CRA.
#
# Usage:
# chmod +x scripts/dev.sh
# ./scripts/dev.sh # API (background) + Next on :3000
# ./scripts/dev.sh --cra # API + CRA React (:3000)
# ./scripts/dev.sh --api-only # Flask only (PORT or 5000)
# ./scripts/dev.sh --next-only # Next only — run API separately
#
# Env:
# PORT API port (default 5000) — same as api.py
# NEXT_PORT Next / CRA dev port (default 3000)
# VENV Path to venv (default .venv in repo root)
set -euo pipefail
ROOT="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
cd "$ROOT"
MODE="next"
API_ONLY=false
UI_ONLY=false
for arg in "$@"; do
case "$arg" in
--cra) MODE="cra" ;;
--next) MODE="next" ;;
--api-only) API_ONLY=true ;;
--ui-only|--next-only) UI_ONLY=true ;;
-h|--help)
sed -n '2,18p' "$0" | cat
exit 0
;;
*)
echo "Unknown option: $arg" >&2
exit 1
;;
esac
done
VENV="${VENV:-$ROOT/.venv}"
if [[ -f "$VENV/bin/activate" ]]; then
# shellcheck source=/dev/null
source "$VENV/bin/activate"
fi
API_PORT="${PORT:-5000}"
NEXT_PORT="${NEXT_PORT:-3000}"
export PORT="$API_PORT"
API_PID=""
cleanup() {
if [[ -n "${API_PID}" ]] && kill -0 "$API_PID" 2>/dev/null; then
echo ""
echo "[dev] Stopping API (pid $API_PID)..."
kill "$API_PID" 2>/dev/null || true
wait "$API_PID" 2>/dev/null || true
fi
}
trap cleanup EXIT INT TERM
if [[ "$UI_ONLY" != true ]]; then
echo "[dev] Starting Flask API on 0.0.0.0:${API_PORT}..."
python api.py &
API_PID=$!
echo "[dev] Waiting for /api/health..."
for _ in $(seq 1 45); do
if curl -sf "http://127.0.0.1:${API_PORT}/api/health" >/dev/null 2>&1; then
echo "[dev] API is up."
break
fi
sleep 1
done
if ! curl -sf "http://127.0.0.1:${API_PORT}/api/health" >/dev/null 2>&1; then
echo "[dev] WARNING: API did not respond on ${API_PORT}. Check logs above." >&2
fi
fi
if [[ "$API_ONLY" == true ]]; then
echo "[dev] API-only mode; press Ctrl+C to stop."
wait "${API_PID:-}"
exit 0
fi
if [[ "$MODE" == "next" ]]; then
if [[ ! -d "$ROOT/web/node_modules" ]]; then
echo "[dev] Installing web dependencies (npm install)..."
(cd "$ROOT/web" && npm install)
fi
echo "[dev] Starting Next.js on http://127.0.0.1:${NEXT_PORT} (rewrites /api → :${API_PORT})"
# No exec: keeps shell alive so EXIT trap stops the API when you quit Next
(cd "$ROOT/web" && npx next dev -p "${NEXT_PORT}")
else
if [[ ! -d "$ROOT/frontend/node_modules" ]]; then
echo "[dev] Installing frontend dependencies (npm install)..."
(cd "$ROOT/frontend" && npm install)
fi
echo "[dev] Starting CRA on http://127.0.0.1:${NEXT_PORT} (proxy → :${API_PORT})"
(cd "$ROOT/frontend" && env PORT="${NEXT_PORT}" npm start)
fi
|