@indigoai-us/hq-cli 5.125.0 → 5.127.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.
- package/CHANGELOG.md +329 -0
- package/assets/bot-workers/setup/skills/joining-a-team.md +125 -0
- package/assets/bot-workers/setup/skills/your-business.md +270 -0
- package/assets/bot-workers/setup/worker.yaml +189 -58
- package/assets/lanes-hooks/hq-lanes-drain.json +15 -0
- package/assets/lanes-hooks/hq-lanes-drain.mjs +254 -0
- package/assets/lanes-hooks/hq-lanes-drain.sh +21 -0
- package/assets/lanes-reconcile/hq-lanes-reconcile.service +11 -0
- package/assets/lanes-reconcile/hq-lanes-reconcile.timer +12 -0
- package/dist/command-catalog.generated.d.ts +643 -6
- package/dist/command-catalog.generated.js +836 -6
- package/dist/command-registration-plan.d.ts +7 -0
- package/dist/command-registration-plan.js +11 -1
- package/dist/commands/agents.d.ts +12 -0
- package/dist/commands/agents.js +46 -2
- package/dist/commands/bot.d.ts +10 -0
- package/dist/commands/bot.js +6 -0
- package/dist/commands/lanes.d.ts +114 -0
- package/dist/commands/lanes.js +2969 -0
- package/dist/commands/mesh.js +287 -24
- package/dist/commands/onboard-create-identity.d.ts +26 -0
- package/dist/commands/onboard-create-identity.js +23 -0
- package/dist/commands/onboard.js +13 -4
- package/dist/lib/bot/progress.d.ts +6 -0
- package/dist/lib/bot/progress.js +16 -0
- package/dist/lib/bot/runtime/grok.d.ts +30 -7
- package/dist/lib/bot/runtime/grok.js +86 -8
- package/dist/lib/bot/runtime/index.js +15 -8
- package/dist/lib/bot/runtime/messages-stream.d.ts +12 -3
- package/dist/lib/bot/runtime/messages-stream.js +49 -3
- package/dist/lib/lanes/accounts.d.ts +103 -0
- package/dist/lib/lanes/accounts.js +318 -0
- package/dist/lib/lanes/compaction.d.ts +96 -0
- package/dist/lib/lanes/compaction.js +197 -0
- package/dist/lib/lanes/config.d.ts +71 -0
- package/dist/lib/lanes/config.js +408 -0
- package/dist/lib/lanes/delivery.d.ts +151 -0
- package/dist/lib/lanes/delivery.js +354 -0
- package/dist/lib/lanes/dropbox.d.ts +96 -0
- package/dist/lib/lanes/dropbox.js +408 -0
- package/dist/lib/lanes/effort.d.ts +50 -0
- package/dist/lib/lanes/effort.js +109 -0
- package/dist/lib/lanes/errors.d.ts +39 -0
- package/dist/lib/lanes/errors.js +72 -0
- package/dist/lib/lanes/hooks-install.d.ts +81 -0
- package/dist/lib/lanes/hooks-install.js +326 -0
- package/dist/lib/lanes/hq-root.d.ts +19 -0
- package/dist/lib/lanes/hq-root.js +28 -0
- package/dist/lib/lanes/index.d.ts +49 -0
- package/dist/lib/lanes/index.js +27 -0
- package/dist/lib/lanes/liveness.d.ts +95 -0
- package/dist/lib/lanes/liveness.js +332 -0
- package/dist/lib/lanes/machine-identity.d.ts +34 -0
- package/dist/lib/lanes/machine-identity.js +92 -0
- package/dist/lib/lanes/mesh-events.d.ts +109 -0
- package/dist/lib/lanes/mesh-events.js +275 -0
- package/dist/lib/lanes/outpost-dispatch.d.ts +65 -0
- package/dist/lib/lanes/outpost-dispatch.js +90 -0
- package/dist/lib/lanes/questions.d.ts +75 -0
- package/dist/lib/lanes/questions.js +243 -0
- package/dist/lib/lanes/quota.d.ts +95 -0
- package/dist/lib/lanes/quota.js +320 -0
- package/dist/lib/lanes/reconcile-install.d.ts +69 -0
- package/dist/lib/lanes/reconcile-install.js +221 -0
- package/dist/lib/lanes/reconcile.d.ts +102 -0
- package/dist/lib/lanes/reconcile.js +985 -0
- package/dist/lib/lanes/registry.d.ts +116 -0
- package/dist/lib/lanes/registry.js +521 -0
- package/dist/lib/lanes/spawn.d.ts +274 -0
- package/dist/lib/lanes/spawn.js +1363 -0
- package/dist/lib/lanes/store.d.ts +68 -0
- package/dist/lib/lanes/store.js +745 -0
- package/dist/lib/lanes/throttle.d.ts +89 -0
- package/dist/lib/lanes/throttle.js +297 -0
- package/dist/lib/lanes/types.d.ts +535 -0
- package/dist/lib/lanes/types.js +350 -0
- package/dist/lib/lanes/watcher-main.d.ts +9 -0
- package/dist/lib/lanes/watcher-main.js +22 -0
- package/dist/lib/lanes/watcher.d.ts +216 -0
- package/dist/lib/lanes/watcher.js +859 -0
- package/dist/lib/mesh/api.d.ts +71 -7
- package/dist/lib/mesh/api.js +167 -28
- package/dist/lib/mesh/live/backfill-held.d.ts +18 -7
- package/dist/lib/mesh/live/backfill-held.js +66 -21
- package/dist/lib/mesh/live/daemon/config.d.ts +27 -0
- package/dist/lib/mesh/live/daemon/config.js +75 -0
- package/dist/lib/mesh/live/daemon/index.d.ts +4 -3
- package/dist/lib/mesh/live/daemon/index.js +3 -3
- package/dist/lib/mesh/live/daemon/install.d.ts +143 -1
- package/dist/lib/mesh/live/daemon/install.js +444 -2
- package/dist/lib/mesh/live/daemon/paths.d.ts +2 -0
- package/dist/lib/mesh/live/daemon/paths.js +2 -0
- package/dist/lib/mesh/live/daemon/run.d.ts +2 -0
- package/dist/lib/mesh/live/daemon/run.js +111 -54
- package/dist/lib/mesh/live/daemon/state.d.ts +2 -0
- package/dist/lib/mesh/live/daemon/transcript-watch.d.ts +3 -0
- package/dist/lib/mesh/live/daemon/transcript-watch.js +31 -8
- package/dist/lib/scan-packages/index.d.ts +2 -0
- package/dist/lib/scan-packages/index.js +18 -13
- package/dist/lib/work-context/config.d.ts +20 -0
- package/dist/lib/work-context/config.js +26 -5
- package/dist/lib/work-context/reconcile.js +28 -7
- package/dist/lib/work-context/state.d.ts +12 -0
- package/dist/lib/work-context/state.js +131 -3
- package/dist/lib/work-context/windows-acl.d.ts +123 -0
- package/dist/lib/work-context/windows-acl.js +425 -0
- package/dist/utils/pack-contributions.js +5 -4
- package/package.json +3 -1
package/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,335 @@
|
|
|
2
2
|
|
|
3
3
|
## [Unreleased]
|
|
4
4
|
|
|
5
|
+
## [5.127.0] — 2026-09-22
|
|
6
|
+
|
|
7
|
+
### Added
|
|
8
|
+
|
|
9
|
+
- Every composed lane brief and every resume turn carries a foreground-only
|
|
10
|
+
rule after the standing authorization: run every command, test suite and
|
|
11
|
+
check in the foreground and wait for it; a turn that ends before the envelope
|
|
12
|
+
is written is classified interrupted.
|
|
13
|
+
- The spec §4 envelope repair turn now runs for grok as well. A provider with
|
|
14
|
+
no session resume gets one fresh single-turn invocation on the same account
|
|
15
|
+
carrying the schema, the parser error and the raw failed output. The lane
|
|
16
|
+
records `envelope_repair.mode` as `resume` (claude, codex) or `fresh_turn`
|
|
17
|
+
(grok) and `hq lanes show` prints it as `envelope_repair_mode`.
|
|
18
|
+
- Lane records now reject omissions of required `hq-lane.v1` fields, and lane
|
|
19
|
+
mutations enforce the durable field-writer ownership map at the store boundary.
|
|
20
|
+
The map grants `reconcile` the quota fields it writes during dead-host
|
|
21
|
+
recovery, the outpost pickup account bind carries the `spawn` writer, and
|
|
22
|
+
`terminal_details` and `outpost_command_id` are typed and owned. The writer
|
|
23
|
+
argument is a required writer name; the function-form call that skipped the
|
|
24
|
+
ownership check is gone. The updater receives a deep clone and the check
|
|
25
|
+
compares against the pre-update snapshot, so mutating the argument in place
|
|
26
|
+
cannot bypass ownership.
|
|
27
|
+
- Answer notes reach a resumed lane: `answered-questions.json` carries the
|
|
28
|
+
operator's `--notes` text read from the lane's own body store, and the resume
|
|
29
|
+
prompt renders each answer as its choice followed by the notes.
|
|
30
|
+
- Every lane brief and every resume turn carries a standing authorization
|
|
31
|
+
paragraph: the brief authorises completing every item it lists, and a
|
|
32
|
+
`decision: ask` envelope is only for a decision the brief does not settle.
|
|
33
|
+
- A question whose options are only continue and stop is recorded with
|
|
34
|
+
`question_kind: "continue"` and `hq lanes questions list` prints it with
|
|
35
|
+
`flag: "continue-loop"`. Nothing answers it automatically.
|
|
36
|
+
- `hq lanes list` reports `senior_lost: true` for a running lane whose senior
|
|
37
|
+
session is absent, ended, or lost, without mutating the lane.
|
|
38
|
+
- `hq lanes questions answer --freeform <text>` answers a question that offered
|
|
39
|
+
options with free text and records `answer_kind: freeform`.
|
|
40
|
+
- `hq lanes resume <lane-id> [--text <message>]` resumes an `interrupted`,
|
|
41
|
+
`done` or `blocked` lane on its recorded provider session and records
|
|
42
|
+
`resumed_from`. Codex lanes record their session id at spawn and resume with
|
|
43
|
+
`codex exec resume`, so `hq lanes message` and the envelope repair turn now
|
|
44
|
+
work for exited Codex lanes as they do for Claude.
|
|
45
|
+
- Lanes now report to the work mesh from the watcher, not only at create. A
|
|
46
|
+
lane that finishes posts a completion event and moves its story to review;
|
|
47
|
+
one that stops to ask posts the question ids; one that is blocked posts the
|
|
48
|
+
reason. While a lane is working, the watcher posts a progress event when it
|
|
49
|
+
sees a new tool call or new output, at most once per five minutes per lane
|
|
50
|
+
(`providers.<provider>.progress_event_min_interval_ms` in
|
|
51
|
+
`personal/lanes/config.json`), and never for silence. The watcher signs in
|
|
52
|
+
the same way the session hooks do and never opens a browser; when it cannot
|
|
53
|
+
reach the mesh it writes `mesh_event_failed` to the lane's watcher log and
|
|
54
|
+
the lane's state is unchanged. On the wire, lane events use the mesh's
|
|
55
|
+
existing activity, question, and note kinds, because the server rejects
|
|
56
|
+
unknown kinds.
|
|
57
|
+
- A lane whose final output is not a valid envelope gets one repair turn: the
|
|
58
|
+
same session is resumed with the schema, the parser error, and the raw text,
|
|
59
|
+
and asked for the corrected JSON only. If that also fails the lane is
|
|
60
|
+
`failed` with reason `envelope_invalid`, and `envelope_repair` on the record
|
|
61
|
+
carries both errors. Codex and Grok lanes cannot be resumed after exit, so
|
|
62
|
+
they still fail on the first parse error; the record says why no repair ran.
|
|
63
|
+
- A worker with `verification.approval_required` or `human_checkpoints` now
|
|
64
|
+
briefs its lane to stop at each checkpoint with a `decision: ask` envelope
|
|
65
|
+
naming the checkpoint. The resume prompt after the answer carries the answer
|
|
66
|
+
inline as well as naming the answers file.
|
|
67
|
+
- `hq lanes ask` retries delivery three times, waiting 5 s then 15 s, when the
|
|
68
|
+
CLI is being replaced under it. On final failure it writes
|
|
69
|
+
`ask_delivery_failed.json` and returns `ask_delivery_failed`; the lane's
|
|
70
|
+
state is never changed.
|
|
71
|
+
- You can hand a piece of work off to run on its own, and it keeps going after
|
|
72
|
+
you close the window. If it hits something only you can decide, it stops and
|
|
73
|
+
asks instead of guessing, and picks up again the moment you answer — you no
|
|
74
|
+
longer have to sit and watch it. If it goes quiet for twenty minutes, you are
|
|
75
|
+
told. Work sent to a second machine that would have landed back on the one
|
|
76
|
+
that asked is stopped before it starts.
|
|
77
|
+
- `hq lanes create --model` records the model on the lane and passes the
|
|
78
|
+
provider's own flag (`--model` for Claude, `-m` for Codex and Grok).
|
|
79
|
+
Account and provider `model` keys in `personal/lanes/config.json` are
|
|
80
|
+
defaults; `--model` wins. An empty `--model` is refused.
|
|
81
|
+
- Lane envelopes may include `story_complete` and `story_complete_reason`.
|
|
82
|
+
`story_complete true` requires `story_status done`; `false` forbids it.
|
|
83
|
+
Both are copied onto the lane record when an envelope is ingested.
|
|
84
|
+
- `hq lanes create --effort <level>` sets reasoning effort per provider
|
|
85
|
+
(`--effort` for Claude, `-c model_reasoning_effort` for Codex,
|
|
86
|
+
`--reasoning-effort` for Grok), validated against each provider's own set.
|
|
87
|
+
`effort` on an account or provider in `personal/lanes/config.json` is the
|
|
88
|
+
default; with nothing set, an Opus or Fable model runs at `low`.
|
|
89
|
+
- A resumed Claude lane whose last message is older than `compact_after_ms`
|
|
90
|
+
(default one hour) is compacted with `/compact` before the resume, and the
|
|
91
|
+
lane records the outcome and the before/after context size. `hq lanes
|
|
92
|
+
message --no-compact` skips it once. `accounts list` and `show` report
|
|
93
|
+
model, effort and the last compaction.
|
|
94
|
+
- `--worker` resolves workers from `core/workers`, `personal/workers`,
|
|
95
|
+
`companies/<co>/workers`, and packages mounted by `hq core scan-packages`.
|
|
96
|
+
A worker id present in two trees is refused; a pack worker that is declared
|
|
97
|
+
but not mounted is `package_workers_unmounted`.
|
|
98
|
+
- A provider 429 is recorded per account and model in
|
|
99
|
+
`personal/lanes/quota.json` (`account_quota_exhausted` with the reset time,
|
|
100
|
+
or `account_model_unavailable` when a model needs credits). The balancer
|
|
101
|
+
skips only what cannot run and never rewrites the operator's `enabled`.
|
|
102
|
+
- `hq mesh story` accepts `--assignee <uid|me|none>` with or without `--status`.
|
|
103
|
+
`me` uses the authenticated person or agent and refuses the synthetic session
|
|
104
|
+
identity. `none` clears the assignee. The command does not send an actor.
|
|
105
|
+
- `hq mesh project set <projectId> --company <slug>` now reads and merges the
|
|
106
|
+
current Board view before replacing it, so a name or description update keeps
|
|
107
|
+
existing stories and repository bindings. It accepts repository bindings from
|
|
108
|
+
PRD `metadata.repos`, `--repos-json`, or repeatable `--repo <path[@branch]>`.
|
|
109
|
+
`hq mesh project register <projectId> --company <slug>` registers the Board's
|
|
110
|
+
deterministic project channel and genesis thread without raw API calls.
|
|
111
|
+
- A work-context session-state lock or directory creation failure is reported
|
|
112
|
+
as not tracking (exit 3) instead of an uncaught filesystem error.
|
|
113
|
+
- The Work Mesh daemon now distinguishes an explicit device-default membership
|
|
114
|
+
revocation from malformed or unavailable membership lookups. Temporary
|
|
115
|
+
failures preserve attribution and retry later; explicit denials clear only
|
|
116
|
+
the unchanged device-default binding through the shared session-state lock,
|
|
117
|
+
so concurrent rebinds are preserved. Transcript-start discovery also leaves
|
|
118
|
+
unavailable lookups unstarted and retries with bounded backoff.
|
|
119
|
+
|
|
120
|
+
### Fixed
|
|
121
|
+
|
|
122
|
+
- `hq agents status` no longer tells you to sign in to a brain that is already
|
|
123
|
+
signed in. A device pairing file can outlive the sign-in it started, so the
|
|
124
|
+
box sign-in probe now decides whether the prompt is shown. Grok and Codex
|
|
125
|
+
prompts are matched to their own brain slot; a Claude prompt has no slot and
|
|
126
|
+
is unaffected.
|
|
127
|
+
- Lane watcher mesh calls now time out, progress events only follow new
|
|
128
|
+
activity, and a persisted progress timestamp prevents duplicate events after
|
|
129
|
+
a watcher restart. Invalid-envelope repair is limited to one attempt even
|
|
130
|
+
when the repair writes a different envelope filename.
|
|
131
|
+
- Completion mesh delivery attempts the thread event and story review update
|
|
132
|
+
independently. Repair prompts cap inlined malformed JSON while retaining the
|
|
133
|
+
raw envelope path.
|
|
134
|
+
|
|
135
|
+
- `hq lanes reconcile install --enable` now enables the systemd user timer; the
|
|
136
|
+
generated unit uses `KillMode=process` so admitted lanes survive the pass, and
|
|
137
|
+
its PATH carries the directories of the resolved provider binaries. A provider
|
|
138
|
+
binary missing from PATH at spawn leaves the lane `queued` with
|
|
139
|
+
`provider_binary_missing` instead of failing it.
|
|
140
|
+
- A provider binary missing from PATH re-queues a lane only on admission. An
|
|
141
|
+
answered-question or operator-message resume keeps the lane's recorded state
|
|
142
|
+
and returns `provider_binary_missing` with the searched PATH, so the next
|
|
143
|
+
reconcile resumes the recorded session instead of starting a fresh run and
|
|
144
|
+
the operator message is not lost.
|
|
145
|
+
- `hq lanes reconcile install` succeeds on a box with only one provider
|
|
146
|
+
installed. The unit PATH carries the providers that resolve; the result lists
|
|
147
|
+
`providers_resolved`, `providers_unresolved`, and a `warnings` line per
|
|
148
|
+
missing provider. It refuses with `provider_binary_unresolved` only when no
|
|
149
|
+
enabled provider resolves.
|
|
150
|
+
- `hq lanes questions answer` treats a whitespace-only `--freeform` as absent,
|
|
151
|
+
so `--choice` is validated against the options and recorded as an option
|
|
152
|
+
answer instead of an empty freeform answer.
|
|
153
|
+
- A synced question conflict sidecar whose `answer_history` is not an array is
|
|
154
|
+
skipped like any other unreadable sidecar instead of failing every read of
|
|
155
|
+
the question.
|
|
156
|
+
- `hq lanes resume` now keeps terminal lanes terminal when account binding
|
|
157
|
+
fails, records project or story attribution without requiring `--text`, and
|
|
158
|
+
rejects a concurrent resume that has already become running. Blocked mesh
|
|
159
|
+
notes use the accepted `audit` note kind and include their reason in text so
|
|
160
|
+
the server preserves the marker.
|
|
161
|
+
|
|
162
|
+
- `hq agents list` shows an agent whose removal is under way as `removing`
|
|
163
|
+
rather than the runtime status it had before the removal started. An agent
|
|
164
|
+
that never finished setting up and is then removed used to keep reading
|
|
165
|
+
`provisioning` until the teardown completed, so a removal that stalled
|
|
166
|
+
looked like a removal that was never accepted. A finished teardown reads
|
|
167
|
+
`removed`; every other agent is unchanged.
|
|
168
|
+
- `hq lanes accounts list` treats Claude as logged in when
|
|
169
|
+
`.credentials.json` exists. Missing Claude credentials are reported as
|
|
170
|
+
unknown, not logged out. Codex and Grok still use `auth.json`.
|
|
171
|
+
- With no `--account`, a lane is assigned the least-loaded enabled
|
|
172
|
+
logged-in account rather than `default_account`.
|
|
173
|
+
- A lane watcher now writes a JSON line to `logs/watcher.out` for each
|
|
174
|
+
decision that changes what it believes: a liveness transition, a silence
|
|
175
|
+
deadline, an envelope appearing, the exit classification, and the
|
|
176
|
+
terminal record write. `hq lanes logs` reports each stream's path, size
|
|
177
|
+
in bytes, and lines, so an empty log file is distinguishable from a
|
|
178
|
+
missing lane. `watcher.out` is capped at 256 KiB by dropping the oldest
|
|
179
|
+
complete lines. `hq lanes message` refuses a lane that will never read
|
|
180
|
+
the drop box (`awaiting_input`, `blocked`, and every terminal state) and
|
|
181
|
+
still accepts a queued lane. After the HQ root is resolved, `hq lanes`
|
|
182
|
+
chdirs into it; relative `--brief-file` and `--payload-file` paths still
|
|
183
|
+
resolve against the caller's original directory.
|
|
184
|
+
- `hq lanes` no longer treats a git worktree's `.claude` folder as the HQ
|
|
185
|
+
root, and it honours `$HQ_ROOT` the same way the watcher and reconcile
|
|
186
|
+
timer already did. Listing or creating a lane from a worktree talks to
|
|
187
|
+
the real store, or fails out loud — it does not return an empty success
|
|
188
|
+
against a directory nothing else reads.
|
|
189
|
+
- Creating a lane with `--outpost` now pushes it through `hq outposts exec`
|
|
190
|
+
instead of leaving a queued row that no machine will pick up. If the
|
|
191
|
+
Outpost is unreachable, the lane is failed, not queued.
|
|
192
|
+
- A lane that finishes by asking a question now actually queues that question,
|
|
193
|
+
so someone can answer it and the lane can continue. Stopping a lane now
|
|
194
|
+
stops the process, not only the record. The drain hook that delivers
|
|
195
|
+
mid-run answers is installed into the account home instead of sitting unused
|
|
196
|
+
in the package. The periodic reconcile timer now names this HQ tree, so it
|
|
197
|
+
does not wander into `$HOME/.claude`. A live lane heartbeats from its
|
|
198
|
+
watcher; a dead watcher is started again; a reused PID is not treated as
|
|
199
|
+
the worker still running; a malformed drop-box line no longer wedges every
|
|
200
|
+
tool call.
|
|
201
|
+
- `hq mesh start` now resolves its claimant from the token that authenticates
|
|
202
|
+
the request before considering a same-identity cache entry. This prevents an
|
|
203
|
+
agent from claiming work as a cached human and stops locally before creating
|
|
204
|
+
a thread when no authenticated claimant can be established.
|
|
205
|
+
|
|
206
|
+
- `hq mesh context backfill-held` no longer reports `reconciled: 0` when
|
|
207
|
+
`--dry-run` predicts non-zero reconcilable sessions. The check that decides
|
|
208
|
+
whether reconcile produced a durable company binding now recognises a
|
|
209
|
+
persisted `companySlug` as sufficient — the daemon resolves the uid on its
|
|
210
|
+
next retry — instead of requiring `companyUid`, which is absent when the
|
|
211
|
+
reconciler runs without a network membership call. Sessions that have no
|
|
212
|
+
company evidence at all now appear in a separate `noEvidence` counter so
|
|
213
|
+
operators can tell them apart from sessions that were genuinely reconciled
|
|
214
|
+
as slug-only bindings.
|
|
215
|
+
|
|
216
|
+
## [5.126.0] — 2026-09-21
|
|
217
|
+
|
|
218
|
+
### Fixed
|
|
219
|
+
|
|
220
|
+
- `hq mesh start` works for people again. It was sending your email address as
|
|
221
|
+
the claimant, and the server compares that to your person id, so every human
|
|
222
|
+
start failed with "claimedBy must match the authenticated author" and left
|
|
223
|
+
the thread unclaimed. Claims now carry your resolved person id (bots keep
|
|
224
|
+
their agent id).
|
|
225
|
+
|
|
226
|
+
### Changed
|
|
227
|
+
|
|
228
|
+
- On Windows, the mesh daemon's Scheduled Task now names the HQ root it was
|
|
229
|
+
installed for right in the task command (`mesh daemon run --hq-root <path>`)
|
|
230
|
+
instead of relying on a remembered list of roots. Install only wraps the
|
|
231
|
+
daemon in `conhost.exe --headless` when the machine is new enough to support
|
|
232
|
+
it (Windows 10 1809 or later) and says which mode it chose. `hq mesh daemon
|
|
233
|
+
status` now reports when the task's last start failed, and reminds you that
|
|
234
|
+
the task only runs while you are logged on. macOS and Linux are unchanged.
|
|
235
|
+
|
|
236
|
+
- `hq mesh daemon install` no longer mistakes a code repo for your HQ. It
|
|
237
|
+
accepts `--hq-root <path>`, otherwise uses `HQ_ROOT`, otherwise walks up
|
|
238
|
+
from the current folder to the nearest real HQ tree (one with
|
|
239
|
+
`companies/manifest.yaml` and `core/`, `.claude/`, or `personal/`). A folder
|
|
240
|
+
that only has `.claude/` does not count. If nothing qualifies, install stops
|
|
241
|
+
and tells you to pass `--hq-root` instead of recording the wrong root. The
|
|
242
|
+
install confirmation now leads with the root it chose and how, and `hq mesh
|
|
243
|
+
daemon status` prints the root the task actually carries and warns when that
|
|
244
|
+
folder has since moved or been deleted.
|
|
245
|
+
|
|
246
|
+
- The setup bot now recognises when you have joined a company that someone
|
|
247
|
+
else already built. Instead of asking what kind of business you own and
|
|
248
|
+
offering to connect apps your team connected months ago, it shows you what
|
|
249
|
+
is already there in real names and counts, answers one real question from
|
|
250
|
+
your company's own memory, asks what you do there, and offers only what is
|
|
251
|
+
missing for you. Things only an owner can do now name the owner instead of
|
|
252
|
+
failing.
|
|
253
|
+
|
|
254
|
+
- The setup bot asks which tools you actually use and connects each one
|
|
255
|
+
however that tool needs it, after recommending the few things a business
|
|
256
|
+
like yours should set up. It no longer works from a fixed list of apps.
|
|
257
|
+
|
|
258
|
+
- Setup no longer asks for your name when you are already signed in, and no
|
|
259
|
+
longer offers to skip itself.
|
|
260
|
+
|
|
261
|
+
### Fixed
|
|
262
|
+
|
|
263
|
+
- The desktop grok bot talks to grok 0.2.56 again. That CLI dropped
|
|
264
|
+
`--output-format streaming-messages-json` (only `plain`, `json`, and
|
|
265
|
+
`streaming-json` remain). The bot now reads the value from `grok --help`
|
|
266
|
+
once and caches it, retries with `streaming-json` if grok rejects the old
|
|
267
|
+
flag, and concatenates `streaming-json` text deltas for the reply instead
|
|
268
|
+
of treating them as Anthropic Messages events.
|
|
269
|
+
|
|
270
|
+
- `hq core scan-packages` writes pack-mount symlinks relative to the host
|
|
271
|
+
directory, so they survive a tree moving between machines. A leftover
|
|
272
|
+
absolute link from another host, or an absolute link that still points at
|
|
273
|
+
this pack's payload, is rewritten to the relative form on the next scan; a
|
|
274
|
+
correct relative link is left alone.
|
|
275
|
+
|
|
276
|
+
- Work Mesh reconcile now owns company attribution explicitly on the acked
|
|
277
|
+
path for every register where `resolvedCompany.uid` is set, not only fully
|
|
278
|
+
bound sessions. Previously the non-bound acked path had no reconcile-owned
|
|
279
|
+
attribution write and relied on an incidental side effect of
|
|
280
|
+
`writeAckedRegisterState` → `writeAcknowledgedRegisterBinding`; that side
|
|
281
|
+
effect already wrote `companyUid`/`companySlug` for ops carrying a uid, so
|
|
282
|
+
the tenant was not dropped in practice, but any future acked path that
|
|
283
|
+
preceded or skipped that call would silently lose it. The fix makes
|
|
284
|
+
attribution explicit: a company-only ack is projected as `needs_project`
|
|
285
|
+
with its tenant intact, the write reflects the true classification, and no
|
|
286
|
+
`projectId`, `taskId`, or binding episode is fabricated on partial paths.
|
|
287
|
+
Note: a company resolved by slug only (no uid) is still not attributed on
|
|
288
|
+
either path.
|
|
289
|
+
|
|
290
|
+
- The setup bot no longer posts the same question twice when a turn takes a
|
|
291
|
+
while: a question asked in an interim update is held back if the final
|
|
292
|
+
answer repeats it.
|
|
293
|
+
|
|
294
|
+
- On Windows, the work-context config safety check now inspects the file's
|
|
295
|
+
Windows ACL instead of POSIX mode bits, so `hq mesh context reconcile` no
|
|
296
|
+
longer refuses every run with "unsafe permissions 666" and session state and
|
|
297
|
+
register operations are written again. The config file and its directory must
|
|
298
|
+
be writable only by the current user, SYSTEM, and Administrators; any other
|
|
299
|
+
principal with write access is rejected, matched by SID so localized account
|
|
300
|
+
names do not matter, and named in the error. When the ACL cannot be read
|
|
301
|
+
at all (icacls missing, non-NTFS volume), the check follows a documented
|
|
302
|
+
reduced-guarantee path: it prints one diagnostic that the config is
|
|
303
|
+
unprotected on this platform and continues rather than blocking. macOS and
|
|
304
|
+
Linux behaviour is unchanged.
|
|
305
|
+
|
|
306
|
+
### Added
|
|
307
|
+
|
|
308
|
+
- `hq mesh daemon install` now works on Windows. It registers a per-user
|
|
309
|
+
Scheduled Task (`ai.getindigo.hq-mesh-daemon`) that starts the mesh daemon at
|
|
310
|
+
logon, hidden, with no execution time limit and a restart-on-failure policy,
|
|
311
|
+
and starts it right away. `hq mesh daemon status` reports whether the task is
|
|
312
|
+
registered and running, `hq mesh daemon uninstall` ends and removes it, and a
|
|
313
|
+
CLI update restarts it like the macOS and Linux services. Before this the
|
|
314
|
+
three commands answered "No service manager integration on this platform",
|
|
315
|
+
so the session-event spool never drained on Windows. The task definition is
|
|
316
|
+
written as XML under `~/.hq/work-mesh/daemon/` and registered with
|
|
317
|
+
`schtasks.exe`; no new dependencies. macOS and Linux behaviour is unchanged.
|
|
318
|
+
|
|
319
|
+
- `hq bot list --json` reports `busy` and `busySince` for each bot on this
|
|
320
|
+
computer, and `hq bot status` shows an `answering:` line. Apps use this to
|
|
321
|
+
keep a "thinking" indicator up for a whole turn, rather than ending it the
|
|
322
|
+
moment the bot posts a progress note.
|
|
323
|
+
|
|
324
|
+
- Library layer for `hq lanes` (`src/lib/lanes/`): lane/question record store
|
|
325
|
+
with compare-and-set writes, provider-account resolution, CPU/memory throttle,
|
|
326
|
+
session liveness from the work-mesh spool, and path-keyed worker tenancy.
|
|
327
|
+
|
|
328
|
+
- `hq lanes` command surface: create/list/show/message/reparent/logs/stop,
|
|
329
|
+
non-blocking ask, questions list/show/answer/escalate/cancel, accounts
|
|
330
|
+
list/login/enable/disable, and sessions list/show. Create admits against
|
|
331
|
+
provider caps, the bounded queue, and the host throttle, then leaves the
|
|
332
|
+
lane queued — process spawn is an explicit not-implemented seam.
|
|
333
|
+
|
|
5
334
|
## [5.125.0] — 2026-09-20
|
|
6
335
|
|
|
7
336
|
### Fixed
|
|
@@ -0,0 +1,125 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: joining-a-team
|
|
3
|
+
title: Joining a team
|
|
4
|
+
description: Set up someone who installed HQ into a company that already exists, by showing them what they just inherited and adding what is missing for them.
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
# Joining a team
|
|
8
|
+
|
|
9
|
+
Most people who install HQ from here on are not founders. They are the fourth
|
|
10
|
+
person at a company that already has channels, connected apps, meetings,
|
|
11
|
+
knowledge and bots. Their setup is not "build an HQ". It is "here is the HQ you
|
|
12
|
+
just walked into, and here is what I will add for you."
|
|
13
|
+
|
|
14
|
+
Getting this wrong is what makes setup feel generic: asking a new account
|
|
15
|
+
manager what kind of business they own, or offering to connect a note taker
|
|
16
|
+
their company connected months ago.
|
|
17
|
+
|
|
18
|
+
## 1. Work out that this is an existing company, before you ask anything
|
|
19
|
+
|
|
20
|
+
Their companies come from the "Owner context" block at the top of their
|
|
21
|
+
message. Never use your own `hq` membership for this; that describes you, the
|
|
22
|
+
bot.
|
|
23
|
+
|
|
24
|
+
When the block names a company, look at how much is already in it. Quiet
|
|
25
|
+
reads, one message of output for them at the end, never a transcript of the
|
|
26
|
+
looking:
|
|
27
|
+
|
|
28
|
+
- People: `hq members list` (and `hq people list`) for the company.
|
|
29
|
+
- Conversations: `hq channels`.
|
|
30
|
+
- Apps the company already connected: `hq integrations list`.
|
|
31
|
+
- Bots already working there: `hq agents list`, and `hq bot list --remote`.
|
|
32
|
+
- What the shared memory holds: the company folder under `companies/<slug>/`
|
|
33
|
+
(knowledge, projects, people), `hq meetings list --limit 5`,
|
|
34
|
+
`hq signals list --limit 10`, and `hq search "<a word from their work>"`.
|
|
35
|
+
|
|
36
|
+
Then decide which of these you are in:
|
|
37
|
+
|
|
38
|
+
- **A company with things in it** (more than one person, or any connected app,
|
|
39
|
+
bot, meeting or knowledge). This skill is the whole middle of their setup.
|
|
40
|
+
- **A company that is empty** (they were invited, but nothing has been set up
|
|
41
|
+
yet). Treat it as a founder's setup that happens to have a company already:
|
|
42
|
+
do not create one, and follow `skills/your-business.md` as written.
|
|
43
|
+
- **No company.** This skill does not apply. Go back to
|
|
44
|
+
`skills/first-company.md`.
|
|
45
|
+
|
|
46
|
+
If the owner-context check failed, say you could not check right now. Never
|
|
47
|
+
treat an unreadable check as "you are alone".
|
|
48
|
+
|
|
49
|
+
## 2. Give them the tour, grounded in what is actually there
|
|
50
|
+
|
|
51
|
+
One short message. Real names and counts from the reads above, never a
|
|
52
|
+
description of HQ as a product:
|
|
53
|
+
|
|
54
|
+
> You're in **Northwind** with Sara, Ali and two others. The team has Slack,
|
|
55
|
+
> Fireflies and Linear connected, 40 meetings recorded, and two bots already
|
|
56
|
+
> running: one that writes the weekly update, one that watches support.
|
|
57
|
+
|
|
58
|
+
Then prove it, in the same breath, with one real answer only their company's
|
|
59
|
+
HQ could give. Pull it yourself and show the answer, not the method:
|
|
60
|
+
|
|
61
|
+
> From last week: the team decided to push the pricing change to November and
|
|
62
|
+
> to keep the legacy plan for existing customers.
|
|
63
|
+
|
|
64
|
+
That single line is what makes the product land. A person who reads it
|
|
65
|
+
understands the shared context layer without being told about it.
|
|
66
|
+
|
|
67
|
+
Then say what it means for them, in their words: everything the team has
|
|
68
|
+
connected is already theirs, every bot they talk to starts from it, and
|
|
69
|
+
anything they add lands for the whole team the same way.
|
|
70
|
+
|
|
71
|
+
Never invent any of this. If a category is empty, say so plainly and make it
|
|
72
|
+
the first thing you offer to fix.
|
|
73
|
+
|
|
74
|
+
## 3. Ask about them, not about the business
|
|
75
|
+
|
|
76
|
+
You already know the business. Confirm it in half a sentence rather than
|
|
77
|
+
asking. What you do not know is where they fit, so ask that, one question, in
|
|
78
|
+
plain words:
|
|
79
|
+
|
|
80
|
+
> What do you do at Northwind, day to day?
|
|
81
|
+
|
|
82
|
+
Their answer decides everything you offer next. Write it into their profile
|
|
83
|
+
the way step 5 of the walkthrough describes, so every other bot knows it too.
|
|
84
|
+
|
|
85
|
+
If they seem more interested in understanding HQ than in configuring it, let
|
|
86
|
+
that be the session: walk them through what is in their HQ, answer questions,
|
|
87
|
+
and offer the additions at the end. Familiarity is a legitimate outcome of
|
|
88
|
+
setup for a joiner.
|
|
89
|
+
|
|
90
|
+
## 4. Offer what is missing for them, not for the company
|
|
91
|
+
|
|
92
|
+
Check what exists before offering anything, and say plainly what they already
|
|
93
|
+
have rather than offering it again:
|
|
94
|
+
|
|
95
|
+
> Fireflies is already connected, so your meetings are in here from today.
|
|
96
|
+
|
|
97
|
+
Then offer only the gaps, three at most, each with a reason tied to what they
|
|
98
|
+
just told you:
|
|
99
|
+
|
|
100
|
+
- **Their own tools on this Mac**: the coding tool they use, signed in.
|
|
101
|
+
- **Apps the company has not connected**, or that are personal to them: their
|
|
102
|
+
own calendar and inbox, the board they personally live in.
|
|
103
|
+
- **A home for their own work**: their projects or their clients, alongside
|
|
104
|
+
the company's.
|
|
105
|
+
- **Their first bot**, aimed at their job rather than the company's: what they
|
|
106
|
+
do every morning that a bot could do first.
|
|
107
|
+
|
|
108
|
+
## 5. Things only an owner can do
|
|
109
|
+
|
|
110
|
+
Inviting people, company-wide credentials and some company files may not be
|
|
111
|
+
theirs to change. When they ask for one, do not attempt it and fail. Say who
|
|
112
|
+
can do it, by name, from the members list, and offer to send that person the
|
|
113
|
+
request from them:
|
|
114
|
+
|
|
115
|
+
> Sara owns Northwind, so the invite has to come from her. Want me to message
|
|
116
|
+
> her and ask?
|
|
117
|
+
|
|
118
|
+
If a read is refused, say so in one line, name the person who can grant it,
|
|
119
|
+
and move on. Never retry, and never guess at what the file said.
|
|
120
|
+
|
|
121
|
+
## 6. Finish
|
|
122
|
+
|
|
123
|
+
Close the way the walkthrough closes, with their version of it: what they
|
|
124
|
+
inherited, what you added today, and the one thing worth trying tomorrow. If
|
|
125
|
+
they have a bot now, hand them over to it.
|