crewswarm 0.9.1 → 0.9.3

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 (210) hide show
  1. package/README.md +22 -9
  2. package/apps/dashboard/dist/assets/{chat-core-Cx4sTxDd.js → chat-core-3KirthZA.js} +1 -1
  3. package/apps/dashboard/dist/assets/index-GSWxxEPO.js +2 -0
  4. package/apps/dashboard/dist/assets/{tab-pm-loop-tab-Bfd449B4.js → tab-pm-loop-tab-DiAPTJXu.js} +1 -1
  5. package/apps/dashboard/dist/assets/{tab-projects-tab-DhNWnlzt.js → tab-projects-tab-SFH4E--a.js} +1 -1
  6. package/apps/dashboard/dist/assets/tab-settings-tab-BselH1c0.js +1 -0
  7. package/apps/dashboard/dist/index.html +82 -11
  8. package/apps/vibe/README.md +2 -2
  9. package/apps/vibe/package.json +1 -1
  10. package/apps/vibe/server.mjs +3 -3
  11. package/crew-lead.mjs +48 -5
  12. package/lib/bridges/gateway-ws.mjs +4 -0
  13. package/lib/bridges/tmux-bridge.mjs +200 -0
  14. package/lib/cli-process-tracker.mjs +2 -1
  15. package/lib/crew-lead/chat-handler.mjs +34 -0
  16. package/lib/crew-lead/http-server.mjs +340 -14
  17. package/lib/crew-lead/llm-caller.mjs +24 -8
  18. package/lib/crew-lead/prompts.mjs +7 -0
  19. package/lib/crew-lead/wave-dispatcher.mjs +53 -3
  20. package/lib/crew-lead/ws-router.mjs +219 -27
  21. package/lib/engines/engine-registry.mjs +9 -0
  22. package/lib/engines/rt-envelope.mjs +1 -0
  23. package/lib/engines/runners.mjs +26 -2
  24. package/lib/runtime/config.mjs +7 -0
  25. package/lib/runtime/paths.mjs +12 -8
  26. package/lib/sessions/session-manager.mjs +287 -0
  27. package/package.json +35 -15
  28. package/scripts/capture-build-flow.mjs +118 -0
  29. package/scripts/coverage-report.mjs +209 -0
  30. package/scripts/coverage-summary.mjs +47 -0
  31. package/scripts/dashboard-validation.mjs +74 -0
  32. package/scripts/dashboard.mjs +560 -70
  33. package/scripts/live-bridge-matrix.mjs +79 -0
  34. package/scripts/live-cli-matrix.mjs +166 -0
  35. package/scripts/live-crewchat-check.mjs +42 -0
  36. package/scripts/live-engine-matrix.mjs +50 -0
  37. package/scripts/live-provider-failover-matrix.mjs +107 -0
  38. package/scripts/live-provider-matrix.mjs +228 -0
  39. package/scripts/restart-all-from-repo.sh +4 -4
  40. package/scripts/smoke-dispatch.mjs +4 -1
  41. package/scripts/test-blast-radius.mjs +204 -0
  42. package/scripts/test-report-summary.mjs +88 -0
  43. package/scripts/test-reporter.mjs +651 -0
  44. package/scripts/test-rerun.mjs +136 -0
  45. package/scripts/tmux-bridge +130 -0
  46. package/apps/dashboard/dist/assets/chat-core-Cx4sTxDd.js.br +0 -0
  47. package/apps/dashboard/dist/assets/cli-process-COMRNPqr.js.br +0 -0
  48. package/apps/dashboard/dist/assets/components-BS9fQjE_.js.br +0 -0
  49. package/apps/dashboard/dist/assets/core-utils-CmOkXgzi.js.br +0 -0
  50. package/apps/dashboard/dist/assets/index-CF0aJRtC.css.br +0 -0
  51. package/apps/dashboard/dist/assets/index-DnClJ1ee.js +0 -2
  52. package/apps/dashboard/dist/assets/index-DnClJ1ee.js.br +0 -0
  53. package/apps/dashboard/dist/assets/orchestration-Ca2DLWN-.js.br +0 -0
  54. package/apps/dashboard/dist/assets/setup-wizard-CA0Or47w.js.br +0 -0
  55. package/apps/dashboard/dist/assets/tab-agents-tab-BgpIsjkw.js.br +0 -0
  56. package/apps/dashboard/dist/assets/tab-comms-tab-kguqTIzD.js.br +0 -0
  57. package/apps/dashboard/dist/assets/tab-contacts-tab-DiOyMYth.js.br +0 -0
  58. package/apps/dashboard/dist/assets/tab-engines-tab-BsdZVvU0.js.br +0 -0
  59. package/apps/dashboard/dist/assets/tab-memory-tab-Cu6u13EQ.js.br +0 -0
  60. package/apps/dashboard/dist/assets/tab-models-tab-BLEjmd19.js.br +0 -0
  61. package/apps/dashboard/dist/assets/tab-pm-loop-tab-Bfd449B4.js.br +0 -0
  62. package/apps/dashboard/dist/assets/tab-projects-tab-DhNWnlzt.js.br +0 -0
  63. package/apps/dashboard/dist/assets/tab-prompts-tab-DVkUNaJd.js.br +0 -0
  64. package/apps/dashboard/dist/assets/tab-services-tab-DU_LH3uG.js.br +0 -0
  65. package/apps/dashboard/dist/assets/tab-settings-tab-Bn4nXtDe.js +0 -1
  66. package/apps/dashboard/dist/assets/tab-settings-tab-Bn4nXtDe.js.br +0 -0
  67. package/apps/dashboard/dist/assets/tab-skills-tab-BpY0uZHW.js.br +0 -0
  68. package/apps/dashboard/dist/assets/tab-spending-tab-DEccQHnt.js.br +0 -0
  69. package/apps/dashboard/dist/assets/tab-swarm-chat-tab-BNrd88-r.js.br +0 -0
  70. package/apps/dashboard/dist/assets/tab-swarm-tab-B1AcjL1W.js.br +0 -0
  71. package/apps/dashboard/dist/assets/tab-usage-tab-BIOOnB-Y.js.br +0 -0
  72. package/apps/dashboard/dist/assets/tab-waves-tab-SaJDkb4x.js.br +0 -0
  73. package/apps/dashboard/dist/assets/tab-workflows-tab-B-soSy1k.js.br +0 -0
  74. package/apps/dashboard/dist/index.html.br +0 -0
  75. package/apps/dashboard/index.html +0 -6459
  76. package/apps/dashboard/package.json +0 -15
  77. package/apps/dashboard/src/app.js +0 -2823
  78. package/apps/dashboard/src/app.js.br +0 -0
  79. package/apps/dashboard/src/app.js.gz +0 -0
  80. package/apps/dashboard/src/chat/chat-actions.js +0 -1847
  81. package/apps/dashboard/src/chat/chat-actions.js.br +0 -0
  82. package/apps/dashboard/src/chat/unified-messages.js +0 -327
  83. package/apps/dashboard/src/chat/unified-messages.js.br +0 -0
  84. package/apps/dashboard/src/cli-process.js +0 -208
  85. package/apps/dashboard/src/cli-process.js.br +0 -0
  86. package/apps/dashboard/src/cli-process.js.gz +0 -0
  87. package/apps/dashboard/src/components/active-tasks-panel.js +0 -175
  88. package/apps/dashboard/src/components/active-tasks-panel.js.br +0 -0
  89. package/apps/dashboard/src/core/api.js +0 -18
  90. package/apps/dashboard/src/core/api.js.br +0 -0
  91. package/apps/dashboard/src/core/dom.js +0 -228
  92. package/apps/dashboard/src/core/dom.js.br +0 -0
  93. package/apps/dashboard/src/core/state.js +0 -91
  94. package/apps/dashboard/src/core/state.js.br +0 -0
  95. package/apps/dashboard/src/core/task-manager.js +0 -134
  96. package/apps/dashboard/src/core/task-manager.js.br +0 -0
  97. package/apps/dashboard/src/orchestration-status.js +0 -127
  98. package/apps/dashboard/src/orchestration-status.js.br +0 -0
  99. package/apps/dashboard/src/setup-wizard.js +0 -562
  100. package/apps/dashboard/src/setup-wizard.js.br +0 -0
  101. package/apps/dashboard/src/styles.css +0 -2085
  102. package/apps/dashboard/src/styles.css.br +0 -0
  103. package/apps/dashboard/src/styles.css.gz +0 -0
  104. package/apps/dashboard/src/tabs/agents-tab.js +0 -2237
  105. package/apps/dashboard/src/tabs/agents-tab.js.br +0 -0
  106. package/apps/dashboard/src/tabs/benchmarks-tab.js +0 -229
  107. package/apps/dashboard/src/tabs/benchmarks-tab.js.br +0 -0
  108. package/apps/dashboard/src/tabs/comms-tab.js +0 -955
  109. package/apps/dashboard/src/tabs/comms-tab.js.br +0 -0
  110. package/apps/dashboard/src/tabs/contacts-tab.js +0 -654
  111. package/apps/dashboard/src/tabs/contacts-tab.js.br +0 -0
  112. package/apps/dashboard/src/tabs/engines-tab.js +0 -175
  113. package/apps/dashboard/src/tabs/engines-tab.js.br +0 -0
  114. package/apps/dashboard/src/tabs/memory-tab.js +0 -182
  115. package/apps/dashboard/src/tabs/memory-tab.js.br +0 -0
  116. package/apps/dashboard/src/tabs/models-tab.js +0 -450
  117. package/apps/dashboard/src/tabs/models-tab.js.br +0 -0
  118. package/apps/dashboard/src/tabs/pm-loop-tab.js +0 -185
  119. package/apps/dashboard/src/tabs/pm-loop-tab.js.br +0 -0
  120. package/apps/dashboard/src/tabs/projects-tab.js +0 -663
  121. package/apps/dashboard/src/tabs/projects-tab.js.br +0 -0
  122. package/apps/dashboard/src/tabs/projects-tab.js.gz +0 -0
  123. package/apps/dashboard/src/tabs/prompts-tab.js +0 -160
  124. package/apps/dashboard/src/tabs/prompts-tab.js.br +0 -0
  125. package/apps/dashboard/src/tabs/services-tab.js +0 -202
  126. package/apps/dashboard/src/tabs/services-tab.js.br +0 -0
  127. package/apps/dashboard/src/tabs/settings-tab.js +0 -803
  128. package/apps/dashboard/src/tabs/settings-tab.js.br +0 -0
  129. package/apps/dashboard/src/tabs/skills-tab.js +0 -284
  130. package/apps/dashboard/src/tabs/skills-tab.js.br +0 -0
  131. package/apps/dashboard/src/tabs/spending-tab.js +0 -173
  132. package/apps/dashboard/src/tabs/spending-tab.js.br +0 -0
  133. package/apps/dashboard/src/tabs/swarm-chat-tab.js +0 -660
  134. package/apps/dashboard/src/tabs/swarm-chat-tab.js.br +0 -0
  135. package/apps/dashboard/src/tabs/swarm-tab.js +0 -538
  136. package/apps/dashboard/src/tabs/swarm-tab.js.br +0 -0
  137. package/apps/dashboard/src/tabs/usage-tab.js +0 -390
  138. package/apps/dashboard/src/tabs/usage-tab.js.br +0 -0
  139. package/apps/dashboard/src/tabs/waves-tab.js +0 -238
  140. package/apps/dashboard/src/tabs/waves-tab.js.br +0 -0
  141. package/apps/dashboard/src/tabs/workflows-tab.js +0 -747
  142. package/apps/dashboard/src/tabs/workflows-tab.js.br +0 -0
  143. package/apps/vibe/.crew/agent-memory/pipeline.json +0 -304
  144. package/apps/vibe/.crew/cost.json +0 -17
  145. package/apps/vibe/.crew/json-parse-metrics.jsonl +0 -27
  146. package/apps/vibe/.crew/pipeline-metrics.jsonl +0 -27
  147. package/apps/vibe/.crew/pipeline-runs/pipeline-0f90c392-2425-4ae5-850c-bd9d17b1d690.jsonl +0 -5
  148. package/apps/vibe/.crew/pipeline-runs/pipeline-1c269dd9-a63f-4fba-af81-5cf08048ef06.jsonl +0 -5
  149. package/apps/vibe/.crew/pipeline-runs/pipeline-288a7765-da24-4a22-89bc-1f3cc9b0562c.jsonl +0 -5
  150. package/apps/vibe/.crew/pipeline-runs/pipeline-2c78fd22-a657-4bd1-bc49-0679fb384409.jsonl +0 -5
  151. package/apps/vibe/.crew/pipeline-runs/pipeline-3da23550-22ed-4904-9a0a-8e79c1f3024c.jsonl +0 -5
  152. package/apps/vibe/.crew/pipeline-runs/pipeline-3e6fe08d-3264-404a-8df3-aab7efef10e7.jsonl +0 -5
  153. package/apps/vibe/.crew/pipeline-runs/pipeline-42eec610-57fe-4e09-9e7e-b315038495c2.jsonl +0 -5
  154. package/apps/vibe/.crew/pipeline-runs/pipeline-4438eb4c-ae13-42b1-90e2-b043d8983be8.jsonl +0 -5
  155. package/apps/vibe/.crew/pipeline-runs/pipeline-4740a9f5-86e7-44b6-a394-de433e291727.jsonl +0 -5
  156. package/apps/vibe/.crew/pipeline-runs/pipeline-49e1da6a-957e-48fd-9220-415019e4f8e2.jsonl +0 -5
  157. package/apps/vibe/.crew/pipeline-runs/pipeline-4c9251db-be68-427b-a3fc-a264f2b5778d.jsonl +0 -5
  158. package/apps/vibe/.crew/pipeline-runs/pipeline-6413fa33-a802-4b57-a8c0-a9056ad67842.jsonl +0 -5
  159. package/apps/vibe/.crew/pipeline-runs/pipeline-65e29a57-664d-4196-8109-017e364f182e.jsonl +0 -5
  160. package/apps/vibe/.crew/pipeline-runs/pipeline-6aa04bc5-9593-4b1f-b58d-3bf2978cb602.jsonl +0 -5
  161. package/apps/vibe/.crew/pipeline-runs/pipeline-6e1cba53-9b70-457e-99e0-59199149dd21.jsonl +0 -5
  162. package/apps/vibe/.crew/pipeline-runs/pipeline-749f41cc-4dac-4204-be64-873a6080a0d2.jsonl +0 -5
  163. package/apps/vibe/.crew/pipeline-runs/pipeline-74d68121-e181-4864-bd9a-c3211341dfaf.jsonl +0 -5
  164. package/apps/vibe/.crew/pipeline-runs/pipeline-8509bc24-142d-4e07-b44a-a50bf99d1103.jsonl +0 -5
  165. package/apps/vibe/.crew/pipeline-runs/pipeline-960339c6-07ca-43ce-9900-f6e1702b39b9.jsonl +0 -5
  166. package/apps/vibe/.crew/pipeline-runs/pipeline-9bef2dd2-6122-42e5-b3d9-19f4d80f9e40.jsonl +0 -5
  167. package/apps/vibe/.crew/pipeline-runs/pipeline-9c6480a9-7031-4146-b241-825b9a2d1de1.jsonl +0 -5
  168. package/apps/vibe/.crew/pipeline-runs/pipeline-9fd42426-8492-4157-9d5f-e1537c060489.jsonl +0 -2
  169. package/apps/vibe/.crew/pipeline-runs/pipeline-ad6d40a3-2f5e-46a9-a345-47caaccc51aa.jsonl +0 -5
  170. package/apps/vibe/.crew/pipeline-runs/pipeline-bc606133-8d5b-4535-8d85-f1a29cdaa981.jsonl +0 -5
  171. package/apps/vibe/.crew/pipeline-runs/pipeline-c1418f4e-b773-4ca1-84a3-216acf36e2f2.jsonl +0 -5
  172. package/apps/vibe/.crew/pipeline-runs/pipeline-c1a13ccd-634a-4d01-a4a7-1177b8a752ff.jsonl +0 -5
  173. package/apps/vibe/.crew/pipeline-runs/pipeline-c7d27b42-249e-4bd4-8f26-6aa998110b8a.jsonl +0 -5
  174. package/apps/vibe/.crew/pipeline-runs/pipeline-cca2e9b9-4a34-4d25-a311-5c793fa7e91e.jsonl +0 -5
  175. package/apps/vibe/.crew/sandbox.json +0 -7
  176. package/apps/vibe/.crew/session.json +0 -330
  177. package/apps/vibe/.crew/training-data.jsonl +0 -0
  178. package/apps/vibe/.github/workflows/studio-quality.yml +0 -37
  179. package/apps/vibe/.studio-data/project-messages/chuck-norris.jsonl +0 -18
  180. package/apps/vibe/.studio-data/project-messages/general.jsonl +0 -81
  181. package/apps/vibe/.studio-data/project-messages/studio-local.jsonl +0 -18
  182. package/apps/vibe/ARCHITECTURE.md +0 -3393
  183. package/apps/vibe/QUICK-REFERENCE.md +0 -211
  184. package/apps/vibe/ROADMAP.md +0 -41
  185. package/apps/vibe/STUDIO-SETUP-COMPLETE.md +0 -35
  186. package/apps/vibe/VISUAL-GUIDE.md +0 -378
  187. package/apps/vibe/capture-demo.mjs +0 -160
  188. package/apps/vibe/capture-full-demo.mjs +0 -255
  189. package/apps/vibe/capture-quickstart.mjs +0 -256
  190. package/apps/vibe/capture-vibe-assets.mjs +0 -71
  191. package/apps/vibe/capture-vibe-video.mjs +0 -260
  192. package/apps/vibe/check-buttons.js +0 -41
  193. package/apps/vibe/diagnose.html +0 -106
  194. package/apps/vibe/fix-buttons.js +0 -103
  195. package/apps/vibe/index.html +0 -3404
  196. package/apps/vibe/package-lock.json +0 -920
  197. package/apps/vibe/scripts/studio-pty-host.py +0 -117
  198. package/apps/vibe/src/main.js +0 -2940
  199. package/apps/vibe/src/register-all-languages.js +0 -98
  200. package/apps/vibe/start-studio.sh +0 -11
  201. package/apps/vibe/test/accessibility-tests.js +0 -77
  202. package/apps/vibe/test/browser-performance-audit.mjs +0 -205
  203. package/apps/vibe/test/performance-tests.js +0 -120
  204. package/apps/vibe/test/security-tests.js +0 -213
  205. package/apps/vibe/tests/e2e.local.mjs +0 -54
  206. package/apps/vibe/tests/server.smoke.mjs +0 -106
  207. package/apps/vibe/update_website.mjs +0 -74
  208. package/apps/vibe/vite.config.js +0 -19
  209. package/lib/crew-lead/chat-handler.mjs.bak +0 -1274
  210. package/lib/engines/rt-envelope.mjs.backup-current +0 -870
