@monster-orange/den 0.2.7 → 0.3.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 (139) hide show
  1. package/CHANGELOG.md +1655 -0
  2. package/README.md +4 -2
  3. package/bin/den +2 -1
  4. package/docs/distributions.md +619 -3
  5. package/make/den.mk +19 -4
  6. package/make/journeys.mk +2 -1
  7. package/make/local_dev.mk +6 -13
  8. package/make/secrets-1password.mk +18 -0
  9. package/make/test.mk +1 -1
  10. package/package.json +9 -2
  11. package/schemas/den.plugin.v1.json +156 -0
  12. package/schemas/den.theme.v1.json +269 -0
  13. package/scripts/auth-configure.ts +16 -8
  14. package/scripts/heal-config.ts +0 -5
  15. package/scripts/setup-1password.ts +41 -19
  16. package/scripts/setup-secrets.ts +67 -101
  17. package/src/pillars/api/global-setup.ts +1 -1
  18. package/src/pillars/journeys/sandbox.ts +23 -18
  19. package/src/pillars/journeys/tools/browser-session.ts +2 -2
  20. package/src/scripts/setup-default-workspace.ts +2 -2
  21. package/src/shared/agent-actor.ts +38 -3
  22. package/src/shared/auth/headless-login.ts +1 -1
  23. package/src/shared/auth/sudo-vault.ts +93 -31
  24. package/src/shared/auth/token-providers/index.ts +7 -3
  25. package/src/shared/brand.ts +7 -0
  26. package/src/shared/config-error.ts +63 -0
  27. package/src/shared/constants.ts +3 -24
  28. package/src/shared/den-config.ts +185 -7
  29. package/src/shared/edge/config.ts +147 -21
  30. package/src/shared/edge/exec.ts +31 -0
  31. package/src/shared/edge/included.ts +169 -0
  32. package/src/shared/edge/render.ts +69 -14
  33. package/src/shared/edge/runtime.ts +128 -121
  34. package/src/shared/edge/status.ts +68 -8
  35. package/src/shared/edge/tls.ts +328 -0
  36. package/src/shared/edge/types.ts +25 -9
  37. package/src/shared/environment-manager/catalog.ts +52 -1
  38. package/src/shared/environment-manager/default-workspace.ts +26 -3
  39. package/src/shared/environment-manager/git-remote.ts +49 -0
  40. package/src/shared/environment-manager/health.ts +73 -38
  41. package/src/shared/environment-manager/scope.ts +168 -0
  42. package/src/shared/environment-manager/service-runner.ts +789 -43
  43. package/src/shared/environment-manager/up-targets.ts +132 -0
  44. package/src/shared/environment-manager/workspace-manager.ts +67 -25
  45. package/src/shared/environment-manager/workspace-org.ts +26 -11
  46. package/src/shared/health/rollup.ts +48 -0
  47. package/src/shared/manifest/service-links.ts +20 -8
  48. package/src/shared/open-url.ts +21 -2
  49. package/src/shared/org-sources.ts +328 -0
  50. package/src/shared/org.ts +53 -5
  51. package/src/shared/plugins/manifest.ts +406 -0
  52. package/src/shared/plugins/store.ts +358 -0
  53. package/src/shared/process/legacy-adopt.ts +285 -0
  54. package/src/shared/process/process-group.ts +202 -0
  55. package/src/shared/process/spawn-streaming.ts +7 -0
  56. package/src/shared/secrets/doppler.ts +1 -1
  57. package/src/shared/secrets/index.ts +279 -50
  58. package/src/shared/secrets/none.ts +56 -0
  59. package/src/shared/secrets/strategies.ts +202 -0
  60. package/src/shared/secrets/types.ts +1 -1
  61. package/src/shared/smoke/git-remote.ts +40 -0
  62. package/src/shared/stacks/manifest-commands.ts +1 -1
  63. package/src/shared/stacks/namespace.ts +178 -0
  64. package/src/shared/stacks/owners.ts +303 -0
  65. package/src/shared/stacks/render.ts +8 -3
  66. package/src/shared/stacks/runtime.ts +100 -16
  67. package/src/shared/stacks/status.ts +63 -12
  68. package/src/shared/strategies/registry.ts +89 -0
  69. package/src/shared/theme/contract.ts +538 -0
  70. package/src/shared/types/index.ts +24 -5
  71. package/src/ui/cli/clone-plan.ts +154 -23
  72. package/src/ui/cli/create.ts +24 -7
  73. package/src/ui/cli/doctor-command.ts +131 -0
  74. package/src/ui/cli/edge-command.ts +56 -10
  75. package/src/ui/cli/flag-parser.ts +62 -3
  76. package/src/ui/cli/health-display.ts +25 -0
  77. package/src/ui/cli/index.ts +649 -72
  78. package/src/ui/cli/notice.ts +20 -0
  79. package/src/ui/cli/org-command.ts +12 -2
  80. package/src/ui/cli/plugin-command.ts +849 -0
  81. package/src/ui/cli/stack-command.ts +63 -2
  82. package/src/ui/cli/test-runner.ts +11 -9
  83. package/src/ui/cli/theme-command.ts +136 -0
  84. package/src/ui/cli/up-args.ts +15 -0
  85. package/src/ui/cli/web-command.ts +47 -23
  86. package/src/ui/mcp/api.ts +28 -2
  87. package/src/ui/mcp/scope.ts +298 -0
  88. package/src/ui/mcp/server.ts +70 -8
  89. package/src/ui/mcp/tools.ts +151 -24
  90. package/src/ui/server/appearance-prefs.ts +95 -0
  91. package/src/ui/server/audit.ts +90 -3
  92. package/src/ui/server/daemon-reaper.ts +29 -1
  93. package/src/ui/server/engine-stamp.ts +83 -0
  94. package/src/ui/server/github-service.ts +29 -45
  95. package/src/ui/server/graph-page.ts +20 -0
  96. package/src/ui/server/graph-prefs.ts +44 -1
  97. package/src/ui/server/http-errors.ts +293 -0
  98. package/src/ui/server/http-helpers.ts +22 -3
  99. package/src/ui/server/index.ts +590 -45
  100. package/src/ui/server/public/appearance.js +531 -0
  101. package/src/ui/server/public/edge-page.js +248 -0
  102. package/src/ui/server/public/edge.html +251 -0
  103. package/src/ui/server/public/environments.html +65 -83
  104. package/src/ui/server/public/error-page.js +247 -0
  105. package/src/ui/server/public/error.html +260 -0
  106. package/src/ui/server/public/graph-model.js +332 -14
  107. package/src/ui/server/public/graph.css +141 -47
  108. package/src/ui/server/public/graph.js +223 -44
  109. package/src/ui/server/public/header.js +396 -600
  110. package/src/ui/server/public/health-fit.js +248 -0
  111. package/src/ui/server/public/health-rollup.js +128 -0
  112. package/src/ui/server/public/i18n/es.js +287 -0
  113. package/src/ui/server/public/i18n/ja.js +276 -0
  114. package/src/ui/server/public/index.html +139 -438
  115. package/src/ui/server/public/local-dev.html +3468 -4044
  116. package/src/ui/server/public/logs.html +71 -208
  117. package/src/ui/server/public/panel.js +15 -3
  118. package/src/ui/server/public/release.html +175 -389
  119. package/src/ui/server/public/services.html +596 -770
  120. package/src/ui/server/public/settings-page.js +759 -0
  121. package/src/ui/server/public/settings-registry.js +521 -0
  122. package/src/ui/server/public/settings.html +590 -0
  123. package/src/ui/server/public/shell.js +3869 -0
  124. package/src/ui/server/public/topbar.js +1413 -0
  125. package/src/ui/server/public/version-label.js +12 -0
  126. package/src/ui/server/public/workspace-picker.js +74 -34
  127. package/src/ui/server/readonly-routes.ts +24 -4
  128. package/src/ui/server/release-service.ts +25 -3
  129. package/src/ui/server/services-list.ts +94 -17
  130. package/src/ui/server/settings-distribution.ts +74 -0
  131. package/src/ui/server/shell-prefs.ts +192 -0
  132. package/src/ui/server/theme-routes.ts +292 -0
  133. package/src/ui/server/theme-runtime.ts +407 -0
  134. package/src/ui/server/ui-assets.ts +16 -1
  135. package/src/ui/server/ui-language.ts +50 -0
  136. package/src/ui/server/workspace-routes.ts +55 -9
  137. package/themes/den/den-theme.json +72 -0
  138. package/themes/den/favicon.ico +0 -0
  139. package/themes/den/mark.svg +6 -0
