shipwright-cli 2.3.1 → 3.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (162) hide show
  1. package/README.md +95 -28
  2. package/completions/_shipwright +1 -1
  3. package/completions/shipwright.bash +3 -8
  4. package/completions/shipwright.fish +1 -1
  5. package/config/defaults.json +111 -0
  6. package/config/event-schema.json +81 -0
  7. package/config/policy.json +155 -2
  8. package/config/policy.schema.json +162 -1
  9. package/dashboard/coverage/coverage-summary.json +14 -0
  10. package/dashboard/public/index.html +1 -1
  11. package/dashboard/server.ts +306 -17
  12. package/dashboard/src/components/charts/bar.test.ts +79 -0
  13. package/dashboard/src/components/charts/donut.test.ts +68 -0
  14. package/dashboard/src/components/charts/pipeline-rail.test.ts +117 -0
  15. package/dashboard/src/components/charts/sparkline.test.ts +125 -0
  16. package/dashboard/src/core/api.test.ts +309 -0
  17. package/dashboard/src/core/helpers.test.ts +301 -0
  18. package/dashboard/src/core/router.test.ts +307 -0
  19. package/dashboard/src/core/router.ts +7 -0
  20. package/dashboard/src/core/sse.test.ts +144 -0
  21. package/dashboard/src/views/metrics.test.ts +186 -0
  22. package/dashboard/src/views/overview.test.ts +173 -0
  23. package/dashboard/src/views/pipelines.test.ts +183 -0
  24. package/dashboard/src/views/team.test.ts +253 -0
  25. package/dashboard/vitest.config.ts +14 -5
  26. package/docs/TIPS.md +1 -1
  27. package/docs/patterns/README.md +1 -1
  28. package/package.json +15 -5
  29. package/scripts/adapters/docker-deploy.sh +1 -1
  30. package/scripts/adapters/tmux-adapter.sh +11 -1
  31. package/scripts/adapters/wezterm-adapter.sh +1 -1
  32. package/scripts/check-version-consistency.sh +1 -1
  33. package/scripts/lib/architecture.sh +126 -0
  34. package/scripts/lib/bootstrap.sh +75 -0
  35. package/scripts/lib/compat.sh +89 -6
  36. package/scripts/lib/config.sh +91 -0
  37. package/scripts/lib/daemon-adaptive.sh +3 -3
  38. package/scripts/lib/daemon-dispatch.sh +39 -16
  39. package/scripts/lib/daemon-health.sh +1 -1
  40. package/scripts/lib/daemon-patrol.sh +24 -12
  41. package/scripts/lib/daemon-poll.sh +37 -25
  42. package/scripts/lib/daemon-state.sh +115 -23
  43. package/scripts/lib/daemon-triage.sh +30 -8
  44. package/scripts/lib/fleet-failover.sh +63 -0
  45. package/scripts/lib/helpers.sh +30 -6
  46. package/scripts/lib/pipeline-detection.sh +2 -2
  47. package/scripts/lib/pipeline-github.sh +9 -9
  48. package/scripts/lib/pipeline-intelligence.sh +85 -35
  49. package/scripts/lib/pipeline-quality-checks.sh +16 -16
  50. package/scripts/lib/pipeline-quality.sh +1 -1
  51. package/scripts/lib/pipeline-stages.sh +242 -28
  52. package/scripts/lib/pipeline-state.sh +40 -4
  53. package/scripts/lib/test-helpers.sh +247 -0
  54. package/scripts/postinstall.mjs +3 -11
  55. package/scripts/sw +10 -4
  56. package/scripts/sw-activity.sh +1 -11
  57. package/scripts/sw-adaptive.sh +109 -85
  58. package/scripts/sw-adversarial.sh +4 -14
  59. package/scripts/sw-architecture-enforcer.sh +1 -11
  60. package/scripts/sw-auth.sh +8 -17
  61. package/scripts/sw-autonomous.sh +111 -49
  62. package/scripts/sw-changelog.sh +1 -11
  63. package/scripts/sw-checkpoint.sh +144 -20
  64. package/scripts/sw-ci.sh +2 -12
  65. package/scripts/sw-cleanup.sh +13 -17
  66. package/scripts/sw-code-review.sh +16 -36
  67. package/scripts/sw-connect.sh +5 -12
  68. package/scripts/sw-context.sh +9 -26
  69. package/scripts/sw-cost.sh +6 -16
  70. package/scripts/sw-daemon.sh +75 -70
  71. package/scripts/sw-dashboard.sh +57 -17
  72. package/scripts/sw-db.sh +506 -15
  73. package/scripts/sw-decompose.sh +1 -11
  74. package/scripts/sw-deps.sh +15 -25
  75. package/scripts/sw-developer-simulation.sh +1 -11
  76. package/scripts/sw-discovery.sh +112 -30
  77. package/scripts/sw-doc-fleet.sh +7 -17
  78. package/scripts/sw-docs-agent.sh +6 -16
  79. package/scripts/sw-docs.sh +4 -12
  80. package/scripts/sw-doctor.sh +134 -43
  81. package/scripts/sw-dora.sh +11 -19
  82. package/scripts/sw-durable.sh +35 -52
  83. package/scripts/sw-e2e-orchestrator.sh +11 -27
  84. package/scripts/sw-eventbus.sh +115 -115
  85. package/scripts/sw-evidence.sh +748 -0
  86. package/scripts/sw-feedback.sh +3 -13
  87. package/scripts/sw-fix.sh +2 -20
  88. package/scripts/sw-fleet-discover.sh +1 -11
  89. package/scripts/sw-fleet-viz.sh +10 -18
  90. package/scripts/sw-fleet.sh +13 -17
  91. package/scripts/sw-github-app.sh +6 -16
  92. package/scripts/sw-github-checks.sh +1 -11
  93. package/scripts/sw-github-deploy.sh +1 -11
  94. package/scripts/sw-github-graphql.sh +2 -12
  95. package/scripts/sw-guild.sh +1 -11
  96. package/scripts/sw-heartbeat.sh +49 -12
  97. package/scripts/sw-hygiene.sh +45 -43
  98. package/scripts/sw-incident.sh +284 -67
  99. package/scripts/sw-init.sh +35 -37
  100. package/scripts/sw-instrument.sh +1 -11
  101. package/scripts/sw-intelligence.sh +362 -51
  102. package/scripts/sw-jira.sh +5 -14
  103. package/scripts/sw-launchd.sh +2 -12
  104. package/scripts/sw-linear.sh +8 -17
  105. package/scripts/sw-logs.sh +4 -12
  106. package/scripts/sw-loop.sh +641 -90
  107. package/scripts/sw-memory.sh +243 -17
  108. package/scripts/sw-mission-control.sh +2 -12
  109. package/scripts/sw-model-router.sh +73 -34
  110. package/scripts/sw-otel.sh +11 -21
  111. package/scripts/sw-oversight.sh +1 -11
  112. package/scripts/sw-patrol-meta.sh +5 -11
  113. package/scripts/sw-pipeline-composer.sh +7 -17
  114. package/scripts/sw-pipeline-vitals.sh +1 -11
  115. package/scripts/sw-pipeline.sh +478 -122
  116. package/scripts/sw-pm.sh +2 -12
  117. package/scripts/sw-pr-lifecycle.sh +203 -29
  118. package/scripts/sw-predictive.sh +16 -22
  119. package/scripts/sw-prep.sh +6 -16
  120. package/scripts/sw-ps.sh +1 -11
  121. package/scripts/sw-public-dashboard.sh +2 -12
  122. package/scripts/sw-quality.sh +77 -10
  123. package/scripts/sw-reaper.sh +1 -11
  124. package/scripts/sw-recruit.sh +15 -25
  125. package/scripts/sw-regression.sh +11 -21
  126. package/scripts/sw-release-manager.sh +19 -28
  127. package/scripts/sw-release.sh +8 -16
  128. package/scripts/sw-remote.sh +1 -11
  129. package/scripts/sw-replay.sh +48 -44
  130. package/scripts/sw-retro.sh +70 -92
  131. package/scripts/sw-review-rerun.sh +220 -0
  132. package/scripts/sw-scale.sh +109 -32
  133. package/scripts/sw-security-audit.sh +12 -22
  134. package/scripts/sw-self-optimize.sh +239 -23
  135. package/scripts/sw-session.sh +3 -13
  136. package/scripts/sw-setup.sh +8 -18
  137. package/scripts/sw-standup.sh +5 -15
  138. package/scripts/sw-status.sh +32 -23
  139. package/scripts/sw-strategic.sh +129 -13
  140. package/scripts/sw-stream.sh +1 -11
  141. package/scripts/sw-swarm.sh +76 -36
  142. package/scripts/sw-team-stages.sh +10 -20
  143. package/scripts/sw-templates.sh +4 -14
  144. package/scripts/sw-testgen.sh +3 -13
  145. package/scripts/sw-tmux-pipeline.sh +1 -19
  146. package/scripts/sw-tmux-role-color.sh +0 -10
  147. package/scripts/sw-tmux-status.sh +3 -11
  148. package/scripts/sw-tmux.sh +2 -20
  149. package/scripts/sw-trace.sh +1 -19
  150. package/scripts/sw-tracker-github.sh +0 -10
  151. package/scripts/sw-tracker-jira.sh +1 -11
  152. package/scripts/sw-tracker-linear.sh +1 -11
  153. package/scripts/sw-tracker.sh +7 -24
  154. package/scripts/sw-triage.sh +24 -34
  155. package/scripts/sw-upgrade.sh +5 -23
  156. package/scripts/sw-ux.sh +1 -19
  157. package/scripts/sw-webhook.sh +18 -32
  158. package/scripts/sw-widgets.sh +3 -21
  159. package/scripts/sw-worktree.sh +11 -27
  160. package/scripts/update-homebrew-sha.sh +67 -0
  161. package/templates/pipelines/tdd.json +72 -0
  162. package/scripts/sw-pipeline.sh.mock +0 -7
