everything-dev 0.3.3 → 1.3.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 (313) hide show
  1. package/README.md +64 -0
  2. package/cli.js +10 -0
  3. package/dist/_virtual/_rolldown/runtime.cjs +29 -0
  4. package/dist/api-contract.cjs +172 -0
  5. package/dist/api-contract.cjs.map +1 -0
  6. package/dist/api-contract.mjs +171 -0
  7. package/dist/api-contract.mjs.map +1 -0
  8. package/dist/api.cjs +124 -0
  9. package/dist/api.cjs.map +1 -0
  10. package/dist/api.d.cts +36 -0
  11. package/dist/api.d.cts.map +1 -0
  12. package/dist/api.d.mts +36 -0
  13. package/dist/api.d.mts.map +1 -0
  14. package/dist/api.mjs +119 -0
  15. package/dist/api.mjs.map +1 -0
  16. package/dist/app.cjs +156 -0
  17. package/dist/app.cjs.map +1 -0
  18. package/dist/app.mjs +153 -0
  19. package/dist/app.mjs.map +1 -0
  20. package/dist/cli/catalog.cjs +30 -0
  21. package/dist/cli/catalog.cjs.map +1 -0
  22. package/dist/cli/catalog.mjs +29 -0
  23. package/dist/cli/catalog.mjs.map +1 -0
  24. package/dist/cli/help.cjs +16 -0
  25. package/dist/cli/help.cjs.map +1 -0
  26. package/dist/cli/help.mjs +16 -0
  27. package/dist/cli/help.mjs.map +1 -0
  28. package/dist/cli/init.cjs +287 -0
  29. package/dist/cli/init.cjs.map +1 -0
  30. package/dist/cli/init.d.cts +36 -0
  31. package/dist/cli/init.d.cts.map +1 -0
  32. package/dist/cli/init.d.mts +36 -0
  33. package/dist/cli/init.d.mts.map +1 -0
  34. package/dist/cli/init.mjs +279 -0
  35. package/dist/cli/init.mjs.map +1 -0
  36. package/dist/cli/parse.cjs +96 -0
  37. package/dist/cli/parse.cjs.map +1 -0
  38. package/dist/cli/parse.mjs +95 -0
  39. package/dist/cli/parse.mjs.map +1 -0
  40. package/dist/cli/prompts.cjs +42 -0
  41. package/dist/cli/prompts.cjs.map +1 -0
  42. package/dist/cli/prompts.mjs +41 -0
  43. package/dist/cli/prompts.mjs.map +1 -0
  44. package/dist/cli.cjs +167 -0
  45. package/dist/cli.cjs.map +1 -0
  46. package/dist/cli.d.cts +1 -0
  47. package/dist/cli.d.mts +1 -0
  48. package/dist/cli.mjs +166 -0
  49. package/dist/cli.mjs.map +1 -0
  50. package/dist/components/dev-view.cjs +307 -0
  51. package/dist/components/dev-view.cjs.map +1 -0
  52. package/dist/components/dev-view.mjs +306 -0
  53. package/dist/components/dev-view.mjs.map +1 -0
  54. package/dist/components/streaming-view.cjs +146 -0
  55. package/dist/components/streaming-view.cjs.map +1 -0
  56. package/dist/components/streaming-view.mjs +144 -0
  57. package/dist/components/streaming-view.mjs.map +1 -0
  58. package/dist/config.cjs +280 -0
  59. package/dist/config.cjs.map +1 -0
  60. package/dist/config.d.cts +35 -0
  61. package/dist/config.d.cts.map +1 -0
  62. package/dist/config.d.mts +35 -0
  63. package/dist/config.d.mts.map +1 -0
  64. package/dist/config.mjs +266 -0
  65. package/dist/config.mjs.map +1 -0
  66. package/dist/contract.cjs +209 -0
  67. package/dist/contract.cjs.map +1 -0
  68. package/dist/contract.d.cts +490 -0
  69. package/dist/contract.d.cts.map +1 -0
  70. package/dist/contract.d.mts +490 -0
  71. package/dist/contract.d.mts.map +1 -0
  72. package/dist/contract.meta.cjs +104 -0
  73. package/dist/contract.meta.cjs.map +1 -0
  74. package/dist/contract.meta.d.cts +141 -0
  75. package/dist/contract.meta.d.cts.map +1 -0
  76. package/dist/contract.meta.d.mts +141 -0
  77. package/dist/contract.meta.d.mts.map +1 -0
  78. package/dist/contract.meta.mjs +102 -0
  79. package/dist/contract.meta.mjs.map +1 -0
  80. package/dist/contract.mjs +186 -0
  81. package/dist/contract.mjs.map +1 -0
  82. package/dist/dev-logs.cjs +53 -0
  83. package/dist/dev-logs.cjs.map +1 -0
  84. package/dist/dev-logs.mjs +51 -0
  85. package/dist/dev-logs.mjs.map +1 -0
  86. package/dist/dev-session.cjs +195 -0
  87. package/dist/dev-session.cjs.map +1 -0
  88. package/dist/dev-session.mjs +194 -0
  89. package/dist/dev-session.mjs.map +1 -0
  90. package/dist/fastkv.cjs +89 -0
  91. package/dist/fastkv.cjs.map +1 -0
  92. package/dist/fastkv.d.cts +11 -0
  93. package/dist/fastkv.d.cts.map +1 -0
  94. package/dist/fastkv.d.mts +11 -0
  95. package/dist/fastkv.d.mts.map +1 -0
  96. package/dist/fastkv.mjs +82 -0
  97. package/dist/fastkv.mjs.map +1 -0
  98. package/dist/federation.server.cjs +27 -0
  99. package/dist/federation.server.cjs.map +1 -0
  100. package/dist/federation.server.mjs +27 -0
  101. package/dist/federation.server.mjs.map +1 -0
  102. package/dist/host.cjs +367 -0
  103. package/dist/host.cjs.map +1 -0
  104. package/dist/host.d.cts +22 -0
  105. package/dist/host.d.cts.map +1 -0
  106. package/dist/host.d.mts +22 -0
  107. package/dist/host.d.mts.map +1 -0
  108. package/dist/host.mjs +364 -0
  109. package/dist/host.mjs.map +1 -0
  110. package/dist/index.cjs +122 -0
  111. package/dist/index.d.cts +7 -0
  112. package/dist/index.d.mts +7 -0
  113. package/dist/index.mjs +9 -0
  114. package/dist/integrity.cjs +39 -0
  115. package/dist/integrity.cjs.map +1 -0
  116. package/dist/integrity.d.cts +7 -0
  117. package/dist/integrity.d.cts.map +1 -0
  118. package/dist/integrity.d.mts +7 -0
  119. package/dist/integrity.d.mts.map +1 -0
  120. package/dist/integrity.mjs +35 -0
  121. package/dist/integrity.mjs.map +1 -0
  122. package/dist/internal/manifest-normalizer.cjs +140 -0
  123. package/dist/internal/manifest-normalizer.cjs.map +1 -0
  124. package/dist/internal/manifest-normalizer.mjs +138 -0
  125. package/dist/internal/manifest-normalizer.mjs.map +1 -0
  126. package/dist/mf.cjs +77 -0
  127. package/dist/mf.cjs.map +1 -0
  128. package/dist/mf.d.cts +19 -0
  129. package/dist/mf.d.cts.map +1 -0
  130. package/dist/mf.d.mts +19 -0
  131. package/dist/mf.d.mts.map +1 -0
  132. package/dist/mf.mjs +71 -0
  133. package/dist/mf.mjs.map +1 -0
  134. package/dist/near-cli.cjs +196 -0
  135. package/dist/near-cli.cjs.map +1 -0
  136. package/dist/near-cli.mjs +193 -0
  137. package/dist/near-cli.mjs.map +1 -0
  138. package/dist/network.cjs +9 -0
  139. package/dist/network.cjs.map +1 -0
  140. package/dist/network.mjs +8 -0
  141. package/dist/network.mjs.map +1 -0
  142. package/dist/orchestrator.cjs +441 -0
  143. package/dist/orchestrator.cjs.map +1 -0
  144. package/dist/orchestrator.d.cts +40 -0
  145. package/dist/orchestrator.d.cts.map +1 -0
  146. package/dist/orchestrator.d.mts +40 -0
  147. package/dist/orchestrator.d.mts.map +1 -0
  148. package/dist/orchestrator.mjs +436 -0
  149. package/dist/orchestrator.mjs.map +1 -0
  150. package/dist/plugin.cjs +830 -0
  151. package/dist/plugin.cjs.map +1 -0
  152. package/dist/plugin.d.cts +347 -0
  153. package/dist/plugin.d.cts.map +1 -0
  154. package/dist/plugin.d.mts +348 -0
  155. package/dist/plugin.d.mts.map +1 -0
  156. package/dist/plugin.mjs +827 -0
  157. package/dist/plugin.mjs.map +1 -0
  158. package/dist/process-registry.cjs +120 -0
  159. package/dist/process-registry.cjs.map +1 -0
  160. package/dist/process-registry.d.cts +25 -0
  161. package/dist/process-registry.d.cts.map +1 -0
  162. package/dist/process-registry.d.mts +25 -0
  163. package/dist/process-registry.d.mts.map +1 -0
  164. package/dist/process-registry.mjs +119 -0
  165. package/dist/process-registry.mjs.map +1 -0
  166. package/dist/sdk.cjs +61 -0
  167. package/dist/sdk.d.cts +5 -0
  168. package/dist/sdk.d.mts +5 -0
  169. package/dist/sdk.mjs +6 -0
  170. package/dist/shared.cjs +143 -0
  171. package/dist/shared.cjs.map +1 -0
  172. package/dist/shared.d.cts +33 -0
  173. package/dist/shared.d.cts.map +1 -0
  174. package/dist/shared.d.mts +33 -0
  175. package/dist/shared.d.mts.map +1 -0
  176. package/dist/shared.mjs +140 -0
  177. package/dist/shared.mjs.map +1 -0
  178. package/dist/types.cjs +160 -0
  179. package/dist/types.cjs.map +1 -0
  180. package/dist/types.d.cts +269 -0
  181. package/dist/types.d.cts.map +1 -0
  182. package/dist/types.d.mts +269 -0
  183. package/dist/types.d.mts.map +1 -0
  184. package/dist/types.mjs +144 -0
  185. package/dist/types.mjs.map +1 -0
  186. package/dist/ui/head.cjs +67 -0
  187. package/dist/ui/head.cjs.map +1 -0
  188. package/dist/ui/head.d.cts +19 -0
  189. package/dist/ui/head.d.cts.map +1 -0
  190. package/dist/ui/head.d.mts +19 -0
  191. package/dist/ui/head.d.mts.map +1 -0
  192. package/dist/ui/head.mjs +61 -0
  193. package/dist/ui/head.mjs.map +1 -0
  194. package/dist/ui/index.cjs +32 -0
  195. package/dist/ui/index.d.cts +7 -0
  196. package/dist/ui/index.d.mts +7 -0
  197. package/dist/ui/index.mjs +6 -0
  198. package/dist/ui/metadata.cjs +106 -0
  199. package/dist/ui/metadata.cjs.map +1 -0
  200. package/dist/ui/metadata.d.cts +35 -0
  201. package/dist/ui/metadata.d.cts.map +1 -0
  202. package/dist/ui/metadata.d.mts +35 -0
  203. package/dist/ui/metadata.d.mts.map +1 -0
  204. package/dist/ui/metadata.mjs +100 -0
  205. package/dist/ui/metadata.mjs.map +1 -0
  206. package/dist/ui/router.cjs +56 -0
  207. package/dist/ui/router.cjs.map +1 -0
  208. package/dist/ui/router.d.cts +11 -0
  209. package/dist/ui/router.d.cts.map +1 -0
  210. package/dist/ui/router.d.mts +11 -0
  211. package/dist/ui/router.d.mts.map +1 -0
  212. package/dist/ui/router.mjs +51 -0
  213. package/dist/ui/router.mjs.map +1 -0
  214. package/dist/ui/runtime.cjs +65 -0
  215. package/dist/ui/runtime.cjs.map +1 -0
  216. package/dist/ui/runtime.d.cts +29 -0
  217. package/dist/ui/runtime.d.cts.map +1 -0
  218. package/dist/ui/runtime.d.mts +29 -0
  219. package/dist/ui/runtime.d.mts.map +1 -0
  220. package/dist/ui/runtime.mjs +53 -0
  221. package/dist/ui/runtime.mjs.map +1 -0
  222. package/dist/ui/types.cjs +0 -0
  223. package/dist/ui/types.d.cts +52 -0
  224. package/dist/ui/types.d.cts.map +1 -0
  225. package/dist/ui/types.d.mts +52 -0
  226. package/dist/ui/types.d.mts.map +1 -0
  227. package/dist/ui/types.mjs +1 -0
  228. package/dist/utils/banner.cjs +24 -0
  229. package/dist/utils/banner.cjs.map +1 -0
  230. package/dist/utils/banner.mjs +23 -0
  231. package/dist/utils/banner.mjs.map +1 -0
  232. package/dist/utils/linkify.cjs +15 -0
  233. package/dist/utils/linkify.cjs.map +1 -0
  234. package/dist/utils/linkify.mjs +14 -0
  235. package/dist/utils/linkify.mjs.map +1 -0
  236. package/dist/utils/run.cjs +40 -0
  237. package/dist/utils/run.cjs.map +1 -0
  238. package/dist/utils/run.mjs +39 -0
  239. package/dist/utils/run.mjs.map +1 -0
  240. package/dist/utils/theme.cjs +44 -0
  241. package/dist/utils/theme.cjs.map +1 -0
  242. package/dist/utils/theme.mjs +37 -0
  243. package/dist/utils/theme.mjs.map +1 -0
  244. package/package.json +269 -80
  245. package/src/api-contract.ts +309 -0
  246. package/src/api.ts +181 -0
  247. package/src/app.ts +346 -0
  248. package/src/cli/catalog.ts +49 -0
  249. package/src/cli/help.ts +13 -0
  250. package/src/cli/init.ts +386 -0
  251. package/src/cli/parse.ts +130 -0
  252. package/src/cli/prompts.ts +64 -0
  253. package/src/cli.ts +203 -1507
  254. package/src/components/dev-view.tsx +307 -255
  255. package/src/components/streaming-view.ts +164 -128
  256. package/src/config.ts +462 -532
  257. package/src/contract.meta.ts +96 -0
  258. package/src/contract.ts +164 -561
  259. package/src/dev-logs.ts +85 -0
  260. package/src/dev-session.ts +318 -0
  261. package/src/fastkv.ts +153 -0
  262. package/src/federation.server.ts +43 -0
  263. package/src/host.ts +526 -0
  264. package/src/index.ts +6 -3
  265. package/src/integrity.ts +54 -0
  266. package/src/internal/manifest-normalizer.ts +251 -0
  267. package/src/mf.ts +105 -0
  268. package/src/near-cli.ts +284 -0
  269. package/src/network.ts +3 -0
  270. package/src/orchestrator.ts +648 -0
  271. package/src/plugin.ts +1130 -2311
  272. package/src/process-registry.ts +154 -0
  273. package/src/scripts/sync-api-contract.ts +24 -0
  274. package/src/sdk.ts +14 -0
  275. package/src/shared.ts +206 -0
  276. package/src/types.ts +152 -206
  277. package/src/ui/head.ts +34 -27
  278. package/src/ui/index.ts +3 -3
  279. package/src/ui/metadata.ts +95 -0
  280. package/src/ui/router.ts +22 -6
  281. package/src/ui/runtime.ts +55 -6
  282. package/src/ui/types.ts +24 -11
  283. package/src/utils/banner.ts +10 -6
  284. package/src/utils/run.ts +26 -27
  285. package/src/utils/theme.ts +3 -66
  286. package/src/components/monitor-view.tsx +0 -475
  287. package/src/components/status-view.tsx +0 -173
  288. package/src/lib/env.ts +0 -109
  289. package/src/lib/near-cli.ts +0 -289
  290. package/src/lib/nova.ts +0 -266
  291. package/src/lib/orchestrator.ts +0 -276
  292. package/src/lib/process-registry.ts +0 -166
  293. package/src/lib/process.ts +0 -550
  294. package/src/lib/resource-monitor/assertions.ts +0 -234
  295. package/src/lib/resource-monitor/command.ts +0 -283
  296. package/src/lib/resource-monitor/diff.ts +0 -157
  297. package/src/lib/resource-monitor/errors.ts +0 -127
  298. package/src/lib/resource-monitor/index.ts +0 -305
  299. package/src/lib/resource-monitor/platform/darwin.ts +0 -306
  300. package/src/lib/resource-monitor/platform/index.ts +0 -35
  301. package/src/lib/resource-monitor/platform/linux.ts +0 -332
  302. package/src/lib/resource-monitor/platform/windows.ts +0 -298
  303. package/src/lib/resource-monitor/snapshot.ts +0 -217
  304. package/src/lib/resource-monitor/types.ts +0 -74
  305. package/src/lib/session-recorder/errors.ts +0 -102
  306. package/src/lib/session-recorder/flows/login.ts +0 -210
  307. package/src/lib/session-recorder/index.ts +0 -361
  308. package/src/lib/session-recorder/playwright.ts +0 -257
  309. package/src/lib/session-recorder/report.ts +0 -353
  310. package/src/lib/session-recorder/server.ts +0 -268
  311. package/src/lib/session-recorder/types.ts +0 -115
  312. package/src/lib/sync.ts +0 -1
  313. package/src/ui/files.ts +0 -134