@@ -12,6 +12,7 @@ export type CommandName =
12
12
  | "services"
13
13
  | "graph"
14
14
  | "register"
15
+ | "relocate"
15
16
  | "use-local"
16
17
  | "use-managed"
17
18
  | "setup"
@@ -61,11 +62,26 @@ const WORKSPACE_READ_COMMANDS = new Set([
61
62
  "stack",
62
63
  ]);
63
64
 
65
+ /**
66
+ * Commands that edit one workspace's entries without changing what runs:
67
+ * `-w` picks the workspace to write, whether or not it is active, and leaves
68
+ * focus alone.
69
+ */
70
+ const WORKSPACE_EDIT_COMMANDS = new Set(["register", "relocate"]);
71
+
64
72
  const WORKSPACE_COMMANDS = new Set([
65
73
  ...WORKSPACE_MUTATION_COMMANDS,
66
74
  ...WORKSPACE_READ_COMMANDS,
75
+ ...WORKSPACE_EDIT_COMMANDS,
67
76
  ]);
68
77
 
78
+ /**
79
+ * Commands that read `-w`/`--workspace` themselves, so it is left in their
80
+ * args: `setup --plan -w a -w b` takes several, and `mcp --workspace <ws>`
81
+ * scopes the MCP server (it never sets the CLI's workspace override).
82
+ */
83
+ const OWN_WORKSPACE_FLAG_COMMANDS = new Set(["setup", "mcp"]);
84
+
69
85
  /** Whether `-w <name>` on this command requires `<name>` to be active. */