@@ -1,213 +0,0 @@
1
- import assert from "node:assert/strict";
2
- import { once } from "node:events";
3
- import fs from "node:fs/promises";
4
- import syncFs from "node:fs";
5
- import path from "node:path";
6
- import { spawn } from "node:child_process";
7
- import { setTimeout as delay } from "node:timers/promises";
8
- import { fileURLToPath } from "node:url";
9
- import { chromium } from "playwright";
10
-
11
- const __dirname = path.dirname(fileURLToPath(import.meta.url));
12
- const rootDir = path.resolve(__dirname, "..");
13
- const reportDir = path.join(rootDir, "output");
14
- const reportPath = path.join(reportDir, "performance-audit.json");
15
- const port = Number(process.env.STUDIO_AUDIT_PORT || 3345);
16
- const baseUrl = `http://127.0.0.1:${port}`;
17
- const systemChrome = [
18
- "/Applications/Google Chrome.app/Contents/MacOS/Google Chrome",
19
- "/Applications/Google Chrome Canary.app/Contents/MacOS/Google Chrome Canary",
20
- ].find((candidate) => syncFs.existsSync(candidate));
21
-
22
- const BUDGETS = {
23
- domContentLoadedMs: 2500,
24
- loadMs: 4000,
25
- lcpMs: 2500,
26
- resourceCount: 40,
27
- totalTransferBytes: 1_500_000,
28
- jsHeapUsedBytes: 80 * 1024 * 1024,
29
- longTasks: 3,
30
- };
31
-
32
- async function ensureBuildOutput() {
33
- await fs.access(path.join(rootDir, "dist", "index.html"));
34
- }
35
-
36
- async function waitForServer(url, timeoutMs = 15_000) {
37
- const deadline = Date.now() + timeoutMs;
38
- let lastError = null;
39
-
40
- while (Date.now() < deadline) {
41
- try {
42
- const response = await fetch(url);
43
- if (response.ok) {
44
- return;
45
- }
46
- lastError = new Error(`HTTP ${response.status}`);
47
- } catch (error) {
48
- lastError = error;
49
- }
50
- await delay(250);
51
- }
52
-
53
- throw lastError || new Error("Studio server did not become ready");
54
- }
55
-
56
- function startServer() {
57
- const child = spawn(process.execPath, ["server.mjs"], {
58
- cwd: rootDir,
59
- env: {
60
- ...process.env,
61
- STUDIO_PORT: String(port),
62
- },
63
- stdio: "ignore",
64
- });
65
- return child;
66
- }
67
-
68
- async function collectMetrics() {
69
- const browser = await chromium.launch({
70
- headless: true,
71
- ...(systemChrome ? { executablePath: systemChrome } : {}),
72
- });
73
- const page = await browser.newPage();
74
- const cdp = await page.context().newCDPSession(page);
75
-
76
- await page.addInitScript(() => {
77
- window.__studioPerf = {
78
- lcp: 0,
79
- cls: 0,
80
- longTasks: 0,
81
- longTaskTime: 0,
82
- };
83
-
84
- new PerformanceObserver((list) => {
85
- const entries = list.getEntries();
86
- const lastEntry = entries.at(-1);
87
- if (lastEntry) {
88
- window.__studioPerf.lcp = lastEntry.startTime;
89
- }
90
- }).observe({ type: "largest-contentful-paint", buffered: true });
91
-
92
- new PerformanceObserver((list) => {
93
- for (const entry of list.getEntries()) {
94
- if (!entry.hadRecentInput) {
95
- window.__studioPerf.cls += entry.value;
96
- }
97
- }
98
- }).observe({ type: "layout-shift", buffered: true });
99
-
100
- new PerformanceObserver((list) => {
101
- for (const entry of list.getEntries()) {
102
- window.__studioPerf.longTasks += 1;
103
- window.__studioPerf.longTaskTime += entry.duration;
104
- }
105
- }).observe({ type: "longtask", buffered: true });
106
- });
107
-
108
- await cdp.send("Performance.enable");
109
- await page.goto(baseUrl, { waitUntil: "domcontentloaded", timeout: 15_000 });
110
- await page.waitForLoadState("load", { timeout: 15_000 });
111
- await delay(750);
112
-
113
- const browserMetrics = await cdp.send("Performance.getMetrics");
114
- const runtimeMetrics = await page.evaluate(() => {
115
- const navigation = performance.getEntriesByType("navigation")[0];
116
- const resources = performance.getEntriesByType("resource");
117
- const totals = resources.reduce(
118
- (acc, entry) => {
119
- acc.transferSize += entry.transferSize || 0;
120
- if (entry.initiatorType === "script") {
121
- acc.scriptTransferSize += entry.transferSize || 0;
122
- }
123
- return acc;
124
- },
125
- { transferSize: 0, scriptTransferSize: 0 },
126
- );
127
-
128
- return {
129
- domContentLoadedMs: navigation?.domContentLoadedEventEnd || 0,
130
- loadMs: navigation?.loadEventEnd || 0,
131
- resourceCount: resources.length,
132
- totalTransferBytes: totals.transferSize,
133
- scriptTransferBytes: totals.scriptTransferSize,
134
- lcpMs: window.__studioPerf?.lcp || 0,
135
- cls: window.__studioPerf?.cls || 0,
136
- longTasks: window.__studioPerf?.longTasks || 0,
137
- longTaskTimeMs: window.__studioPerf?.longTaskTime || 0,
138
- };
139
- });
140
-
141
- await browser.close();
142
-
143
- const cdpMetricMap = Object.fromEntries(
144
- browserMetrics.metrics.map((metric) => [metric.name, metric.value]),
145
- );
146
-
147
- return {
148
- collectedAt: new Date().toISOString(),
149
- url: baseUrl,
150
- budgets: BUDGETS,
151
- metrics: {
152
- ...runtimeMetrics,
153
- jsHeapUsedBytes: cdpMetricMap.JSHeapUsedSize || 0,
154
- nodes: cdpMetricMap.Nodes || 0,
155
- documents: cdpMetricMap.Documents || 0,
156
- },
157
- };
158
- }
159
-
160
- function evaluateBudgets(report) {
161
- const { metrics } = report;
162
-
163
- const checks = [
164
- ["domContentLoadedMs", metrics.domContentLoadedMs <= BUDGETS.domContentLoadedMs],
165
- ["loadMs", metrics.loadMs <= BUDGETS.loadMs],
166
- ["resourceCount", metrics.resourceCount <= BUDGETS.resourceCount],
167
- ["totalTransferBytes", metrics.totalTransferBytes <= BUDGETS.totalTransferBytes],
168
- ["jsHeapUsedBytes", metrics.jsHeapUsedBytes <= BUDGETS.jsHeapUsedBytes],
169
- ["longTasks", metrics.longTasks <= BUDGETS.longTasks],
170
- ];
171
-
172
- if (metrics.lcpMs > 0) {
173
- checks.push(["lcpMs", metrics.lcpMs <= BUDGETS.lcpMs]);
174
- }
175
-
176
- report.checks = checks.map(([name, pass]) => ({ name, pass }));
177
- report.ok = report.checks.every((check) => check.pass);
178
- }
179
-
180
- async function main() {
181
- await ensureBuildOutput();
182
- await fs.mkdir(reportDir, { recursive: true });
183
-
184
- console.log("Starting Studio server for performance audit...");
185
- const server = startServer();
186
-
187
- try {
188
- console.log("Waiting for Studio server...");
189
- await waitForServer(baseUrl);
190
- console.log("Collecting browser metrics...");
191
- const report = await collectMetrics();
192
- console.log("Evaluating budgets...");
193
- evaluateBudgets(report);
194
- await fs.writeFile(reportPath, `${JSON.stringify(report, null, 2)}\n`, "utf8");
195
-
196
- console.log(`Performance audit written to ${reportPath}`);
197
- report.checks.forEach((check) => {
198
- console.log(`${check.pass ? "PASS" : "FAIL"} ${check.name}`);
199
- });
200
-
201
- assert.ok(report.ok, "Studio performance audit exceeded one or more budgets");
202
- } finally {
203
- if (server.exitCode === null && !server.killed) {
204
- server.kill("SIGTERM");
205
- await Promise.race([once(server, "exit"), delay(2_000)]);
206
- }
207
- }
208
- }
209
-
210
- main().catch((error) => {
211
- console.error(error.stack || error.message);
212
- process.exitCode = 1;
213
- });
@@ -1,54 +0,0 @@
1
- import assert from "node:assert/strict";
2
- import fs from "node:fs/promises";
3
- import os from "node:os";
4
- import path from "node:path";
5
-
6
- process.env.STUDIO_DISABLE_LISTEN = "1";
7
- process.env.STUDIO_DATA_DIR = path.join(process.cwd(), ".tmp-e2e-data");
8
-
9
- const { createOrUpdateProject, listWorkspaceFiles, readProjects } = await import("../server.mjs");
10
-
11
- const projectDir = await fs.mkdtemp(
12
- path.join(os.tmpdir(), "crewswarm-vibe-e2e-"),
13
- );
14
-
15
- try {
16
- const created = createOrUpdateProject({
17
- name: "E2E Project",
18
- description: "Local E2E check",
19
- outputDir: projectDir,
20
- });
21
- assert.equal(created.status, 200);
22
-
23
- await fs.writeFile(
24
- path.join(projectDir, "README.md"),
25
- "# E2E Project\n\nLocal test file.\n",
26
- "utf8",
27
- );
28
-
29
- const projectsPayload = {
30
- projects: readProjects(),
31
- };
32
- assert.ok(
33
- projectsPayload.projects.some((project) => project.id === created.payload.project.id),
34
- );
35
-
36
- const filesPayload = {
37
- files: listWorkspaceFiles(projectDir),
38
- };
39
- assert.ok(filesPayload.files.some((entry) => entry.path.endsWith("README.md")));
40
-
41
- const filePayload = {
42
- content: await fs.readFile(path.join(projectDir, "README.md"), "utf8"),
43
- };
44
- assert.match(filePayload.content, /Local test file/);
45
-
46
- const distIndex = await fs.readFile(path.join(process.cwd(), "dist", "index.html"), "utf8");
47
- assert.match(distIndex, /toggle-bottom-terminal/);
48
- assert.doesNotMatch(distIndex, /cdn\.jsdelivr\.net\/npm\/xterm/);
49
-
50
- console.log("Studio local e2e checks passed");
51
- } finally {
52
- await fs.rm(projectDir, { recursive: true, force: true });
53
- await fs.rm(process.env.STUDIO_DATA_DIR, { recursive: true, force: true });
54
- }
@@ -1,106 +0,0 @@
1
- import assert from "node:assert/strict";
2
- import path from "node:path";
3
- import fs from "node:fs/promises";
4
- import { fileURLToPath } from "node:url";
5
-
6
- const __dirname = path.dirname(fileURLToPath(import.meta.url));
7
- const rootDir = path.resolve(__dirname, "..");
8
-
9
- // Set env vars to avoid side effects during import
10
- process.env.STUDIO_DISABLE_LISTEN = "1";
11
- process.env.STUDIO_DATA_DIR = path.join(rootDir, ".tmp-smoke-data");
12
-
13
- const {
14
- ensureDataDirs,
15
- readProjects,
16
- listWorkspaceFiles,
17
- createOrUpdateProject,
18
- createTerminalSession,
19
- } = await import("../server.mjs");
20
-
21
- async function runSmokeTests() {
22
- console.log("Starting Studio smoke tests...");
23
-
24
- try {
25
- // 1. Data directories
26
- ensureDataDirs();
27
- const dataDirExists = await fs.stat(process.env.STUDIO_DATA_DIR).then(s => s.isDirectory()).catch(() => false);
28
- assert.ok(dataDirExists, "Data directory should be created");
29
-
30
- // 2. Projects
31
- const projects = readProjects();
32
- assert.ok(Array.isArray(projects), "Projects should be an array");
33
- assert.ok(projects.length > 0, "Should have at least one project");
34
- assert.ok(
35
- projects.some((project) => project.id === "studio-local"),
36
- "Projects should include the default studio-local workspace",
37
- );
38
-
39
- // 3. Workspace files
40
- const files = listWorkspaceFiles(rootDir);
41
- console.log(`Found ${files.length} files in ${rootDir}`);
42
- if (files.length > 0) {
43
- console.log("Sample file paths:", files.slice(0, 5).map(f => f.path));
44
- }
45
- assert.ok(Array.isArray(files), "Files should be an array");
46
- assert.ok(files.some(f => f.path.endsWith("package.json")), "Should find package.json in root");
47
-
48
- // 4. Create project
49
- const tempProjectDir = await fs.mkdtemp(path.join(rootDir, ".tmp-project-"));
50
- const newProject = {
51
- name: "Smoke Test Project",
52
- description: "Temporary project for smoke test",
53
- outputDir: tempProjectDir
54
- };
55
- const result = createOrUpdateProject(newProject);
56
- assert.equal(result.status, 200, "Should create project successfully");
57
- assert.ok(result.payload.project.id, "Created project should have an ID");
58
-
59
- // 5. Terminal session
60
- process.env.STUDIO_SHELL_BIN = "/bin/sh";
61
- process.env.STUDIO_SHELL_ARGS_JSON = JSON.stringify([
62
- "-lc",
63
- "printf terminal-smoke-ready\\n",
64
- ]);
65
- const terminalOutput = [];
66
- let terminalExitCode = null;
67
- await new Promise((resolve, reject) => {
68
- const timeout = setTimeout(() => {
69
- reject(new Error("Terminal smoke test timed out"));
70
- }, 5000);
71
-
72
- createTerminalSession({
73
- projectDir: rootDir,
74
- cols: 80,
75
- rows: 24,
76
- onData(chunk) {
77
- terminalOutput.push(chunk);
78
- },
79
- onExit(code) {
80
- terminalExitCode = code;
81
- clearTimeout(timeout);
82
- resolve();
83
- },
84
- });
85
- });
86
- assert.equal(terminalExitCode, 0, "Terminal session should exit cleanly");
87
- assert.match(
88
- terminalOutput.join(""),
89
- /terminal-smoke-ready/,
90
- "Terminal should produce shell output",
91
- );
92
-
93
- // Cleanup temp project dir
94
- await fs.rm(tempProjectDir, { recursive: true, force: true });
95
-
96
- console.log("Studio smoke tests passed!");
97
- } finally {
98
- // Cleanup smoke data dir
99
- await fs.rm(process.env.STUDIO_DATA_DIR, { recursive: true, force: true });
100
- }
101
- }
102
-
103
- runSmokeTests().catch(err => {
104
- console.error("Smoke test failed:", err);
105
- process.exit(1);
106
- });
@@ -1,74 +0,0 @@
1
- import fs from 'fs';
2
- import path from 'path';
3
-
4
- const INDEX_PATH = '../website/index.html';
5
- let html = fs.readFileSync(INDEX_PATH, 'utf8');
6
-
7
- console.log('🚀 Updating crewswarm.ai marketing site...');
8
-
9
- // 1. Tagline & Agent Count Consistency
10
- // Ensuring all instances of 20 or 21 are updated to "21+" for future-proofing
11
- html = html.replace('<h1>One idea.<br/>One build.<br/>', '<h1>One idea.<br/>One build.<br/>');
12
- html = html.replace(/20 specialist agents/g, '21+ specialist agents');
13
- html = html.replace(/21-agent specialist crew/g, '21+ specialist agent crew');
14
-
15
- // 2. Add Vibe to Control Surfaces (Replacing CrewChat cs-item)
16
- const crewChatCsItem = `<div class="cs-item cs-native">
17
- <strong>CrewChat</strong>
18
- <span>Menu bar app — same conversation, one click away</span>
19
- </div>`;
20
-
21
- const vibeCsItem = `<div class="cs-item cs-native">
22
- <strong><a href="vibe.html" style="color:var(--accent);">crewswarm Vibe</a></strong>
23
- <span>Browser-native IDE with Monaco — real-time file tree + agent chat.</span>
24
- </div>
25
- <div class="cs-item cs-native">
26
- <strong>CrewChat v2.0</strong>
27
- <span>Quick & Advanced modes — multimodal image + voice support.</span>
28
- </div>`;
29
-
30
- html = html.replace(crewChatCsItem, vibeCsItem);
31
-
32
- // 3. Update Shared Memory (Replacing Tech Badge)
33
- const sharedMemoryBadge = `<div class="tech-badge">
34
- <img src="https://cdn.simpleicons.org/markdown/94a3b8" alt="Markdown" width="28" height="28" loading="lazy">
35
- <div>
36
- <strong>Shared Memory</strong>
37
- <span>Markdown — current-state, decisions, handoff, roadmap</span>
38
- </div>
39
- </div>`;
40
-
41
- const ragMemoryBadge = `<div class="tech-badge">
42
- <img src="https://cdn.simpleicons.org/markdown/94a3b8" alt="Markdown" width="28" height="28" loading="lazy">
43
- <div>
44
- <strong>Shared Memory RAG</strong>
45
- <span>Semantic search over history via local TF-IDF (no API calls).</span>
46
- </div>
47
- </div>
48
- <div class="tech-badge">
49
- <div style="font-size:24px;">🌊</div>
50
- <div>
51
- <strong>Wave Orchestration</strong>
52
- <span>Parallel task dispatch — 10x faster concurrent builds.</span>
53
- </div>
54
- </div>`;
55
-
56
- html = html.replace(sharedMemoryBadge, ragMemoryBadge);
57
-
58
- // 4. Update Execution Engines (Add Gemini CLI)
59
- html = html.replace('Codex CLI', 'Codex CLI, and Gemini CLI');
60
-
61
- // 5. Add Waves FAQ
62
- const faqListStart = '<div class="faq-list" id="faqList">';
63
- const waveFaq = ` <div class="faq-item">
64
- <button class="faq-question" aria-expanded="false">
65
- <span>What are "Waves" and parallel dispatch?</span>
66
- <span class="faq-icon">+</span>
67
- </button>
68
- <div class="faq-answer"><div class="faq-answer-inner"><p>Waves allow multiple specialists (like crew-coder and crew-qa) to work simultaneously on different parts of the same project. Tasks in Wave 1 must finish before Wave 2 starts, but everything inside a wave runs in parallel.</p></div></div>
69
- </div>`;
70
-
71
- html = html.replace(faqListStart, faqListStart + '\n' + waveFaq);
72
-
73
- fs.writeFileSync(INDEX_PATH, html);
74
- console.log('✨ Website updated successfully!');
@@ -1,19 +0,0 @@
1
- import { defineConfig } from "vite";
2
-
3
- export default defineConfig({
4
- server: {
5
- port: 3333,
6
- strictPort: true,
7
- host: "127.0.0.1",
8
- },
9
- build: {
10
- outDir: "dist",
11
- assetsDir: "assets",
12
- },
13
- optimizeDeps: {
14
- include: ["monaco-editor"],
15
- },
16
- worker: {
17
- format: "es",
18
- },
19
- });