@@ -0,0 +1,386 @@
1
+ import { spawn } from "node:child_process";
2
+ import {
3
+ createWriteStream,
4
+ existsSync,
5
+ lstatSync,
6
+ mkdirSync,
7
+ readFileSync,
8
+ rmSync,
9
+ writeFileSync,
10
+ } from "node:fs";
11
+ import { createRequire } from "node:module";
12
+ import { tmpdir } from "node:os";
13
+ import { dirname, join, resolve } from "node:path";
14
+ import { pipeline } from "node:stream/promises";
15
+ import { glob } from "glob";
16
+ import { fetchBosConfigFromFastKv } from "../fastkv";
17
+ import {
18
+ loadManifestNormalizationSpec,
19
+ normalizePackageManifestsInTree,
20
+ } from "../internal/manifest-normalizer";
21
+ import type { BosConfig } from "../types";
22
+
23
+ const require = createRequire(import.meta.url);
24
+
25
+ interface SourceResult {
26
+ sourceDir: string;
27
+ parentConfig: BosConfig;
28
+ cleanup: () => Promise<void>;
29
+ }
30
+
31
+ export async function resolveSourceDir(opts: {
32
+ account: string;
33
+ gateway: string;
34
+ source?: string;
35
+ }): Promise<SourceResult> {
36
+ if (opts.source) {
37
+ const sourceDir = resolve(opts.source);
38
+ if (!existsSync(join(sourceDir, "bos.config.json"))) {
39
+ throw new Error(`No bos.config.json found in source directory: ${sourceDir}`);
40
+ }
41
+ const parentConfig = JSON.parse(
42
+ readFileSync(join(sourceDir, "bos.config.json"), "utf-8"),
43
+ ) as BosConfig;
44
+ return { sourceDir, parentConfig, cleanup: async () => {} };
45
+ }
46
+
47
+ const parentConfig = await fetchParentConfig(opts.account, opts.gateway);
48
+
49
+ if (!parentConfig.repository) {
50
+ throw new Error("Parent config has no repository field — cannot locate template source");
51
+ }
52
+
53
+ const { dir: sourceDir, cleanup } = await downloadTarball(parentConfig.repository);
54
+ return { sourceDir, parentConfig, cleanup };
55
+ }
56
+
57
+ export async function fetchParentConfig(account: string, gateway: string): Promise<BosConfig> {
58
+ const bosUrl = `bos://${account}/${gateway}`;
59
+ return fetchBosConfigFromFastKv<BosConfig>(bosUrl);
60
+ }
61
+
62
+ export async function downloadTarball(
63
+ repoUrl: string,
64
+ ): Promise<{ dir: string; cleanup: () => Promise<void> }> {
65
+ const parsed = parseGitHubUrl(repoUrl);
66
+ if (!parsed) {
67
+ throw new Error(`Cannot parse repository URL: ${repoUrl}`);
68
+ }
69
+
70
+ const { owner, repo, branch } = parsed;
71
+ const tarballUrl = `https://api.github.com/repos/${owner}/${repo}/tarball/${branch}`;
72
+
73
+ const tmpDir = mkTmpDir("bos-init-tarball-");
74
+ const tarballPath = join(tmpDir, "source.tar.gz");
75
+
76
+ const response = await fetch(tarballUrl, {
77
+ headers: { "User-Agent": "everything-dev" },
78
+ redirect: "follow",
79
+ });
80
+
81
+ if (!response.ok) {
82
+ rmSync(tmpDir, { recursive: true, force: true });
83
+ throw new Error(`GitHub tarball download failed: ${response.status} ${response.statusText}`);
84
+ }
85
+
86
+ if (!response.body) {
87
+ rmSync(tmpDir, { recursive: true, force: true });
88
+ throw new Error("GitHub tarball download returned empty body");
89
+ }
90
+
91
+ const fileStream = createWriteStream(tarballPath);
92
+ const reader = response.body as unknown as NodeJS.ReadableStream;
93
+ await pipeline(reader, fileStream);
94
+
95
+ const extractDir = mkTmpDir("bos-init-extract-");
96
+ try {
97
+ const tar = require("tar") as {
98
+ extract: (opts: { cwd: string; file: string; strip: number }) => Promise<void>;
99
+ };
100
+ await tar.extract({ cwd: extractDir, file: tarballPath, strip: 1 });
101
+ } catch {
102
+ await execCommand("tar", ["-xzf", tarballPath, "--strip-components=1", "-C", extractDir]);
103
+ }
104
+
105
+ rmSync(tmpDir, { recursive: true, force: true });
106
+
107
+ return {
108
+ dir: extractDir,
109
+ cleanup: async () => {
110
+ rmSync(extractDir, { recursive: true, force: true });
111
+ },
112
+ };
113
+ }
114
+
115
+ function parseGitHubUrl(url: string): { owner: string; repo: string; branch: string } | null {
116
+ const httpsMatch = url.match(/^https?:\/\/github\.com\/([^/]+)\/([^/]+?)(?:\.git)?(?:\/.*)?$/);
117
+ if (httpsMatch) {
118
+ return { owner: httpsMatch[1], repo: httpsMatch[2], branch: "main" };
119
+ }
120
+
121
+ const sshMatch = url.match(/^git@github\.com:([^/]+)\/([^/]+?)(?:\.git)?$/);
122
+ if (sshMatch) {
123
+ return { owner: sshMatch[1], repo: sshMatch[2], branch: "main" };
124
+ }
125
+
126
+ return null;
127
+ }
128
+
129
+ export async function readTemplatekeep(sourceDir: string): Promise<string[]> {
130
+ const keepFile = join(sourceDir, ".templatekeep");
131
+ if (!existsSync(keepFile)) {
132
+ return [];
133
+ }
134
+
135
+ const content = readFileSync(keepFile, "utf-8");
136
+ return content
137
+ .split("\n")
138
+ .map((line) => line.trim())
139
+ .filter((line) => line.length > 0 && !line.startsWith("#"));
140
+ }
141
+
142
+ export async function copyFilteredFiles(
143
+ sourceDir: string,
144
+ destination: string,
145
+ patterns: string[],
146
+ options: { withHost: boolean },
147
+ ): Promise<number> {
148
+ if (patterns.length === 0) {
149
+ return 0;
150
+ }
151
+
152
+ const effectivePatterns = options.withHost
153
+ ? [...patterns, "host/**"]
154
+ : patterns.filter((p) => !p.startsWith("host/") && p !== "host/**");
155
+
156
+ const allFiles = new Set<string>();
157
+ for (const pattern of effectivePatterns) {
158
+ const matches = await glob(pattern, {
159
+ cwd: sourceDir,
160
+ nodir: true,
161
+ dot: true,
162
+ absolute: false,
163
+ });
164
+ for (const match of matches) {
165
+ allFiles.add(match);
166
+ }
167
+ }
168
+
169
+ mkdirSync(destination, { recursive: true });
170
+
171
+ let count = 0;
172
+ for (const filePath of allFiles) {
173
+ const src = join(sourceDir, filePath);
174
+ const stat = lstatSync(src);
175
+ if (!stat.isFile()) continue;
176
+
177
+ const dest = join(destination, filePath);
178
+ mkdirSync(dirname(dest), { recursive: true });
179
+ const content = readFileSync(src);
180
+ writeFileSync(dest, content);
181
+ count++;
182
+ }
183
+
184
+ return count;
185
+ }
186
+
187
+ export async function personalizeConfig(
188
+ destination: string,
189
+ opts: {
190
+ parentAccount: string;
191
+ parentGateway: string;
192
+ name?: string;
193
+ domain?: string;
194
+ workspaceOpts?: { localOverrides?: boolean; sourceDir?: string };
195
+ },
196
+ ): Promise<void> {
197
+ const configPath = join(destination, "bos.config.json");
198
+ if (existsSync(configPath)) {
199
+ const config = JSON.parse(readFileSync(configPath, "utf-8")) as Record<string, unknown>;
200
+
201
+ config.extends = `bos://${opts.parentAccount}/${opts.parentGateway}`;
202
+
203
+ if (opts.name) {
204
+ config.account = opts.name;
205
+ }
206
+ if (opts.domain) {
207
+ config.domain = opts.domain;
208
+ }
209
+
210
+ if (config.app && typeof config.app === "object") {
211
+ const app = config.app as Record<string, unknown>;
212
+ for (const entryKey of Object.keys(app)) {
213
+ const entry = app[entryKey];
214
+ if (entry && typeof entry === "object") {
215
+ const e = entry as Record<string, unknown>;
216
+ delete e.production;
217
+ delete e.productionIntegrity;
218
+ delete e.ssr;
219
+ delete e.ssrIntegrity;
220
+ }
221
+ }
222
+ }
223
+
224
+ if (config.plugins && typeof config.plugins === "object") {
225
+ const plugins = config.plugins as Record<string, unknown>;
226
+ for (const pluginKey of Object.keys(plugins)) {
227
+ const plugin = plugins[pluginKey];
228
+ if (plugin && typeof plugin === "object") {
229
+ const p = plugin as Record<string, unknown>;
230
+ delete p.production;
231
+ delete p.productionIntegrity;
232
+ }
233
+ }
234
+ }
235
+
236
+ writeFileSync(configPath, `${JSON.stringify(config, null, 2)}\n`);
237
+ }
238
+
239
+ const pkgPath = join(destination, "package.json");
240
+ if (existsSync(pkgPath)) {
241
+ const pkg = JSON.parse(readFileSync(pkgPath, "utf-8")) as Record<string, unknown>;
242
+
243
+ if (pkg.workspaces && typeof pkg.workspaces === "object") {
244
+ const ws = pkg.workspaces as { packages?: string[] };
245
+ if (Array.isArray(ws.packages)) {
246
+ ws.packages = ws.packages.filter((p: string) => p !== "host" && !p.startsWith("packages/"));
247
+ }
248
+ }
249
+
250
+ if (pkg.scripts && typeof pkg.scripts === "object") {
251
+ const scripts = pkg.scripts as Record<string, string>;
252
+ const rewrite = (key: string, from: string, to: string) => {
253
+ if (scripts[key]?.includes(from)) {
254
+ scripts[key] = scripts[key].replaceAll(from, to);
255
+ }
256
+ };
257
+ rewrite("dev", "packages/everything-dev/cli.js", "node_modules/.bin/bos");
258
+ rewrite("dev:ui", "packages/everything-dev/cli.js", "node_modules/.bin/bos");
259
+ rewrite("dev:api", "packages/everything-dev/cli.js", "node_modules/.bin/bos");
260
+ rewrite("dev:proxy", "packages/everything-dev/cli.js", "node_modules/.bin/bos");
261
+ rewrite("build", "packages/everything-dev/cli.js", "node_modules/.bin/bos");
262
+ rewrite("deploy", "packages/everything-dev/cli.js", "node_modules/.bin/bos");
263
+ rewrite("publish", "packages/everything-dev/cli.js", "node_modules/.bin/bos");
264
+ rewrite("start", "packages/everything-dev/cli.js", "node_modules/.bin/bos");
265
+
266
+ if (scripts["sync:api-contract"]) {
267
+ delete scripts["sync:api-contract"];
268
+ }
269
+ if (scripts.postinstall) {
270
+ delete scripts.postinstall;
271
+ }
272
+ if (scripts.typecheck?.includes("sync:api-contract")) {
273
+ scripts.typecheck = scripts.typecheck.replace("bun run sync:api-contract && ", "");
274
+ }
275
+ }
276
+
277
+ if (pkg.devDependencies && typeof pkg.devDependencies === "object") {
278
+ const deps = pkg.devDependencies as Record<string, string>;
279
+ delete deps["every-plugin"];
280
+ delete deps["everything-dev"];
281
+ }
282
+
283
+ if (!pkg.dependencies) pkg.dependencies = {};
284
+ const deps = pkg.dependencies as Record<string, string>;
285
+ const spec = opts.workspaceOpts?.sourceDir
286
+ ? loadManifestNormalizationSpec(opts.workspaceOpts.sourceDir)
287
+ : null;
288
+ if (!deps["everything-dev"] && spec)
289
+ deps["everything-dev"] = spec.rootCatalog["everything-dev"];
290
+ if (!deps["every-plugin"] && spec) deps["every-plugin"] = spec.rootCatalog["every-plugin"];
291
+
292
+ writeFileSync(pkgPath, `${JSON.stringify(pkg, null, 2)}\n`);
293
+ }
294
+
295
+ await resolveWorkspaceRefs(destination, opts.workspaceOpts);
296
+ }
297
+
298
+ export async function runBunInstall(destination: string): Promise<void> {
299
+ await execCommand("bun", ["install"], destination);
300
+ }
301
+
302
+ const WORKSPACE_LOCAL_PATHS: Record<string, string> = {
303
+ "everything-dev": "packages/everything-dev",
304
+ "every-plugin": "packages/every-plugin",
305
+ };
306
+
307
+ async function resolveWorkspaceRefs(
308
+ destination: string,
309
+ options?: { localOverrides?: boolean; sourceDir?: string },
310
+ ): Promise<void> {
311
+ await normalizePackageManifestsInTree({
312
+ sourceRootDir: options?.sourceDir ?? destination,
313
+ targetDir: destination,
314
+ resolveCatalogRefs: false,
315
+ removeWorkspaceDeps: ["host"],
316
+ });
317
+
318
+ if (options?.localOverrides && options.sourceDir) {
319
+ const rootPkgPath = join(destination, "package.json");
320
+ if (existsSync(rootPkgPath)) {
321
+ const pkg = JSON.parse(readFileSync(rootPkgPath, "utf-8")) as Record<string, unknown>;
322
+ if (!pkg.overrides) pkg.overrides = {};
323
+ const overrides = pkg.overrides as Record<string, string>;
324
+
325
+ const rootWorkspaces = ((pkg.workspaces as Record<string, string[]>)?.packages ?? []).filter(
326
+ Boolean,
327
+ );
328
+
329
+ for (const [name, relPath] of Object.entries(WORKSPACE_LOCAL_PATHS)) {
330
+ if (!rootWorkspaces.some((ws) => ws === relPath || ws === `plugins/${name}`)) {
331
+ const srcPkgPath = join(options.sourceDir, relPath, "package.json");
332
+ if (existsSync(srcPkgPath)) {
333
+ overrides[name] = `file:${relPath}`;
334
+ rootWorkspaces.push(relPath);
335
+ }
336
+ }
337
+ }
338
+
339
+ if (rootWorkspaces.length > 0) {
340
+ if (!pkg.workspaces) pkg.workspaces = {};
341
+ (pkg.workspaces as Record<string, string[]>).packages = rootWorkspaces;
342
+ }
343
+
344
+ writeFileSync(rootPkgPath, `${JSON.stringify(pkg, null, 2)}\n`);
345
+ }
346
+ }
347
+ }
348
+
349
+ function mkTmpDir(prefix: string): string {
350
+ const base = join(tmpdir(), prefix);
351
+ let attempt = 0;
352
+ while (true) {
353
+ const dir = `${base}-${Date.now()}-${attempt}`;
354
+ try {
355
+ mkdirSync(dir, { recursive: true });
356
+ return dir;
357
+ } catch {
358
+ attempt++;
359
+ if (attempt > 10) throw new Error("Failed to create temp directory");
360
+ }
361
+ }
362
+ }
363
+
364
+ function execCommand(command: string, args: string[], cwd?: string): Promise<void> {
365
+ return new Promise((resolve, reject) => {
366
+ const child = spawn(command, args, {
367
+ cwd,
368
+ stdio: "pipe",
369
+ shell: true,
370
+ });
371
+ let stderr = "";
372
+ child.stderr?.on("data", (data: Buffer) => {
373
+ stderr += data.toString();
374
+ });
375
+ child.on("close", (code) => {
376
+ if (code === 0) resolve();
377
+ else
378
+ reject(
379
+ new Error(
380
+ `Command '${command} ${args.join(" ")}' failed with exit code ${code}: ${stderr}`,
381
+ ),
382
+ );
383
+ });
384
+ child.on("error", reject);
385
+ });
386
+ }
@@ -0,0 +1,130 @@
1
+ import type { CommandDescriptor } from "./catalog";
2
+
3
+ type SchemaLike = {
4
+ _def?: {
5
+ type?: string;
6
+ innerType?: SchemaLike;
7
+ shape?: Record<string, SchemaLike>;
8
+ values?: Record<string, string> | string[];
9
+ };
10
+ parse: (value: unknown) => unknown;
11
+ };
12
+
13
+ function unwrap(schema: SchemaLike): SchemaLike {
14
+ let current = schema;
15
+ while (true) {
16
+ const type = current._def?.type;
17
+ if (type === "default" || type === "optional" || type === "nullable" || type === "nullish") {
18
+ const inner = current._def?.innerType;
19
+ if (!inner) break;
20
+ current = inner;
21
+ continue;
22
+ }
23
+ return current;
24
+ }
25
+ return current;
26
+ }
27
+
28
+ function isBooleanSchema(schema: SchemaLike): boolean {
29
+ return unwrap(schema)._def?.type === "boolean";
30
+ }
31
+
32
+ function coerceValue(raw: string, schema: SchemaLike): unknown {
33
+ const inner = unwrap(schema);
34
+ switch (inner._def?.type) {
35
+ case "boolean":
36
+ return raw === "true" || raw === "1" || raw === "yes";
37
+ case "number": {
38
+ const value = Number(raw);
39
+ if (Number.isNaN(value)) throw new Error(`Invalid number: ${raw}`);
40
+ return value;
41
+ }
42
+ case "enum":
43
+ return raw;
44
+ default:
45
+ return raw;
46
+ }
47
+ }
48
+
49
+ function toFlagName(field: string): string {
50
+ return `--${field.replace(/([a-z0-9])([A-Z])/g, "$1-$2").toLowerCase()}`;
51
+ }
52
+
53
+ function getShape(schema: SchemaLike): Record<string, SchemaLike> {
54
+ const inner = unwrap(schema);
55
+ const shape = inner._def?.shape;
56
+ if (!shape) return {};
57
+ return shape;
58
+ }
59
+
60
+ export function parseCommandInput(descriptor: CommandDescriptor, argv: string[]): unknown {
61
+ const schema = (descriptor.procedure as any)["~orpc"]?.inputSchema as SchemaLike | undefined;
62
+ if (!schema) return {};
63
+
64
+ const shape = getShape(schema);
65
+ const fields = Object.entries(shape);
66
+ const fieldByFlag = new Map<string, string>();
67
+ const positionalFields: string[] = [];
68
+
69
+ for (const [fieldName] of fields) {
70
+ fieldByFlag.set(toFlagName(fieldName), fieldName);
71
+ if (descriptor.meta.fields?.[fieldName]?.positional) {
72
+ positionalFields.push(fieldName);
73
+ }
74
+ }
75
+
76
+ const input: Record<string, unknown> = {};
77
+ const positionals: string[] = [];
78
+
79
+ for (let i = 0; i < argv.length; i += 1) {
80
+ const token = argv[i];
81
+ if (!token) continue;
82
+
83
+ if (token.startsWith("--no-")) {
84
+ const flagName = `--${token.slice(5)}`;
85
+ const fieldName = fieldByFlag.get(flagName);
86
+ if (!fieldName) throw new Error(`Unknown flag: ${token}`);
87
+ input[fieldName] = false;
88
+ continue;
89
+ }
90
+
91
+ if (token.startsWith("--")) {
92
+ const [flag, inline] = token.split("=", 2);
93
+ const fieldName = fieldByFlag.get(flag);
94
+ if (!fieldName) throw new Error(`Unknown flag: ${token}`);
95
+
96
+ const fieldSchema = shape[fieldName];
97
+ if (isBooleanSchema(fieldSchema)) {
98
+ input[fieldName] = inline ? coerceValue(inline, fieldSchema) : true;
99
+ continue;
100
+ }
101
+
102
+ const next = inline ?? argv[i + 1];
103
+ if (next === undefined || next.startsWith("--")) {
104
+ throw new Error(`Missing value for ${flag}`);
105
+ }
106
+ input[fieldName] = coerceValue(next, fieldSchema);
107
+ if (!inline) i += 1;
108
+ continue;
109
+ }
110
+
111
+ positionals.push(token);
112
+ }
113
+
114
+ if (positionalFields.length > 0) {
115
+ positionalFields.forEach((fieldName, index) => {
116
+ const raw = positionals[index];
117
+ if (raw !== undefined) {
118
+ input[fieldName] = coerceValue(raw, shape[fieldName]);
119
+ }
120
+ });
121
+ } else if (positionals.length > 0) {
122
+ const candidate = fields.find(([, fieldSchema]) => !isBooleanSchema(fieldSchema));
123
+ if (candidate) {
124
+ const [fieldName, fieldSchema] = candidate;
125
+ input[fieldName] = coerceValue(positionals[0], fieldSchema);
126
+ }
127
+ }
128
+
129
+ return schema.parse(input);
130
+ }
@@ -0,0 +1,64 @@
1
+ import { createInterface } from "node:readline";
2
+
3
+ export async function prompt(question: string, defaultValue?: string): Promise<string> {
4
+ const rl = createInterface({
5
+ input: process.stdin,
6
+ output: process.stdout,
7
+ });
8
+
9
+ const suffix = defaultValue ? ` [${defaultValue}]` : "";
10
+ const fullQuestion = `${question}${suffix}: `;
11
+
12
+ return new Promise<string>((resolve) => {
13
+ rl.question(fullQuestion, (answer) => {
14
+ rl.close();
15
+ const trimmed = answer.trim();
16
+ resolve(trimmed || defaultValue || "");
17
+ });
18
+ });
19
+ }
20
+
21
+ export async function promptYesNo(question: string, defaultVal = false): Promise<boolean> {
22
+ const hint = defaultVal ? "Y/n" : "y/N";
23
+ const answer = await prompt(`${question} (${hint})`);
24
+ if (!answer) return defaultVal;
25
+ return answer.toLowerCase() === "y" || answer.toLowerCase() === "yes";
26
+ }
27
+
28
+ export async function promptInitOptions(input: {
29
+ account?: string;
30
+ gateway?: string;
31
+ destination?: string;
32
+ name?: string;
33
+ domain?: string;
34
+ withHost?: boolean;
35
+ }): Promise<{
36
+ account: string;
37
+ gateway: string;
38
+ destination: string;
39
+ name?: string;
40
+ domain?: string;
41
+ withHost: boolean;
42
+ }> {
43
+ const account = input.account || (await prompt("NEAR account", "dev.everything.near"));
44
+
45
+ const gateway = input.gateway || (await prompt("Gateway ID", "everything.dev"));
46
+
47
+ const destination = input.destination || (await prompt("Project directory", gateway));
48
+
49
+ const name = input.name || (await prompt("New project NEAR account (optional)", ""));
50
+
51
+ const domain = input.domain || (await prompt("New project domain (optional)", ""));
52
+
53
+ const withHost =
54
+ input.withHost !== undefined ? input.withHost : await promptYesNo("Include host?", false);
55
+
56
+ return {
57
+ account,
58
+ gateway,
59
+ destination,
60
+ name: name || undefined,
61
+ domain: domain || undefined,
62
+ withHost,
63
+ };
64
+ }