70
86
  export function workspaceFlagRequiresActive(command: string): boolean {
71
87
  return WORKSPACE_MUTATION_COMMANDS.has(command);
@@ -180,8 +196,11 @@ const COMMAND_FLAGS: Record<string, readonly string[]> = {
180
196
  ],
181
197
  restart: ["-A", "--app", "-n", "--dry-run"],
182
198
  logs: [],
183
- setup: ["-f", "--force", "--plan"],
199
+ setup: ["-f", "--force", "--plan", "-w", "--workspace", "--all-active"],
184
200
  sync: [],
201
+ // The only override for an edge another state dir owns; a typo'd one
202
+ // must not be ignored.
203
+ edge: ["--take-over"],
185
204
  };
186
205
 
187
206
  /**
@@ -200,8 +219,9 @@ export function unknownCommandFlags(command: string, args: string[]): string[] {
200
219
  (a) =>
201
220
  a.startsWith("-") &&
202
221
  !allowed.includes(a) &&
203
- // `--app=<name>` is the one flag that also takes the = form.
204
- !(allowed.includes("--app") && a.startsWith("--app=")),
222
+ // `--app=<name>` and `-w=`/`--workspace=` also take the = form.
223
+ !(allowed.includes("--app") && a.startsWith("--app=")) &&
224
+ !(allowed.includes("--workspace") && /^(-w|--workspace)=/.test(a)),
205
225
  );
206
226
  }
207
227
 
@@ -228,6 +248,16 @@ export function parseCliArgs(raw: string[]): ParsedCliArgs {
228
248
  continue;
229
249
  }
230
250
 
251
+ if (
252
+ parsed.command &&
253
+ OWN_WORKSPACE_FLAG_COMMANDS.has(parsed.command) &&
254
+ /^(-w|--workspace)(=|$)/.test(token)
255
+ ) {
256
+ parsed.args.push(token);
257
+ i += 1;
258
+ continue;
259
+ }
260
+
231
261
  const nextIndex = applyFlag(raw, i, parsed.flags);
232
262
  if (nextIndex !== null) {
233
263
  i = nextIndex;
@@ -245,3 +275,32 @@ export function parseCliArgs(raw: string[]): ParsedCliArgs {
245
275
  validateFlagScopes(parsed);
246
276
  return parsed;
247
277
  }
278
+
279
+ /**
280
+ * Every `-w <ws>` / `--workspace <ws>` (and `=` form) in `args`, in order and
281
+ * repeatable, and the args without them. For a command that reads `-w`
282
+ * itself (OWN_WORKSPACE_FLAG_COMMANDS).
283
+ */
284
+ export function takeWorkspaceFlags(args: readonly string[]): {
285
+ workspaces: string[];
286
+ rest: string[];
287
+ } {
288
+ const workspaces: string[] = [];
289
+ const rest: string[] = [];
290
+ for (let i = 0; i < args.length; i++) {
291
+ const a = args[i];
292
+ const m = /^(-w|--workspace)(?:=(.*))?$/.exec(a);
293
+ if (!m) {
294
+ rest.push(a);
295
+ continue;
296
+ }
297
+ if (m[2] !== undefined) {
298
+ if (!m[2]) throw new Error(`${m[1]} requires a value`);
299
+ workspaces.push(m[2]);
300
+ continue;
301
+ }
302
+ workspaces.push(consumeFlagValue([...args], i, m[1]));
303
+ i++;
304
+ }
305
+ return { workspaces, rest };
306
+ }
@@ -2,6 +2,7 @@ import chalk from "chalk";
2
2
  import type { ServiceHealthResult } from "../../shared/environment-manager/health.js";
