@indigoai-us/hq-cli 5.345.154 → 5.345.156

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 (57) hide show
  1. package/CHANGELOG.md +138 -0
  2. package/dist/command-catalog.generated.d.ts +59 -7
  3. package/dist/command-catalog.generated.js +75 -7
  4. package/dist/commands/agent-inbox.js +2 -2
  5. package/dist/commands/auth.d.ts +2 -0
  6. package/dist/commands/auth.js +92 -3
  7. package/dist/commands/core.js +1 -1
  8. package/dist/commands/files-browse.d.ts +16 -0
  9. package/dist/commands/files-browse.js +52 -1
  10. package/dist/commands/integrations-core.d.ts +13 -1
  11. package/dist/commands/integrations-core.js +49 -4
  12. package/dist/commands/integrations.js +4 -2
  13. package/dist/commands/library-add.d.ts +6 -2
  14. package/dist/commands/library-add.js +45 -6
  15. package/dist/commands/library-caption.d.ts +38 -1
  16. package/dist/commands/library-caption.js +304 -3
  17. package/dist/commands/library-link.d.ts +7 -3
  18. package/dist/commands/library-link.js +10 -4
  19. package/dist/commands/library-remove.d.ts +122 -0
  20. package/dist/commands/library-remove.js +681 -0
  21. package/dist/commands/library.d.ts +26 -1
  22. package/dist/commands/library.js +101 -14
  23. package/dist/commands/secrets.d.ts +16 -0
  24. package/dist/commands/secrets.js +144 -8
  25. package/dist/commands/storage-offload.d.ts +22 -4
  26. package/dist/commands/storage-offload.js +196 -2
  27. package/dist/commands/storage.js +5 -0
  28. package/dist/lib/agent-kit/inbox-state.d.ts +7 -0
  29. package/dist/lib/agent-kit/inbox-state.js +5 -1
  30. package/dist/lib/agent-kit/mcp/tools.js +2 -1
  31. package/dist/lib/daemon/machine-login.d.ts +20 -0
  32. package/dist/lib/daemon/machine-login.js +53 -8
  33. package/dist/lib/daemon/machine-token-identity.d.ts +34 -0
  34. package/dist/lib/daemon/machine-token-identity.js +123 -0
  35. package/dist/lib/doctor/checks/sync-health.d.ts +9 -0
  36. package/dist/lib/doctor/checks/sync-health.js +66 -1
  37. package/dist/lib/doctor/company-resolution-state.d.ts +30 -0
  38. package/dist/lib/doctor/company-resolution-state.js +89 -0
  39. package/dist/lib/doctor/fix/apply.d.ts +36 -6
  40. package/dist/lib/doctor/fix/apply.js +128 -12
  41. package/dist/lib/doctor/types.d.ts +1 -1
  42. package/dist/lib/doctor/types.js +1 -0
  43. package/dist/lib/hook-engine/resolve.js +6 -2
  44. package/dist/lib/index-render/company-knowledge.d.ts +1 -1
  45. package/dist/lib/index-render/company-knowledge.js +3 -2
  46. package/dist/lib/index-render/index.js +44 -3
  47. package/dist/lib/index-render/projects.d.ts +1 -1
  48. package/dist/lib/index-render/projects.js +4 -2
  49. package/dist/lib/lanes/registry-flag.d.ts +23 -2
  50. package/dist/lib/lanes/registry-flag.js +256 -36
  51. package/dist/lib/personal-secrets-audit.d.ts +31 -0
  52. package/dist/lib/personal-secrets-audit.js +45 -0
  53. package/dist/sentry-before-send.js +1 -0
  54. package/dist/utils/access-denied-hint.js +6 -0
  55. package/dist/utils/client-health.d.ts +34 -0
  56. package/dist/utils/client-health.js +96 -3
  57. package/package.json +7 -7
@@ -33,6 +33,9 @@
33
33
  import * as fs from "node:fs";
34
34
  import * as path from "node:path";
35
35
  import { randomBytes } from "node:crypto";
