@ouro.bot/cli 0.1.0-alpha.431 → 0.1.0-alpha.432

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.
package/changelog.json CHANGED
@@ -1,6 +1,14 @@
1
1
  {
2
2
  "_note": "This changelog is maintained as part of the PR/version-bump workflow. Agent-curated, not auto-generated. Agents read this file directly via read_file to understand what changed between versions.",
3
3
  "versions": [
4
+ {
5
+ "version": "0.1.0-alpha.432",
6
+ "changes": [
7
+ "`ouro up` no longer risks hanging forever on an unbounded npm registry check during startup; the update-check phase now shows live detail, aborts the stalled fetch after a short shared timeout, and continues booting with truthful status like `skipped; registry did not answer`.",
8
+ "The same bounded update-check helper now powers `ouro versions`, so published-version lookup cannot freeze there either and the human-facing status wording stays consistent across commands.",
9
+ "Focused startup/version coverage plus the full test suite now protect the stalled-registry regression, and `@ouro.bot/cli` plus the `ouro.bot` wrapper are version-synced for the startup freeze fix release."
10
+ ]
11
+ },
4
12
  {
5
13
  "version": "0.1.0-alpha.431",
6
14
  "changes": [
@@ -53,6 +53,7 @@ const runtime_1 = require("../../nerves/runtime");
53
53
  const ouro_path_installer_1 = require("../versioning/ouro-path-installer");
54
54
  const ouro_uti_1 = require("../versioning/ouro-uti");
55
55
  const ouro_version_manager_1 = require("../versioning/ouro-version-manager");
56
+ const update_checker_1 = require("../versioning/update-checker");
56
57
  const skill_management_installer_1 = require("./skill-management-installer");
57
58
  const hatch_flow_1 = require("../hatch/hatch-flow");
58
59
  const specialist_orchestrator_1 = require("../hatch/specialist-orchestrator");
@@ -144,6 +145,29 @@ function defaultReadRecentDaemonLogLines(lines = 10) {
144
145
  }
145
146
  return recentLines.slice(-lines).map((line) => (0, log_tailer_1.formatLogLine)(line));
146
147
  }
148
+ /* v8 ignore start -- CLI npm registry fetch wrapper: integration code @preserve */
149
+ async function defaultFetchCliRegistryJson(timeoutMs) {
150
+ const controller = new AbortController();
151
+ const timeoutId = setTimeout(() => {
152
+ controller.abort();
153
+ }, timeoutMs);
154
+ try {
155
+ const res = await fetch("https://registry.npmjs.org/@ouro.bot/cli", {
156
+ signal: controller.signal,
157
+ });
158
+ return res.json();
159
+ }
160
+ catch (error) {
161
+ if (error instanceof Error && error.name === "AbortError") {
162
+ throw new Error(`update check timed out after ${Math.max(1, Math.round(timeoutMs / 1000))}s`);
163
+ }
164
+ throw error;
165
+ }
166
+ finally {
167
+ clearTimeout(timeoutId);
168
+ }
169
+ }
170
+ /* v8 ignore stop */
147
171
  function defaultSleep(ms) {
148
172
  return new Promise((resolve) => setTimeout(resolve, ms));
149
173
  }
@@ -501,6 +525,7 @@ function createDefaultOuroCliDeps(socketPath = socket_client_1.DEFAULT_DAEMON_SO
501
525
  readRecentDaemonLogLines: defaultReadRecentDaemonLogLines,
502
526
  sleep: defaultSleep,
503
527
  now: () => Date.now(),
528
+ updateCheckTimeoutMs: update_checker_1.CLI_UPDATE_CHECK_TIMEOUT_MS,
504
529
  startupPollIntervalMs: 250,
505
530
  startupStabilityWindowMs: 1_500,
506
531
  startupTimeoutMs: 10_000,
@@ -540,10 +565,7 @@ function createDefaultOuroCliDeps(socketPath = socket_client_1.DEFAULT_DAEMON_SO
540
565
  checkForCliUpdate: async () => {
541
566
  const { checkForUpdate } = await Promise.resolve().then(() => __importStar(require("../versioning/update-checker")));
542
567
  return checkForUpdate((0, bundle_manifest_1.getPackageVersion)(), {
543
- fetchRegistryJson: async () => {
544
- const res = await fetch("https://registry.npmjs.org/@ouro.bot/cli");
545
- return res.json();
546
- },
568
+ fetchRegistryJson: () => defaultFetchCliRegistryJson(update_checker_1.CLI_UPDATE_CHECK_TIMEOUT_MS),
547
569
  distTag: "latest",
548
570
  });
549
571
  },
@@ -76,6 +76,7 @@ const provider_state_1 = require("../provider-state");
76
76
  const machine_identity_1 = require("../machine-identity");
77
77
  const provider_models_1 = require("../provider-models");
78
78
  const ouro_version_manager_1 = require("../versioning/ouro-version-manager");
79
+ const update_checker_1 = require("../versioning/update-checker");
79
80
  const sync_1 = require("../sync");
80
81
  const cli_parse_1 = require("./cli-parse");
81
82
  const cli_parse_2 = require("./cli-parse");
@@ -104,6 +105,55 @@ const DEFAULT_DAEMON_STARTUP_POLL_INTERVAL_MS = 500;
104
105
  const DEFAULT_DAEMON_STARTUP_STABILITY_WINDOW_MS = 1_500;
105
106
  const DEFAULT_DAEMON_STARTUP_RETRY_LIMIT = 1;
106
107
  const DEFAULT_DAEMON_STARTUP_LOG_LINES = 10;
108
+ function summarizeCliUpdateCheckStatus(error, timedOut = false) {
109
+ const normalized = error.trim().toLowerCase();
110
+ if (timedOut || normalized.includes("timed out") || normalized.includes("abort")) {
111
+ return "skipped; registry did not answer";
112
+ }
113
+ if (normalized.includes("registry unavailable")) {
114
+ return "skipped; registry unavailable";
115
+ }
116
+ if (normalized.includes("network") ||
117
+ normalized.includes("fetch failed") ||
118
+ normalized.includes("enotfound") ||
119
+ normalized.includes("eai_again") ||
120
+ normalized.includes("econnreset")) {
121
+ return "skipped; registry unavailable";
122
+ }
123
+ return "skipped; update check unavailable";
124
+ }
125
+ async function runCliUpdateCheckWithTimeout(checkForCliUpdate, timeoutMs = update_checker_1.CLI_UPDATE_CHECK_TIMEOUT_MS) {
126
+ return await new Promise((resolve, reject) => {
127
+ let settled = false;
128
+ const timeoutId = setTimeout(() => {
129
+ settled = true;
130
+ resolve({
131
+ timedOut: true,
132
+ result: {
133
+ available: false,
134
+ error: `update check timed out after ${Math.max(1, Math.round(timeoutMs / 1000))}s`,
135
+ },
136
+ });
137
+ }, timeoutMs);
138
+ /* v8 ignore start -- Promise-settlement wiring is exercised by command tests; v8 misses these callback lines @preserve */
139
+ void checkForCliUpdate()
140
+ .then((result) => {
141
+ if (settled)
142
+ return;
143
+ settled = true;
144
+ clearTimeout(timeoutId);
145
+ resolve({ result, timedOut: false });
146
+ })
147
+ .catch((error) => {
148
+ if (settled)
149
+ return;
150
+ settled = true;
151
+ clearTimeout(timeoutId);
152
+ reject(error);
153
+ });
154
+ /* v8 ignore stop */
155
+ });
156
+ }
107
157
  async function checkAgentProviders(deps, agentsOverride, onProgress) {
108
158
  const agents = agentsOverride ?? await listCliAgents(deps);
109
159
  const bundlesRoot = deps.bundlesRoot ?? (0, identity_1.getAgentBundlesRoot)();
@@ -3590,9 +3640,11 @@ async function runOuroCli(args, deps = (0, cli_defaults_1.createDefaultOuroCliDe
3590
3640
  // ── versioned CLI update check ──
3591
3641
  if (deps.checkForCliUpdate) {
3592
3642
  progress.startPhase("update check");
3643
+ progress.updateDetail("checking npm registry\ncontinuing startup if it stays quiet");
3593
3644
  let pendingReExec = false;
3645
+ let updateCheckStatus = "up to date";
3594
3646
  try {
3595
- const updateResult = await deps.checkForCliUpdate();
3647
+ const { result: updateResult, timedOut } = await runCliUpdateCheckWithTimeout(deps.checkForCliUpdate, deps.updateCheckTimeoutMs ?? update_checker_1.CLI_UPDATE_CHECK_TIMEOUT_MS);
3596
3648
  if (updateResult.available && updateResult.latestVersion) {
3597
3649
  /* v8 ignore next -- fallback: getCurrentCliVersion always injected in tests @preserve */
3598
3650
  const currentVersion = linkedVersionBeforeUp ?? "unknown";
@@ -3606,9 +3658,13 @@ async function runOuroCli(args, deps = (0, cli_defaults_1.createDefaultOuroCliDe
3606
3658
  }
3607
3659
  pendingReExec = true;
3608
3660
  }
3661
+ else if (updateResult.error) {
3662
+ updateCheckStatus = summarizeCliUpdateCheckStatus(updateResult.error, timedOut);
3663
+ }
3609
3664
  /* v8 ignore start -- update check error: tested via daemon-cli-update-flow.test.ts @preserve */
3610
3665
  }
3611
3666
  catch (error) {
3667
+ updateCheckStatus = summarizeCliUpdateCheckStatus(error instanceof Error ? error.message : String(error));
3612
3668
  (0, runtime_1.emitNervesEvent)({
3613
3669
  level: "warn",
3614
3670
  component: "daemon",
@@ -3623,7 +3679,7 @@ async function runOuroCli(args, deps = (0, cli_defaults_1.createDefaultOuroCliDe
3623
3679
  deps.reExecFromNewVersion(args);
3624
3680
  }
3625
3681
  else {
3626
- progress.completePhase("update check", "up to date");
3682
+ progress.completePhase("update check", updateCheckStatus);
3627
3683
  }
3628
3684
  }
3629
3685
  progress.startPhase("system setup");
@@ -4028,16 +4084,16 @@ async function runOuroCli(args, deps = (0, cli_defaults_1.createDefaultOuroCliDe
4028
4084
  const sections = [localSection];
4029
4085
  if (deps.checkForCliUpdate) {
4030
4086
  try {
4031
- const updateResult = await deps.checkForCliUpdate();
4087
+ const { result: updateResult, timedOut } = await runCliUpdateCheckWithTimeout(deps.checkForCliUpdate, deps.updateCheckTimeoutMs ?? update_checker_1.CLI_UPDATE_CHECK_TIMEOUT_MS);
4032
4088
  if (updateResult.latestVersion) {
4033
4089
  sections.push(`published latest: ${updateResult.latestVersion} (${updateResult.available ? "update available" : "up to date"})`);
4034
4090
  }
4035
4091
  else if (updateResult.error) {
4036
- sections.push(`published latest: unavailable (${updateResult.error})`);
4092
+ sections.push(`published latest: unavailable (${summarizeCliUpdateCheckStatus(updateResult.error, timedOut)})`);
4037
4093
  }
4038
4094
  }
4039
4095
  catch (err) {
4040
- const reason = err instanceof Error ? err.message : String(err);
4096
+ const reason = summarizeCliUpdateCheckStatus(err instanceof Error ? err.message : String(err));
4041
4097
  sections.push(`published latest: unavailable (${reason})`);
4042
4098
  }
4043
4099
  }
@@ -33,12 +33,14 @@ var __importStar = (this && this.__importStar) || (function () {
33
33
  };
34
34
  })();
35
35
  Object.defineProperty(exports, "__esModule", { value: true });
36
+ exports.CLI_UPDATE_CHECK_TIMEOUT_MS = void 0;
36
37
  exports.checkForUpdate = checkForUpdate;
37
38
  exports.startUpdateChecker = startUpdateChecker;
38
39
  exports.stopUpdateChecker = stopUpdateChecker;
39
40
  const semver = __importStar(require("semver"));
40
41
  const runtime_1 = require("../../nerves/runtime");
41
42
  const DEFAULT_INTERVAL_MS = 30 * 60 * 1000; // 30 minutes
43
+ exports.CLI_UPDATE_CHECK_TIMEOUT_MS = 3_000;
42
44
  async function checkForUpdate(currentVersion, deps) {
43
45
  (0, runtime_1.emitNervesEvent)({
44
46
  component: "daemon",
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ouro.bot/cli",
3
- "version": "0.1.0-alpha.431",
3
+ "version": "0.1.0-alpha.432",
4
4
  "main": "dist/heart/daemon/ouro-entry.js",
5
5
  "bin": {
6
6
  "cli": "dist/heart/daemon/ouro-bot-entry.js",