3
3
 
4
4
  import { product } from "../../shared/product.js";
5
+ import type { RepoRollup } from "../../shared/health/rollup.js";
5
6
  type HealthState = ServiceHealthResult["health"];
6
7
  type HealthReasonInput = Pick<ServiceHealthResult, "health" | "healthDetail">;
7
8
 
@@ -62,3 +63,27 @@ export function formatHealthReason(result: HealthReasonInput): string {
62
63
  const reason = healthReasonText(result);
63
64
  return reason ? chalk.gray(reason.slice(0, 48)) : "";
64
65
  }
66
+
67
+ /**
68
+ * A repo row's rolled-up state (rollupRepoHealth), the one the web UI's
69
+ * header and graph show: "● down", "● degraded", "● ok", "● unknown".
70
+ */
71
+ export function formatRollupLabel(r: RepoRollup): string {
72
+ if (r.state === "down") return chalk.red("● down");
73
+ if (r.state === "degraded") return chalk.yellow("● degraded");
74
+ if (r.state === "ok") return chalk.green("● ok");
75
+ return chalk.gray("● unknown");
76
+ }
77
+
78
+ /**
79
+ * Why, for a repo row: the down services ("mailpit down"), and how many
80
+ * services aren't checked ("25 not checked"). Unchecked never means down.
81
+ */
82
+ export function rollupReasonText(r: RepoRollup): string {
83
+ return [
84
+ r.down.length ? `${r.down.join(", ")} down` : "",
85
+ r.unchecked ? `${r.unchecked} not checked` : "",
86
+ ]
87
+ .filter(Boolean)
88
+ .join("; ");
89
+ }