36
+ import { spawnSync } from "node:child_process";
37
+ import { createRequire } from "node:module";
38
+ import { pathToFileURL } from "node:url";
36
39
  import { getStateDir, listJournals } from "@indigoai-us/hq-cloud";
37
40
  import { isExpiring, isMachineIdentity, loadCachedTokens, } from "./cognito-session.js";
38
41
  import { vaultApiFetch } from "./vault-api.js";
@@ -73,6 +76,17 @@ export const CLIENT_HEALTH_OBSERVATION_FILE = "cli-client-health.observation.jso
73
76
  * always re-observe — they have opened the store anyway, so it costs nothing.
74
77
  */
75
78
  export const JOURNAL_OBSERVATION_TTL_MS = 15 * 60_000;
79
+ /**
80
+ * V8 old-space cap, in MB, for the child process that enumerates journals on
81
+ * behalf of a plain invocation. `listJournals()` materializes every area of
82
+ * the local sync state store; on a large store that took a short-lived
83
+ * command such as `hq secrets exec` to 2.5-4 GB RSS (feedback_d70e9d63). The
84
+ * child either finishes inside this cap or dies, and the command never holds
85
+ * that memory itself.
86
+ */
87
+ export const JOURNAL_OBSERVER_HEAP_MB = 512;
88
+ /** Wall-clock bound for the isolated journal observer. */
89
+ export const JOURNAL_OBSERVER_TIMEOUT_MS = 20_000;
76
90
  /** An observation lock older than this is treated as abandoned. */
77
91
  const JOURNAL_OBSERVATION_LOCK_STALE_MS = 5 * 60_000;