@@ -6,7 +6,7 @@
6
6
  set -euo pipefail
7
7
  trap 'echo "ERROR: $BASH_SOURCE:$LINENO exited with status $?" >&2' ERR
8
8
 
9
- VERSION="2.3.1"
9
+ VERSION="3.0.0"
10
10
  SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
11
11
 
12
12
  # ─── Cross-platform compatibility ──────────────────────────────────────────
@@ -16,6 +16,7 @@ SCRIPT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")" && pwd)"
16
16
  # Canonical helpers (colors, output, events)
17
17
  # shellcheck source=lib/helpers.sh
18
18
  [[ -f "$SCRIPT_DIR/lib/helpers.sh" ]] && source "$SCRIPT_DIR/lib/helpers.sh"
19
+ [[ -f "$SCRIPT_DIR/lib/config.sh" ]] && source "$SCRIPT_DIR/lib/config.sh"
19
20
  # Fallbacks when helpers not loaded (e.g. test env with overridden SCRIPT_DIR)
20
21
  [[ "$(type -t info 2>/dev/null)" == "function" ]] || info() { echo -e "\033[38;2;0;212;255m\033[1m▸\033[0m $*"; }
21
22
  [[ "$(type -t success 2>/dev/null)" == "function" ]] || success() { echo -e "\033[38;2;74;222;128m\033[1m✓\033[0m $*"; }
