@indigoai-us/hq-cli 5.345.146 → 5.345.147

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.md CHANGED
@@ -2,6 +2,21 @@
2
2
 
3
3
  ## [Unreleased]
4
4
 
5
+ ## [5.345.147] — 2026-10-18
6
+
7
+ - Worker registry rebuild now also skips Codex worktrees (`.codex/worktrees/`). Same nested-checkout trap as `.claude/worktrees/`.
8
+ - Worker registry rebuild now skips Claude Code worktrees (`.claude/worktrees/`). A nested HQ checkout under a company project used to land in `core/workers/registry.yaml`, and `hq lanes create` then failed with `worker_tenancy_unresolved`.
9
+
10
+ - HQ bots no longer quit and relaunch the HQ desktop app when they answer a message. Bots now run with the desktop update check turned off, so the app is never restarted in the middle of onboarding or a conversation; the app still updates itself as usual.
11
+ - `hq doctor` now reports a release link that does not open, including one left pointing at a deleted update folder. The result tells you to run `hq rescue -y` again. On Windows without Developer Mode, that retry writes a directory link as a junction and a file link as a copy.
12
+ - The bundled sync engine now uses hq-cloud 6.18.85. `hq outposts refresh-config --company <slug>` re-applies the server's job runner configuration to a running company Outpost without rebuilding it (owner or admin).
13
+ - The bundled sync engine now uses hq-cloud 6.18.87. Sync reports every refused stale upload as a failure instead of skipping it quietly.
14
+ - `hq login --no-browser` and `hq auth login --no-browser` print the sign-in URL and wait without launching a browser. CI and Linux sessions without a display use the same behavior. Remote sign-in instructions include SSH port forwarding.
15
+ - `hq files unshare <path>` reports the number of empty entries removed, distinguishes retained grants from a deleted share, and shows the server’s owner/admin-only reason when cleanup is forbidden.
16
+ - Added the native hook engine scaffold and six-platform build checks, including
17
+ Windows GUI-subsystem builds and a 50-launch no-console test. This prepares
18
+ Windows hook parity; installed hook settings and behavior are unchanged.
19
+
5
20
  ## [5.345.146] — 2026-10-17
6
21
  - `hq capacity route` and `hq lanes create --account auto` can now use a Claude account whose weekly limit is used up but whose paid extra usage is on. Pass `--allow-extra-usage` to allow it; the account is picked last. Without the flag, the refusal now says extra usage is on and names the flag.
7
22
 
package/README.md CHANGED
@@ -163,3 +163,17 @@ Use `--target lane:<lane-id>` or
163
163
  `--target session:<claude|codex|grok>:<session-id>` when automatic target
164
164
  detection is not appropriate. Monitor output is framed as script data before
165
165
  it is added to an agent's context.
166
+
167
+ ### Sign in without opening a browser
168
+
169
+ Run `hq login --no-browser` or `hq auth login --no-browser` to print a sign-in
170
+ URL and wait for completion. Open the URL in your browser. HQ also uses this
171
+ mode in CI and on Linux without DISPLAY or WAYLAND_DISPLAY. Existing cached
172
+ sessions are reused.
173
+
174
+ For an SSH host, first connect with `ssh -L 8765:localhost:8765 user@host`,
175
+ then run the login command there and open the printed URL on your computer.
176
+ If your callback port is configured differently, forward that port instead.
177
+ Keep the SSH connection open until login finishes. The sign-in uses a localhost
178
+ callback with PKCE, so there is no device code to enter. It times out after
179
+ 15 minutes. Tokens are cached locally and never printed.
@@ -1170,6 +1170,10 @@ export declare const COMMAND_CATALOG: readonly [{
1170
1170
  readonly flags: "--provider <provider>";
1171
1171
  readonly description: "OAuth provider to use: google, microsoft, or picker";
1172
1172
  readonly hidden: false;
1173
+ }, {
1174
+ readonly flags: "--no-browser";
1175
+ readonly description: "Print the sign-in URL without opening a browser";
1176
+ readonly hidden: false;
1173
1177
  }];
1174
1178
  readonly subcommands: readonly [];