78
92
  /**
@@ -234,6 +248,66 @@ export function latestJournalSyncTime(journals) {
234
248
  }
235
249
  return latest === null ? null : new Date(latest).toISOString();
236
250
  }
251
+ /**
252
+ * The isolated observer could not produce a value (heap cap, timeout, crash or
253
+ * unreadable output). The caller stamps the observation so the next attempt
254
+ * waits a full TTL instead of re-running a read already known to fail here.
255
+ */
256
+ export class JournalObservationUnavailableError extends Error {
257
+ constructor(message) {
258
+ super(message);
259
+ this.name = "JournalObservationUnavailableError";
260
+ }
261
+ }
262
+ const JOURNAL_OBSERVER_SOURCE = [
263
+ "const engine = await import(process.argv[1]);",
264
+ "const out = [];",
265
+ "for (const entry of engine.listJournals()) {",
266
+ " const value = entry && entry.journal ? entry.journal.lastSync : undefined;",
267
+ " if (typeof value === 'string') out.push(value);",
268
+ "}",
269
+ "process.stdout.write(JSON.stringify(out));",
270
+ ].join("\n");
271
+ function defaultJournalEngineUrl() {
272
+ return pathToFileURL(createRequire(import.meta.url).resolve("@indigoai-us/hq-cloud")).href;
273
+ }
274
+ /**
275
+ * Run `listJournals()` in a heap-capped child process and return only the
276
+ * `lastSync` values. Used for plain invocations so the full store
277
+ * materialization never lands in the invoking command's own memory.
278
+ */
279
+ export function observeJournalsIsolated(opts = {}) {
280
+ const engineUrl = opts.engineUrl ?? defaultJournalEngineUrl();
281
+ const result = spawnSync(process.execPath, [
282
+ `--max-old-space-size=${opts.heapMb ?? JOURNAL_OBSERVER_HEAP_MB}`,
283
+ "--input-type=module",
284
+ "-e",
285
+ JOURNAL_OBSERVER_SOURCE,
286
+ engineUrl,
287
+ ], {
288
+ encoding: "utf8",
289
+ stdio: ["ignore", "pipe", "ignore"],
290
+ timeout: opts.timeoutMs ?? JOURNAL_OBSERVER_TIMEOUT_MS,
291
+ maxBuffer: 1024 * 1024,
292
+ windowsHide: true,
293
+ });
294
+ if (result.error || result.status !== 0 || result.signal) {
295
+ throw new JournalObservationUnavailableError(`journal observer failed (status ${String(result.status)}, signal ${String(result.signal)})`);
296
+ }
297
+ let values;
298
+ try {
299
+ values = JSON.parse(result.stdout);
300
+ }
301
+ catch {
302
+ throw new JournalObservationUnavailableError("journal observer output was not JSON");
303
+ }
304
+ if (!Array.isArray(values)) {
305
+ throw new JournalObservationUnavailableError("journal observer output was not a list");
306
+ }
307
+ return values
308
+ .filter((value) => typeof value === "string")
309
+ .map((lastSync) => ({ journal: { lastSync } }));
310
+ }
237
311
  /**
238
312
  * True when this event kind must pay for a fresh `listJournals()` read.
239
313
  *
@@ -527,7 +601,14 @@ async function contributeClientHealthUnbounded(kind, deps, failureReason) {
527
601
  }
528
602
  else {
529
603
  try {
530
- const observed = latestJournalSyncTime((deps.journals ?? listJournals)());
604
+ // A plain invocation (any command, `hq secrets exec` included) reads
605
+ // the store in a heap-capped child. Sync commands have the store open
606
+ // already and read in-process.
607
+ const source = deps.journals ??
608
+ (kind === "invocation"
609
+ ? (deps.isolatedJournals ?? observeJournalsIsolated)
610
+ : listJournals);
611
+ const observed = latestJournalSyncTime(source());
531
612
  if (observed !== null) {
532
613
  journalLastSyncAt = observed;
533
614
  observation.lastSyncAt = observed;
@@ -543,8 +624,20 @@ async function contributeClientHealthUnbounded(kind, deps, failureReason) {
543
624
  observation.observedAt = now.toISOString();
544
625
  persistJournalObservation(stateDir, observation);
545
626
  }
546
- catch {
547
- // Journal enumeration is best effort.
627
+ catch (error) {
628
+ // Journal enumeration is best effort. When the isolated observer hit
629
+ // its heap or time cap, keep the previous value but stamp the attempt
630
+ // so the next invocation waits a full TTL instead of retrying a read
631
+ // already known to fail on this machine.
632
+ if (error instanceof JournalObservationUnavailableError) {
633
+ observation.observedAt = now.toISOString();
634
+ try {
635
+ persistJournalObservation(stateDir, observation);
636
+ }
637
+ catch {
638
+ // Best effort.
639
+ }
640
+ }
548
641
  }
549
642
  finally {
550
643
  release();
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@indigoai-us/hq-cli",
3
- "version": "5.345.154",
3
+ "version": "5.345.156",
4
4
  "description": "HQ by Indigo management CLI — modules and cloud sync",
5
5
  "main": "dist/index.js",
6
6
  "bin": {
@@ -114,11 +114,11 @@
114
114
  "*.{ts,tsx,mts,cts,js,jsx,mjs,cjs}": "eslint --cache --no-error-on-unmatched-pattern"
115
115
  },
116
116
  "optionalDependencies": {
117
- "@indigoai-us/hq-hook-win32-x64": "5.345.154",
118
- "@indigoai-us/hq-hook-win32-arm64": "5.345.154",
119
- "@indigoai-us/hq-hook-darwin-x64": "5.345.154",
120
- "@indigoai-us/hq-hook-darwin-arm64": "5.345.154",
121
- "@indigoai-us/hq-hook-linux-x64": "5.345.154",
122
- "@indigoai-us/hq-hook-linux-arm64": "5.345.154"
117
+ "@indigoai-us/hq-hook-win32-x64": "5.345.156",
118
+ "@indigoai-us/hq-hook-win32-arm64": "5.345.156",
119
+ "@indigoai-us/hq-hook-darwin-x64": "5.345.156",
120
+ "@indigoai-us/hq-hook-darwin-arm64": "5.345.156",
121
+ "@indigoai-us/hq-hook-linux-x64": "5.345.156",
122
+ "@indigoai-us/hq-hook-linux-arm64": "5.345.156"
123
123
  }
124
124
  }