@@ -33,15 +34,6 @@ if [[ "$(type -t emit_event 2>/dev/null)" != "function" ]]; then
33
34
  echo "${payload}}" >> "${HOME}/.shipwright/events.jsonl"
34
35
  }
35
36
  fi
36
- CYAN="${CYAN:-\033[38;2;0;212;255m}"
37
- PURPLE="${PURPLE:-\033[38;2;124;58;237m}"
38
- BLUE="${BLUE:-\033[38;2;0;102;255m}"
39
- GREEN="${GREEN:-\033[38;2;74;222;128m}"
40
- YELLOW="${YELLOW:-\033[38;2;250;204;21m}"
41
- RED="${RED:-\033[38;2;248;113;113m}"
42
- DIM="${DIM:-\033[2m}"
43
- BOLD="${BOLD:-\033[1m}"
44
- RESET="${RESET:-\033[0m}"
45
37
  UNDERLINE='\033[4m'
46
38
 
47
39
  # ─── Paths ──────────────────────────────────────────────────────────────────
@@ -50,7 +42,7 @@ PID_FILE="${TEAMS_DIR}/dashboard.pid"
50
42
  LOG_DIR="${TEAMS_DIR}/logs"
51
43
  LOG_FILE="${LOG_DIR}/dashboard.log"