1175
1179
  }, {
@@ -1603,6 +1607,10 @@ export declare const COMMAND_CATALOG: readonly [{
1603
1607
  readonly flags: "--provider <provider>";
1604
1608
  readonly description: "OAuth provider to use: google, microsoft, or picker";
1605
1609
  readonly hidden: false;
1610
+ }, {
1611
+ readonly flags: "--no-browser";
1612
+ readonly description: "Print the sign-in URL without opening a browser";
1613
+ readonly hidden: false;
1606
1614
  }];
1607
1615
  readonly subcommands: readonly [];
1608
1616
  }, {
@@ -2836,7 +2844,7 @@ export declare const COMMAND_CATALOG: readonly [{
2836
2844
  readonly subcommands: readonly [];
2837
2845
  }, {
2838
2846
  readonly name: "unshare";
2839
- readonly description: "Remove a named file access grant, or remove an empty ACL row without --with.";
2847
+ readonly description: "Remove a named file access grant, or remove an empty ACL row or grantee-less entries without --with.";
2840
2848
  readonly aliases: readonly [];
2841
2849
  readonly hidden: false;
2842
2850
  readonly helpOption: true;
@@ -7590,6 +7598,26 @@ export declare const COMMAND_CATALOG: readonly [{
7590
7598
  readonly hidden: false;
7591
7599
  }];
7592
7600
  readonly subcommands: readonly [];
7601
+ }, {
7602
+ readonly name: "refresh-config";
7603
+ readonly description: "Re-apply the server's job runner configuration to the company Outpost (owner or admin)";
7604
+ readonly aliases: readonly [];
7605
+ readonly hidden: false;
7606
+ readonly helpOption: true;
7607
+ readonly helpCommand: false;
7608
+ readonly usage: "[options]";
7609
+ readonly helpText: readonly [];
7610
+ readonly arguments: readonly [];
7611
+ readonly options: readonly [{
7612
+ readonly flags: "--company <slug>";
7613
+ readonly description: "Company slug";
7614
+ readonly hidden: false;
7615
+ }, {
7616
+ readonly flags: "--json";
7617
+ readonly description: "Emit raw JSON";
7618
+ readonly hidden: false;
7619
+ }];
7620
+ readonly subcommands: readonly [];
7593
7621
  }, {
7594
7622
  readonly name: "codex-enable";
7595
7623
  readonly description: "Enable (or retry) Codex on an Outpost";
@@ -1402,6 +1402,11 @@ export const COMMAND_CATALOG = [
1402
1402
  "flags": "--provider <provider>",
1403
1403
  "description": "OAuth provider to use: google, microsoft, or picker",
1404
1404
  "hidden": false
1405
+ },
1406
+ {
1407
+ "flags": "--no-browser",
1408
+ "description": "Print the sign-in URL without opening a browser",
1409
+ "hidden": false
1405
1410
  }
1406
1411
  ],
1407
1412
  "subcommands": []
@@ -1917,6 +1922,11 @@ export const COMMAND_CATALOG = [
1917
1922
  "flags": "--provider <provider>",
1918
1923
  "description": "OAuth provider to use: google, microsoft, or picker",
1919
1924
  "hidden": false
1925
+ },
1926
+ {
1927
+ "flags": "--no-browser",
1928
+ "description": "Print the sign-in URL without opening a browser",
1929
+ "hidden": false
1920
1930
  }
1921
1931
  ],
1922
1932
  "subcommands": []
@@ -3409,7 +3419,7 @@ export const COMMAND_CATALOG = [
3409
3419
  },
3410
3420
  {
3411
3421
  "name": "unshare",
3412
- "description": "Remove a named file access grant, or remove an empty ACL row without --with.",
3422
+ "description": "Remove a named file access grant, or remove an empty ACL row or grantee-less entries without --with.",
3413
3423
  "aliases": [],
3414
3424
  "hidden": false,
3415
3425
  "helpOption": true,
@@ -9245,6 +9255,30 @@ export const COMMAND_CATALOG = [
9245
9255
  ],
9246
9256
  "subcommands": []
9247
9257
  },
9258
+ {
9259
+ "name": "refresh-config",
9260
+ "description": "Re-apply the server's job runner configuration to the company Outpost (owner or admin)",
9261
+ "aliases": [],
9262
+ "hidden": false,
9263
+ "helpOption": true,
9264
+ "helpCommand": false,
9265
+ "usage": "[options]",
9266
+ "helpText": [],
9267
+ "arguments": [],
9268
+ "options": [
9269
+ {
9270
+ "flags": "--company <slug>",
9271
+ "description": "Company slug",
9272
+ "hidden": false
9273
+ },
9274
+ {
9275
+ "flags": "--json",
9276
+ "description": "Emit raw JSON",
9277
+ "hidden": false
9278
+ }
9279
+ ],
9280
+ "subcommands": []
9281
+ },
9248
9282
  {
9249
9283
  "name": "codex-enable",
9250
9284
  "description": "Enable (or retry) Codex on an Outpost",
@@ -14,13 +14,14 @@
14
14
  * session is kept valid by `hq auth refresh` / `hq-auth-refresh` and consumed
15
15
  * by the deploy + sync skills.
16
16
  */
17
+ import { loginWithBrowserPreference } from "../utils/login-browser.js";
17
18
  import { releaseCurrentPackageUseLease, releasePackageUseLeaseAfterResidentPreload } from "../utils/package-use-lease.js";
18
19
  import { preloadResidentPackageModules, reportResidentPackagePreloadFailure } from "../utils/resident-package-preload.js";
19
20
  import * as fs from "node:fs";
20
21
  import { open, realpath } from "node:fs/promises";
21
22
  import path from "node:path";
22
23
  import chalk from "chalk";
23
- import { browserLogin, clearCachedTokens, loadCachedTokens, isExpiring, loadMachineCreds, CognitoAuthError, } from "@indigoai-us/hq-cloud";
24
+ import { clearCachedTokens, loadCachedTokens, isExpiring, loadMachineCreds, CognitoAuthError, } from "@indigoai-us/hq-cloud";
24
25
  import { DEFAULT_COGNITO, refreshCachedSession, resolveCognitoTokenSource, ensureMachineSessionTokens, personTokenCacheFile, machineTokenCacheFile, loadMachineCachedTokens, } from "../utils/cognito-session.js";
25
26
  // Static (node builtins only): a lazy import here would need a resident
26
27
  // preload entry for the auth-login path.
@@ -212,6 +213,7 @@ export function registerAuthCommands(program) {
212
213
  .command("login")
213
214
  .description("Sign in to HQ — opens the Cognito Hosted UI and caches tokens locally")
214
215
  .option("--provider <provider>", "OAuth provider to use: google, microsoft, or picker")
216
+ .option("--no-browser", "Print the sign-in URL without opening a browser")
215
217
  .action(async (options) => {
216
218
  if (resolveCognitoTokenSource() === "machine") {
217
219
  console.log(chalk.green(`Running as ${machineIdentityLabel()} — sessions mint automatically; no browser login needed.`));
@@ -237,7 +239,7 @@ export function registerAuthCommands(program) {
237
239
  }
238
240
  const selection = resolveLoginProviderSelection(options.provider, process.env, rememberedProvider);
239
241
  await releasePackageUseLeaseAfterResidentPreload(() => preloadResidentPackageModules("auth-login"), reportResidentPackagePreloadFailure, releaseCurrentPackageUseLease);
240
- const tokens = await browserLogin(selection.config);
242
+ const tokens = await loginWithBrowserPreference(selection.config, options.browser);
241
243
  try {
242
244
  storeLastLoginProvider(providerFromIdToken(tokens.idToken) ?? selection.providerToRemember);
243
245
  }
@@ -243,7 +243,7 @@ export function spawnDetachedRun(name, dir) {
243
243
  detached: true,
244
244
  windowsHide: true,
245
245
  stdio: ["ignore", fd, fd],
246
- env: { ...process.env, HQ_NO_UPDATE_CHECK: "1" },
246
+ env: { ...process.env, HQ_NO_UPDATE_CHECK: "1", HQ_NO_ENSURE_HQ_DESKTOP: "1" },
247
247
  });
248
248
  fs.closeSync(fd);
249
249
  child.unref();
@@ -267,7 +267,7 @@ export function registerFilesCommand(program) {
267
267
  });
268
268
  files
269
269
  .command("unshare <prefix>")
270
- .description("Remove a named file access grant, or remove an empty ACL row without --with.")
270
+ .description("Remove a named file access grant, or remove an empty ACL row or grantee-less entries without --with.")
271
271
  .option("--with <principal>", "Person uid, agent uid, email address, group id, or '@all' to remove the grant")
272
272
  .action(async (prefix, opts) => {
273
273
  try {
@@ -328,17 +328,21 @@ export function registerFilesCommand(program) {
328
328
  }
329
329
  if (!res.ok) {
330
330
  if (res.status === 403) {
331
- console.error(chalk.red("Not authorized to remove this ACL row"));
332
- await offerAccessLadder(canonicalPrefix, {
333
- company: files.opts().company,
334
- });
331
+ console.error(chalk.red(body.error ?? "Not authorized to remove this ACL row"));
332
+ console.error(chalk.dim("Ask a company admin to remove this entry."));
335
333
  }
336
334
  else {
337
335
  console.error(chalk.red(body.error ?? "Unable to remove ACL row"));
338
336
  }
339
337
  process.exit(1);
340
338
  }
341
- console.log(chalk.green(`Removed empty ACL pattern '${canonicalPrefix}'. It now follows its parent folder's access, so anyone who can see that parent can see this folder.`));
339
+ const removedCount = body.removedEntries;
340
+ const cleanupMessage = typeof removedCount === "number" && removedCount > 0
341
+ ? `Removed ${removedCount} empty ${removedCount === 1 ? "entry" : "entries"} from '${canonicalPrefix}'. `
342
+ : "";
343
+ console.log(chalk.green(body.aclRemoved === false
344
+ ? `${cleanupMessage || `Removed grantee-less entries from '${canonicalPrefix}'. `}Existing grants remain.`
345
+ : `${cleanupMessage || `Removed empty ACL pattern '${canonicalPrefix}'. `}It now follows its parent folder's access, so anyone who can see that parent can see this folder.`));
342
346
  return;
343
347
  }
344
348
  const res = await vaultApiFetch({
@@ -1,10 +1,11 @@
1
1
  /**
2
2
  * hq login — opens browser for Cognito auth.
3
3
  */
4
+ import { loginWithBrowserPreference } from "../utils/login-browser.js";
4
5
  import { releaseCurrentPackageUseLease, releasePackageUseLeaseAfterResidentPreload } from "../utils/package-use-lease.js";
5
6
  import { preloadResidentPackageModules, reportResidentPackagePreloadFailure } from "../utils/resident-package-preload.js";
6
7
  import chalk from 'chalk';
7
- import { browserLogin, loadCachedTokens, isExpiring } from '@indigoai-us/hq-cloud';
8
+ import { loadCachedTokens, isExpiring } from '@indigoai-us/hq-cloud';
8
9
  import { cognitoConfigForLoginProvider } from '../utils/login-provider.js';
9
10
  import * as readline from "node:readline/promises";
10
11
  import { listActiveMembershipCompanies } from "../lib/mesh/api.js";
@@ -31,6 +32,7 @@ export function registerLoginCommand(program) {
31
32
  .command('login')
32
33
  .description('Authenticate with HQ via Cognito')
33
34
  .option('--provider <provider>', 'OAuth provider to use: google, microsoft, or picker')
35
+ .option("--no-browser", "Print the sign-in URL without opening a browser")
34
36
  .action(async (options) => {
35
37
  let accessToken;
36
38
  let packageUseLeaseReleased = false;
@@ -51,8 +53,7 @@ export function registerLoginCommand(program) {
51
53
  }
52
54
  else {
53
55
  await releaseForInteractiveWait();
54
- console.log('Opening browser for authentication...');
55
- const tokens = await browserLogin(cognitoConfigForLoginProvider(options.provider));
56
+ const tokens = await loginWithBrowserPreference(cognitoConfigForLoginProvider(options.provider), options.browser);
56
57
  const who = peekIdToken(tokens.idToken).email ?? 'HQ';
57
58
  console.log(chalk.green(`Logged in as ${who}`));
58
59
  accessToken = tokens.accessToken;