52
44
  EVENTS_FILE="${TEAMS_DIR}/events.jsonl"
53
- DEFAULT_PORT=8767
45
+ DEFAULT_PORT=$(_config_get_int "dashboard.port" 8767 2>/dev/null || echo 8767)
54
46
 
55
47
  # ─── Header ────────────────────────────────────────────────────────────────
56
48
  dashboard_header() {
@@ -78,6 +70,7 @@ show_help() {
78
70
  echo -e "${BOLD}OPTIONS${RESET}"
79
71
  echo -e " ${CYAN}--port${RESET} <N> Port to run on ${DIM}(default: ${DEFAULT_PORT})${RESET}"
80
72
  echo -e " ${CYAN}--foreground${RESET} Run in foreground ${DIM}(don't daemonize)${RESET}"
73
+ echo -e " ${CYAN}--no-build${RESET} Skip build check; start immediately"
81
74
  echo ""
82
75
  echo -e "${BOLD}EXAMPLES${RESET}"
83
76
  echo -e " ${DIM}shipwright dashboard${RESET} # Start in foreground"
@@ -91,13 +84,47 @@ show_help() {
91
84
 
92
85
  # ─── Prerequisite Check ────────────────────────────────────────────────────
93
86
  check_bun() {
94
- if ! command -v bun &>/dev/null; then
87
+ if ! command -v bun >/dev/null 2>&1; then
95
88
  error "Bun is required but not installed"
96
89
  info "Install Bun: ${UNDERLINE}https://bun.sh${RESET}"
97
90
  exit 1
98
91
  fi
99
92
  }
100
93
 
94
+ # ─── Build Check (before serve) ─────────────────────────────────────────────
95
+ ensure_dashboard_built() {
96
+ local server_ts="$1"
97
+ local repo_root
98
+ repo_root=$(dirname "$(dirname "$server_ts")")
99
+ local dist_dir="$repo_root/dashboard/public/dist"
100
+ local src_dir="$repo_root/dashboard/src"
101
+
102
+ # Check if dist exists and has main.js
103
+ if [[ ! -d "$dist_dir" ]] || [[ ! -f "$dist_dir/main.js" ]]; then
104
+ echo "Dashboard not built. Building..."
105
+ if command -v bun &>/dev/null; then
106
+ (cd "$repo_root" && bun run dashboard:build)
107
+ elif command -v npx &>/dev/null; then
108
+ (cd "$repo_root" && npx esbuild dashboard/src/main.ts --bundle --outdir=dashboard/public/dist --target=esnext)
109
+ else
110
+ warn "Cannot build dashboard: neither bun nor npx available"
111
+ return 1
112
+ fi
113
+ else
114
+ # Check if source is newer than build
115
+ local src_mtime
116
+ src_mtime=$(find "$src_dir" -name "*.ts" -newer "$dist_dir/main.js" 2>/dev/null | head -1)
117
+ if [[ -n "$src_mtime" ]]; then
118
+ echo "Dashboard source changed. Rebuilding..."
119
+ if command -v bun &>/dev/null; then
120
+ (cd "$repo_root" && bun run dashboard:build)
121
+ elif command -v npx &>/dev/null; then
122
+ (cd "$repo_root" && npx esbuild dashboard/src/main.ts --bundle --outdir=dashboard/public/dist --target=esnext)
123
+ fi
124
+ fi
125
+ fi
126
+ }
127
+
101
128
  # ─── Find Server ───────────────────────────────────────────────────────────
102
129
  find_server() {
103
130
  # Look for dashboard/server.ts relative to the script's repo location
@@ -161,6 +188,10 @@ dashboard_start_bg() {
161
188
  local server_ts
162
189
  server_ts=$(find_server)
163
190
 
191
+ if [[ "$NO_BUILD" != "true" ]]; then
192
+ ensure_dashboard_built "$server_ts" || exit 1
193
+ fi
194
+
164
195
  # Ensure directories exist
165
196
  mkdir -p "$LOG_DIR" "$TEAMS_DIR"
166
197
 
@@ -217,6 +248,10 @@ dashboard_start_fg() {
217
248
  local server_ts
218
249
  server_ts=$(find_server)
219
250
 
251
+ if [[ "$NO_BUILD" != "true" ]]; then
252
+ ensure_dashboard_built "$server_ts" || exit 1
253
+ fi
254
+
220
255
  mkdir -p "$TEAMS_DIR"
221
256
 
222
257
  info "Starting dashboard server on port ${CYAN}${port}${RESET} ${DIM}(foreground)${RESET}"
@@ -294,7 +329,7 @@ dashboard_status() {
294
329
 
295
330
  # Try to get port from /proc or lsof
296
331
  local port=""
297
- if command -v lsof &>/dev/null; then
332
+ if command -v lsof >/dev/null 2>&1; then
298
333
  port=$(lsof -nP -iTCP -sTCP:LISTEN -a -p "$pid" 2>/dev/null | grep -oE ':\d+' | head -1 | tr -d ':' || true)
299
334
  fi
300
335
 
@@ -309,7 +344,7 @@ dashboard_status() {
309
344
  if [[ -f "$PID_FILE" ]]; then
310
345
  local pid_mtime
311
346
  if [[ "$(uname)" == "Darwin" ]]; then
312
- pid_mtime=$(stat -f %m "$PID_FILE" 2>/dev/null || echo "0")
347
+ pid_mtime=$(file_mtime "$PID_FILE")
313
348
  else
314
349
  pid_mtime=$(stat -c %Y "$PID_FILE" 2>/dev/null || echo "0")
315
350
  fi
@@ -331,7 +366,7 @@ dashboard_status() {
331
366
  if [[ -n "$port" ]]; then
332
367
  local health
333
368
  health=$(curl -s --max-time 2 "http://localhost:${port}/api/health" 2>/dev/null || true)
334
- if [[ -n "$health" ]] && command -v jq &>/dev/null; then
369
+ if [[ -n "$health" ]] && command -v jq >/dev/null 2>&1; then
335
370
  local connections
336
371
  connections=$(echo "$health" | jq -r '.connections // empty' 2>/dev/null || true)
337
372
  if [[ -n "$connections" ]]; then
@@ -361,7 +396,7 @@ dashboard_open() {
361
396
  if is_running; then
362
397
  local pid
363
398
  pid=$(get_pid)
364
- if command -v lsof &>/dev/null; then
399
+ if command -v lsof >/dev/null 2>&1; then
365
400
  local detected_port
366
401
  detected_port=$(lsof -nP -iTCP -sTCP:LISTEN -a -p "$pid" 2>/dev/null | grep -oE ':\d+' | head -1 | tr -d ':' || true)
367
402
  if [[ -n "$detected_port" ]]; then
@@ -379,7 +414,7 @@ dashboard_open() {
379
414
 
380
415
  if open_url "$url" 2>/dev/null; then
381
416
  : # opened via compat.sh
382
- elif command -v powershell.exe &>/dev/null; then
417
+ elif command -v powershell.exe >/dev/null 2>&1; then
383
418
  powershell.exe -Command "Start-Process '$url'" 2>/dev/null
384
419
  else
385
420
  error "No browser opener found"
@@ -392,6 +427,7 @@ dashboard_open() {
392
427
  SUBCOMMAND=""
393
428
  PORT="$DEFAULT_PORT"
394
429
  FOREGROUND=false
430
+ NO_BUILD=false
395
431
 
396
432
  while [[ $# -gt 0 ]]; do
397
433
  case "$1" in
@@ -427,6 +463,10 @@ while [[ $# -gt 0 ]]; do
427
463
  FOREGROUND=true
428
464
  shift
429
465
  ;;
466
+ --no-build)
467
+ NO_BUILD=true
468
+ shift
469
+ ;;
430
470
  --version|-v)
431
471
  echo "shipwright dashboard v${VERSION}"
432
472
  exit 0