Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
1538 commits
Select commit Hold shift + click to select a range
1ab033c
test(gateway): skip real-UNIX-socket witness cases on native Windows
liuhao1024 Aug 29, 2026
15e74fa
fix(desktop): guard the whole build-critical dep set, before clean
jackulau Aug 16, 2026
ae04185
chore: export BUILD_CRITICAL_PACKAGES for the test, drop dead default…
kshitijk4poor Sep 1, 2026
fdb2e10
fix(desktop): refuse the build when ANY declared non-optional dep is …
teknium1 Sep 2, 2026
6879a62
fix(gateway): live foreign token lock at startup exits 78 instead of …
teknium1 Sep 2, 2026
ee2147f
fix: hard stop tool loops on non-interactive platforms
plcunha Jun 19, 2026
384fc4b
fix(guardrails): preserve interactive platform defaults
plcunha Aug 28, 2026
cd2d308
fix(agent): guard repeated skill reads
benbenlijie Jun 16, 2026
76648a7
fix(guardrails): identical-call streaks hard-stop any tool on unatten…
teknium1 Sep 2, 2026
25d954c
fix(guardrails): hard stops catch replays, never legitimate iteration
teknium1 Sep 2, 2026
5f43a3f
fix(gateway): rescue orphaned FIFO overflow when session goes idle (#…
salch-cred Sep 1, 2026
625bcbd
refactor(gateway): drop constant conditional in rescue helper
salch-cred Sep 1, 2026
98eb6eb
fix(gateway): rescued FIFO orphan runs exactly once, chain stays in o…
teknium1 Sep 2, 2026
fbabfa7
fix(gateway): flush the FIFO overflow tail to disk at shutdown too (#…
teknium1 Sep 2, 2026
7f53ad1
fix(desktop): route approval responses through the runtime event's ex…
liuhao1024 Aug 28, 2026
55d8c05
test(desktop): pin sole-local registry approval routing through the e…
teknium1 Sep 2, 2026
8068786
fix(update): stop crediting unmanaged serve runtimes with a gateway's…
chelsealong Sep 1, 2026
5733d55
fix(update): warn surviving pre-update serve and dashboard runtimes o…
twotnguyen Sep 1, 2026
f9bca5a
fix(update): reconcile serve/dashboard runtimes in their own vocabula…
teknium1 Sep 2, 2026
2b7132c
chore: map contributor email for salvaged #100493
teknium1 Sep 2, 2026
bfbb34b
fix(update): Windows progress server hands out its URL only once it i…
teknium1 Sep 2, 2026
8fd76fd
fix(cron): surface delivery_failed instead of last_status ok
jwilson411 Sep 1, 2026
94e49b8
fix(cron): stop manual-run notice from asserting delivery that never …
strzhao Aug 15, 2026
fd387c1
fix(cron): treat falsy deliver as local in manual-run notice
strzhao Aug 16, 2026
2f58cbf
fix(cron): adapt delivery-notice tests to the return_job claim API
strzhao Aug 16, 2026
758114b
fix(cron): manual run reports delivery_failed as a failed run; docs f…
teknium1 Sep 2, 2026
df4b373
fix(cron): every last_status consumer renders delivery_failed explici…
teknium1 Sep 2, 2026
fb76fb0
fix(agent): thinking-only length truncations no longer wedge continua…
AlexGabbia Aug 31, 2026
2a0605a
fix(agent): reasoning-off continuation reaches the wire on the legacy…
teknium1 Sep 2, 2026
c83ea9b
test(agent): pin the reasoning-off continuation to exactly one reques…
teknium1 Sep 2, 2026
dd72b42
fix(cron): require positive evidence for live-adapter delivery confir…
kaiomp Sep 1, 2026
d3b4217
fix(gateway): exempt cron artifacts from the silence-narration drop
kaiomp Sep 1, 2026
4b69ba2
fix(cron): mark live deliveries as final notifications
tianma-if Jul 4, 2026
3294eed
test(cron): pin notify=True on live cron text and media routes
teknium1 Sep 2, 2026
00a7115
fix(cron): make cron push-notify configurable (cron.delivery.notify) …
teknium1 Sep 2, 2026
3038493
fix(auth): never fork single-use OAuth grants across profiles (#100339)
teknium1 Sep 2, 2026
37f3ba1
fix(auth): auto-heal single-use OAuth grants already forked across pr…
teknium1 Sep 2, 2026
619ca30
fix(agent): isolate background review snapshots
notkisk Sep 2, 2026
26f0de2
fix(agent): clone the /refine snapshot too, not just the automatic re…
kshitijk4poor Sep 2, 2026
2adb1a4
refactor(agent): clone the review snapshot once at the spawn chokepoint
kshitijk4poor Sep 2, 2026
a260074
feat(delegate): tag every subagent progress line with its batch id
teknium1 Sep 2, 2026
2f44998
fix(dashboard-auth): a non-JWT bearer is "not my token", not "provide…
teknium1 Sep 2, 2026
0aa84bb
fix(state): reap stale state-owned sessions safely
stepanov1975 Aug 28, 2026
9bc249c
fix(state): report closed stale-open count from auto-maintenance, doc…
teknium1 Sep 2, 2026
aa80626
fix(tui-gateway): adopt late compute-host compress acks instead of a …
teknium1 Sep 2, 2026
6840bb0
fmt(js): `npm run fix` on merge (#101102)
hermes-seaeye[bot] Sep 2, 2026
867e415
fix(gateway): honor explicit platforms.<x>.enabled: false over env cr…
teknium1 Sep 2, 2026
7ff8aae
gateway: warn once when an explicit platforms.<x>.enabled: false over…
teknium1 Sep 2, 2026
fbd40c9
fmt(js): `npm run fix` on merge (#101107)
hermes-seaeye[bot] Sep 2, 2026
fb50239
perf(desktop): group chat rooms answer in the time of one bot, not th…
teknium1 Sep 2, 2026
d96b180
chore: map contact@danteschrauwen.be -> deinte (PR #101090 salvage)
kshitijk4poor Sep 2, 2026
1872518
fix(cron): don't silently skip a due run after a timezone-offset migr…
deinte Sep 2, 2026
bcb412c
refactor(cron): share the fire-path telemetry recorder
kshitijk4poor Sep 2, 2026
5d4aa4f
fix(desktop): group chat rooms are serial again; keep only the push-w…
teknium1 Sep 2, 2026
3e63367
feat(desktop): status bar can show live cache-hit rate and tokens/sec…
teknium1 Sep 2, 2026
254158f
fmt(js): `npm run fix` on merge (#101150)
hermes-seaeye[bot] Sep 2, 2026
6e7c7c7
fix(desktop): a bot row click always lands on the Bot Chat the row pr…
teknium1 Sep 2, 2026
32fe129
perf(bot-mode): cold DM hops skip the live /models probe; relay repli…
teknium1 Sep 2, 2026
61635e1
fix(state): single-flight shared database opens
fangliquanflq Sep 2, 2026
6f1733c
test(state): reset the single-flight _opening map in the registry fix…
kshitijk4poor Sep 2, 2026
f40333a
fix(agent): preserve busy steer during compression and avoid replayin…
Finn763 Sep 1, 2026
bc71b8b
fix(compression): anchor on the LAST intent row — newer user turn out…
teknium1 Sep 2, 2026
45b0d8c
feat(gateway): one gateway.trust_env key controls aiohttp proxy-env h…
teknium1 Sep 2, 2026
238b6c1
fix(compression): persist the anti-thrash recovery deadline so gatewa…
teknium1 Sep 2, 2026
fd05029
fix(state): fail fast on non-contention flock errors and retry deferr…
teknium1 Sep 2, 2026
c513861
test(state): cover deferred FTS retry, leftover lock files, and WAL i…
HexLab98 Sep 1, 2026
dbb6acd
test(state): non-contention errno table, repair-lock sibling, in-proc…
teknium1 Sep 2, 2026
d8616f1
chore: map contributor email for leocamilo@me.com
leomcamilo Sep 2, 2026
bcc2e65
fix(state): quarantine SessionDB handle after structural corruption
leomcamilo Sep 2, 2026
e916062
fix(state): also disable SQLite's internal close-time checkpoint on q…
kshitijk4poor Sep 2, 2026
3a980a4
fix(desktop): keep drafts editable while connecting
ayushnangia Aug 31, 2026
d3e2ace
fix(profiles): profile delete refuses to kill another profile's gatew…
teknium1 Aug 31, 2026
1bd9fce
fix(kanban): judge unachievable goals as blocked, never done
itsflownium Sep 2, 2026
ae63db2
chore: map contributor email
itsflownium Sep 2, 2026
5c6cbbc
fix(loops): pause /loop --until on a blocked verdict; trim redundant …
teknium1 Sep 2, 2026
97baa38
test(kanban): pin that stale blocked-task notify subs are purged
itsflownium Sep 2, 2026
a81e503
fix(kanban): reap notify subscriptions for stale blocked tasks too
teknium1 Sep 2, 2026
805498e
fix(providers): give alibaba-coding-plan-cn its own API key env var
Edizzier Sep 2, 2026
44a5792
fix(providers): hide phantom -cn picker rows lit only by shared intl …
teknium1 Sep 2, 2026
ab1f81c
chore(contributors): map umit.ediz@hotmail.com -> Edizzier
teknium1 Sep 2, 2026
92a9864
feat(email): configurable IMAP/SMTP transport security (tls/starttls/…
alessandrolamberti Sep 2, 2026
4d02c78
refactor(email): single _normalize_security helper, loopback-scoped v…
teknium1 Sep 2, 2026
6ff9426
fix(anthropic): track the current fast-mode model matrix (Opus 4.8 / …
aldoeliacim Aug 9, 2026
2e25d17
chore(contributors): map ifastcc email (PR #34308 co-author)
teknium1 Sep 2, 2026
c7e2e0b
feat(fast): bounded /fast auto|cold windows behind one route-aware gate
teknium1 Sep 2, 2026
d1efa0d
fix(compression): provider-proven overflow gets one real compaction a…
teknium1 Sep 2, 2026
aaa34b0
fix(desktop): model picker no longer hardcodes --global; one persist …
teknium1 Sep 2, 2026
8be47c1
fix(slack): treat allowlisted users' Web-API (user-token) posts as human
xoy8n Sep 2, 2026
d208538
fix(slack): route SessionSource/history is_bot through _event_declare…
teknium1 Sep 2, 2026
1cd736f
fix(terminal): scope terminal config per turn under profile multiplexing
muhifni Aug 31, 2026
ea9924b
fix(container): honor config.yaml multiplex_profiles at boot
1052326311 Aug 19, 2026
a78bb93
docs: terminal settings resolve per profile under multiplexing
teknium1 Sep 2, 2026
4a7f228
chore: map contributor email for muhifni (#99225 salvage)
teknium1 Sep 2, 2026
ef6d336
feat(cli,tui): add display.bell_on_clarify — terminal bell on clarify…
TurgutKural Aug 30, 2026
3082a34
feat(cli,tui): add display.bell_on_approval + fix eslint error
TurgutKural Aug 30, 2026
552159d
feat(cli,tui): collapse bell_on_clarify/approval into display.bell_on…
teknium1 Sep 2, 2026
782dd63
feat(tts): speech toggles warm/release plugin and command TTS providers
teknium1 Sep 2, 2026
51953a3
fix(desktop): keep busy tile transcripts stable
Dolverin Aug 27, 2026
a532869
fix(desktop): bot tile transcripts read from their owner backend
teknium1 Sep 2, 2026
a0e4ce2
fix(desktop): open cron-run transcripts stay live
teknium1 Sep 2, 2026
6d061ed
fix(desktop): open transcript catches up on every reconnect
teknium1 Sep 2, 2026
87d5e40
fix(desktop): fail closed when Bot Chat lookup returns zero rows
chelsealong Aug 30, 2026
2599793
fix(bot-mode): hand off group tabs to remote bots
helix4u Sep 2, 2026
202997b
fix(desktop): one conversation never opens as two tabs after compaction
praxis1244-consulting Aug 31, 2026
9b84a98
test: trim salvaged #99763 to the two invariant-pinning tests
teknium1 Sep 2, 2026
3292fbc
chore: map praxis1244-consulting contributor email
teknium1 Sep 2, 2026
d417aee
fix(desktop): sync pins across all session slices
fangliquanflq Aug 23, 2026
7b951e4
fix(desktop): route a shared-id unpin to the row the pull adopted
teknium1 Sep 2, 2026
209de12
fix(desktop): Bot Mode tabs caption a Bot Chat with the bot's name, n…
teknium1 Sep 2, 2026
fb9a294
fix(sessions): protect canonical Bot Chat from auto-title
fangliquanflq Aug 31, 2026
89e2e4f
docs(sessions): explain why the canonical Bot Chat guard is provenanc…
teknium1 Sep 2, 2026
1bf2cf5
fix(desktop): project tree follows sessions.changed so external sessi…
teknium1 Sep 2, 2026
54b2c0e
fix(tui_gateway): scope live-session reuse to the requesting profile
teknium1 Sep 2, 2026
000d6ef
test: widen _find_live_session_by_key monkeypatch for the optional pr…
teknium1 Sep 2, 2026
ad800ea
fix(desktop): cold resume paints the prefetched REST transcript befor…
teknium1 Sep 2, 2026
8d6a286
fix(desktop): restored background tabs resolve their session title wi…
teknium1 Sep 2, 2026
c65c79a
fix(bot-mode): group chat picker rows overflow and scroll names out o…
johnsonAyo Aug 20, 2026
d1f8c2e
test(desktop): group chat picker row label opts out of min-width:auto…
teknium1 Sep 2, 2026
1592e48
fix(desktop): a split-dragged Bot tab keeps its Bot workspace scope
Sep 2, 2026
7f7df1c
fix(state): refuse SessionDB open and writes on a deleted WAL generation
cursoragent Sep 2, 2026
e9fa7bc
fix(state): keep the #94736 teardown self-heal alive under the delete…
kshitijk4poor Sep 2, 2026
55e1698
fix(gateway): a secondary profile handoff fails closed when its confi…
Adolanium Aug 29, 2026
f069ffd
fix(gateway): offload handoff secret scope loading
fangliquanflq Sep 1, 2026
17f86ab
fix(gateway): enter per-message profile scope off the event loop too
teknium1 Sep 2, 2026
0437fe6
fix(discord): native slash commands honor guild/channel profile_routes
teknium1 Sep 2, 2026
7aff724
feat(desktop): add display.resume_last_session config toggle (#60812)
jinglun010-cpu Sep 2, 2026
648c664
feat(desktop): gate cold-start restore on display.resume_last_session
teknium1 Sep 2, 2026
351e4c0
fix(state): namespace telegram topic tables by profile_name
crdesign8 Aug 2, 2026
62be704
fix(gateway): pass routed source.profile into telegram topic state
crdesign8 Aug 2, 2026
d55d9d1
fix(gateway): route profile into topic prune, cooldowns, and docs
crdesign8 Aug 2, 2026
458e2ef
refactor(state): collapse telegram topic v3 migration into one table-…
teknium1 Sep 2, 2026
bb7838c
chore: map contributor crdesign8@hotmail.com -> @crdesign8
teknium1 Sep 2, 2026
3d0ac69
feat(desktop): user-made sections in the bot roster, with drag-and-dr…
Fortunate787 Sep 1, 2026
bd9955d
fix(desktop): section rename — Escape cancels, Enter commits once
Fortunate787 Sep 1, 2026
e9dd0bf
feat(desktop): polish bot roster sections — dialog rename, Undo delet…
teknium1 Sep 2, 2026
5180601
perf(cli): dispatch serve without the full parser tree
helix4u Aug 28, 2026
4afbecb
test(cli): trim fast-serve coverage to the parity + dispatch invariants
teknium1 Sep 2, 2026
4346721
fix(telegram): resolve button-caller authorization via the injected a…
Jul 16, 2026
74775df
fix(gateway): route-stamp primary callback auth and carry is_bot thro…
teknium1 Sep 2, 2026
bbb087f
fix(gateway): egress adapter and channel directory no longer follow t…
teknium1 Sep 2, 2026
11f932c
fix(slack): interactive-caller and pre-fetch auth prefer the injected…
teknium1 Sep 2, 2026
c2954c8
feat(model-catalog): picker catalogs refresh every 20 minutes, gatewa…
teknium1 Sep 2, 2026
632078b
feat(cli): OSC 9 + Warp OSC 777 notifications ride on the bell flags
teknium1 Sep 2, 2026
70dc160
test(cli): pin OSC 9 / Warp OSC 777 bell emitters; docs + contributor…
teknium1 Sep 2, 2026
21cebbf
fix(doctor): honor disabled built-in memory stores
fangliquanflq Sep 2, 2026
af86ad0
fix(doctor): reuse resolved memory config at Memory Provider section
teknium1 Sep 2, 2026
7a86397
fix(api_server): fail closed on unstamped runs; claim session-chat-st…
teknium1 Sep 2, 2026
8076c78
fix(desktop): scope handoff config to session profile
aeonsong Sep 1, 2026
16370ae
fix(tui_gateway): setup.status / setup.runtime_check answer for the r…
teknium1 Sep 2, 2026
d29a793
fix(bot-mode): DMs to a Desktop-owned Bot Chat land in the live sessi…
teknium1 Sep 2, 2026
0058bde
fix(bot-relay): a DM into a live Bot Chat queues as the next turn, ne…
teknium1 Sep 2, 2026
1aa62ce
fix(security): isolate multiplex dotenv reloads
lesterlxt Aug 3, 2026
0a6aa7c
fix(env_loader): log routed-scope dotenv skip once per home; port sin…
teknium1 Sep 2, 2026
1eb7175
toolchain-self-improve: route API_SERVER_KEY to profile env
patrykkopycinski Sep 1, 2026
d7dc75c
fix(gateway): multiplex must not apply default-profile creds to uncon…
webtecnica Aug 11, 2026
b53c50c
fix(config): resolve ${VAR} config refs through the profile secret sc…
teknium1 Sep 2, 2026
2475335
fix(config): keep .env publishes inside the routed profile scope unde…
teknium1 Sep 2, 2026
011a60b
docs(design): add the multiplexing-gateway design doc referenced by s…
100yenadmin Aug 19, 2026
b6f0106
docs(design): note loader-boundary dotenv guard, scoped ${VAR} expans…
teknium1 Sep 2, 2026
638c1f3
chore(contributors): map patryk.kopycinski@elastic.co -> patrykkopyci…
teknium1 Sep 2, 2026
0fd9218
docs: ${VAR} config refs resolve per-profile under a multiplexed gateway
teknium1 Sep 2, 2026
4155ea9
perf(serve): Desktop backend announces its socket before MCP discover…
teknium1 Sep 2, 2026
9da8842
fix(cron): resolve profile store paths per call
wanliqin Aug 28, 2026
e48bb82
test(cron): preserve explicit suggestions path override
honor2030 Aug 28, 2026
a2fea79
fix(cron): isolate multiplex profile failures per profile (#74878)
Cyber-Yichen Sep 2, 2026
357062f
fix(dashboard): multiplex cron fire URL uses the default profile's li…
bergusdz Sep 2, 2026
62a4599
fix(cron): keep profile scope on the standalone fallback pool; deskto…
teknium1 Sep 2, 2026
a6351a7
fix(cron): route a credentialless satellite's cron delivery through t…
teknium1 Sep 2, 2026
eed481b
docs(profiles): cron delivery for routed profiles rides the shared bo…
teknium1 Sep 2, 2026
fbd9730
fix(gateway): run /insights, /debug and /goal draft inside the routed…
Drexuxux Aug 4, 2026
257da5c
fix(gateway): route /review and /reload-skills executor hops through …
teknium1 Sep 2, 2026
94a2d7f
fix(gateway): persist slash-command config writes into the routed pro…
StanleyStetson Sep 2, 2026
d45bc39
fix(gateway): resolve the ephemeral personality prompt per turn from …
teknium1 Sep 2, 2026
527da60
fix(cli): report a named profile as running when the default multiple…
teknium1 Sep 2, 2026
97b8a97
fix(feishu): include app credentials in multiplex fingerprint (#76793)
webtecnica Aug 2, 2026
5b4cff9
fix(gateway): fingerprint Teams client_id and WeCom bot_id for the mu…
teknium1 Sep 2, 2026
9f40d3b
fix(feishu): resolve DM admission config per-profile under multiplex …
pittosporum-seu Sep 2, 2026
14f20d1
fix(feishu): isolate lark_oapi WS globals per profile and supervise t…
pittosporum-seu Sep 2, 2026
b1bc9bb
fix(google-chat): scope multiplex profile config and fail ADC closed
zyz619963502zyz Sep 2, 2026
db639e1
fix(gateway): bind every adapter to the runner at the _create_adapter…
heyhudson Sep 2, 2026
dca9a54
fix(gateway): match WhatsApp profile_routes across JID/LID/number forms
vKongv Sep 2, 2026
3245264
fix(relay): carry routed profile through the passthrough-plane forward
pierrenode Sep 2, 2026
3fcfa64
docs(google-chat): document per-profile scoping and ADC fail-closed u…
teknium1 Sep 2, 2026
ae81786
fix(desktop): let a per-profile remote override win over the forced-l…
SZWzz Aug 28, 2026
ff8c1ac
test(desktop): cover combined remote route precedence
SZWzz Aug 28, 2026
2ce6f5c
fix(desktop): refresh routed-profile Bot Chat transcripts (salvage #9…
teknium1 Sep 2, 2026
74b00d7
fix(dashboard): route every per-row session request at the row's owni…
liuhao1024 Sep 2, 2026
dfa74b5
fix(desktop): boot session pop-out/watch windows against the session'…
teknium1 Sep 2, 2026
9189e42
fix(desktop): reconnect an active profile whose gateway is closed
ayushnangia Aug 28, 2026
d9b051a
fix(desktop): pin the project '+' new chat to the profile its tree is…
teknium1 Sep 2, 2026
504dd1f
fix(raft): scope RAFT_PROFILE resolution to the active multiplex profile
nftpoetrist Sep 2, 2026
79732c6
fix(a2a): scope multiplex secondary-profile construction, not shared env
nftpoetrist Sep 2, 2026
39fca69
fix(tools): log boot-time UnscopedSecretError probes at debug, not wa…
liuhao1024 Sep 1, 2026
7d50965
fix(tts): resolve default output dir from the active profile
liuhao1024 Aug 30, 2026
dd666d2
fix(gateway): honor explicit webhook disable in _apply_env_overrides
webtecnica Aug 14, 2026
64bbbaa
fix(gateway): honor explicit msgraph_webhook disable under env override
teknium1 Sep 2, 2026
8167cfa
fix(a2a): scope multiplexed peer authorization
fangliquanflq Aug 7, 2026
04c640a
fix(gateway): honor secondary adapters under profile runtime scope
fangliquanflq Aug 7, 2026
87ad7aa
fix(gateway): route multiplexed profile logs to their own logs/ dir
teknium1 Sep 2, 2026
1398c0f
fix(update): stage-and-swap the Desktop rebuild so a failed pack neve…
teknium1 Sep 2, 2026
8ecf19b
chore: map contributor deathxdefeat@users.noreply.github.com -> @deat…
teknium1 Sep 2, 2026
b1193b2
test(desktop): corrupt-exe integrity test follows stage-and-swap — co…
teknium1 Sep 2, 2026
0483688
fix(gateway): run secondary-profile adapter auth setup off the event …
GoBeromsu Aug 31, 2026
df50b52
fix(gateway): coerce profile route IDs to str for YAML ints
fangliquanflq Jul 24, 2026
956f493
fix(plugins): route platform_actions through profile-aware adapter re…
pierrenode Aug 13, 2026
e8231f0
fix(gateway): hydrate secondary-profile secrets off-loop at startup t…
teknium1 Sep 2, 2026
ca42d7a
fix(gateway): isolate /voice state and voice-channel input per multip…
teknium1 Sep 2, 2026
bedebf5
fix(gateway): only coerce int route ids; warn when a float/bool id ca…
teknium1 Sep 2, 2026
bb5a1b7
fix(plugins): platform_actions fails closed when the active profile c…
teknium1 Sep 2, 2026
7463cd1
fix(session): fence multiplex peer-fallback recovery and profile inhe…
teknium1 Sep 2, 2026
ad8b9e0
chore(contributors): map gobeumsu@gmail.com -> GoBeromsu
teknium1 Sep 2, 2026
29640e3
fix(gateway): register secondary profiles' shell hooks and outbound w…
chelsealong Aug 23, 2026
600b9c7
fix(gateway): scope force-reload hook re-registration to its own home
chelsealong Aug 23, 2026
98c27aa
feat(webhooks): stamp the emitting profile on outbound webhook payloads
teknium1 Sep 2, 2026
4e7aa48
fix(browser): reap idle multiplexed sessions under their owner profil…
teknium1 Sep 2, 2026
cd7811a
fix(memory/hindsight): propagate profile scope into background thread…
teknium1 Sep 2, 2026
dc7e1b7
fix(webhook): load URL-resolved profile's skills under multiplex
teknium1 Sep 2, 2026
ee0e234
fix(gateway): discover and reload MCP servers per profile under multi…
teknium1 Sep 2, 2026
bd81bf0
chore(contributors): map tky.juani@gmail.com -> JuaniLezcano
teknium1 Sep 2, 2026
05aa749
fix(irc): scope server/port/nickname/channel/use_tls reads to the act…
nftpoetrist Sep 1, 2026
327e904
fix(ntfy): scope server/topic/publish_topic reads to the active profi…
nftpoetrist Sep 1, 2026
c36def6
fix(photon): scope project_id/node_bin/require_mention/reactions/side…
nftpoetrist Sep 1, 2026
56d869d
fix(mattermost): scope url/reply_mode/require_mention/free_response_c…
nftpoetrist Sep 1, 2026
07ee457
fix(wecom): scope WECOM_BOT_ID reads to the active profile under mult…
nftpoetrist Sep 1, 2026
2bcbdb6
fix(simplex): scope SIMPLEX_* reads to the active profile under multi…
teknium1 Sep 2, 2026
9be1168
fix(wecom): scope WECOM_WEBSOCKET_URL like its neighbours
teknium1 Sep 2, 2026
001b8ab
fix(matrix): pin the E2EE crypto store per profile at connect(), not …
teknium1 Sep 2, 2026
9d5c58b
fix(gateway): guard Teams multiplex listener ownership
JoelMTaylor Aug 7, 2026
4fa1d54
docs(multiplex): list teams among port-binding platforms
teknium1 Sep 2, 2026
febd2af
fix(gateway): skip credential-less WhatsApp on secondary multiplex pr…
teknium1 Sep 2, 2026
2e25b47
chore: map contributor email for #80825 salvage
teknium1 Sep 2, 2026
65b0f00
fix(agent): stop the between-turns tool refresh from forking the cach…
JoaoMarcos44 Sep 1, 2026
8e4366d
fix(tools): freeze tools[] across agent-cache eviction; make /reload-…
teknium1 Sep 2, 2026
73f6836
fix(sessions): auto-prune state.db by default (90d) and gate VACUUM o…
teknium1 Sep 2, 2026
c9491e6
feat(cron): per-job failure_deliver — route or suppress failure notic…
victor-kyriazakos Sep 1, 2026
fd35e1e
fix(cron): delivery bookkeeping reads the failure lane it actually ro…
victor-kyriazakos Sep 1, 2026
95f62ca
fix(cron): validate failure_deliver at preflight and dashboard update…
kshitijk4poor Sep 2, 2026
af52474
fix(gateway): quiesce the thread pool before closing state.db at shut…
JoaoMarcos44 Sep 2, 2026
11942f6
fix(gateway): fail closed when a shutdown worker survives the quiesce…
JoaoMarcos44 Sep 2, 2026
1e8f829
fix(model): show copilot-acp in pickers when its executable resolves
Solitud1nem Jul 13, 2026
6b00567
test(model): clear COPILOT_ACP_BASE_URL in the copilot-acp fixture
Solitud1nem Jul 16, 2026
fd439ac
fix(auth): dispatch external-process providers by auth_type, add posi…
unsupportedpastels Sep 1, 2026
323168a
fix(dashboard): correct copilot-acp sign-in command, honest status card
unsupportedpastels Sep 1, 2026
15f003e
test(auth): cover external-process dispatch, auth evidence, sign-in c…
unsupportedpastels Sep 1, 2026
6b2d32d
fix(picker): keep signed-in copilot-acp visible in explicit-only desk…
unsupportedpastels Sep 1, 2026
5487222
fix(models): live Copilot catalog for CLI-login users; unbreak picker…
unsupportedpastels Sep 1, 2026
426dab7
fix(copilot-acp): apply the picker-selected model via session/set_model
unsupportedpastels Sep 1, 2026
a94b68a
fix(copilot-acp): stop substituted models impersonating the requested…
unsupportedpastels Sep 1, 2026
afc3d9d
fix(copilot-acp): prefer stable session config for model selection
unsupportedpastels Sep 1, 2026
61bbcca
test(morning-report): cover LINE push success/failure paths
bottlerex Sep 3, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
6 changes: 3 additions & 3 deletions .dockerignore
Original file line number Diff line number Diff line change
Expand Up @@ -107,9 +107,9 @@ plans/
.hadolint.yaml
.mailmap

# Repo-root debug/export artifacts — must never reach image layers (COPY . .)
# Debug/export artifacts — must never reach image layers (COPY . .)
/log.txt
/sqlite_leak_fix.png
/*.png.bak
/default.tar.gz
/*.tar.gz
*.tar.gz
*.tgz
41 changes: 36 additions & 5 deletions .env.example
Original file line number Diff line number Diff line change
Expand Up @@ -153,6 +153,35 @@
# Optional base URL override:
# UPSTAGE_BASE_URL=https://api.upstage.ai/v1

# =============================================================================
# LLM PROVIDER (Ramp Router)
# =============================================================================
# Ramp Router (router.com) — Responses-native LLM gateway; model IDs come
# from your account's live catalog (GET /v1/models).
# Get your key at: https://app.router.com/keys
# RAMP_ROUTER_API_KEY=your_key_here
# Optional base URL override:
# RAMP_ROUTER_BASE_URL=https://api.router.com/v1

# =============================================================================
# LLM PROVIDER (Nebius Token Factory)
# =============================================================================
# Nebius Token Factory — OpenAI-compatible inference for open models.
# Get your key at: https://tokenfactory.nebius.com/
# NEBIUS_API_KEY=your_key_here
# Optional base URL override:
# NEBIUS_BASE_URL=https://api.tokenfactory.nebius.com/v1

# =============================================================================
# LLM PROVIDER (Tencent Hy — TokenHub & TokenPlan)
# =============================================================================
# Tencent TokenHub (OpenAI-compatible): https://tokenhub.tencentmaas.com
# TOKENHUB_API_KEY=your_key_here
# TOKENHUB_BASE_URL=https://tokenhub.tencentmaas.com/v1
# Tencent TokenPlan (Anthropic Messages endpoint via LKEAP):
# TOKENPLAN_API_KEY=your_key_here
# TOKENPLAN_BASE_URL=https://api.lkeap.cloud.tencent.com/plan/anthropic

# =============================================================================
# TOOL API KEYS
# =============================================================================
Expand Down Expand Up @@ -293,12 +322,14 @@ BROWSERBASE_PROXIES=true
# Uses custom Chromium build to avoid bot detection altogether
BROWSERBASE_ADVANCED_STEALTH=false

# Browser engine for local mode (default: auto = Chrome)
# "auto" — use Chrome (don't pass --engine flag)
# "lightpanda" — use Lightpanda (1.3-5.8x faster navigation, no screenshots)
# Local browser engine (default: auto = Chrome)
# "auto" — use Chrome
# "lightpanda" — use Lightpanda (faster navigation, no screenshots)
# "chrome" — explicitly request Chrome
# Requires agent-browser v0.25.3+. Lightpanda commands that fail or return
# empty results are automatically retried with Chrome.
# Browser Use mode (default) spawns `lightpanda serve` itself; the built-in
# browser tools pass --engine to agent-browser v0.25.3+ and retry failed or
# empty Lightpanda results with Chrome. Ignored while a cloud provider,
# Camofox or browser.cdp_url is active (`hermes doctor` reports that).
# Also configurable via browser.engine in config.yaml.
# AGENT_BROWSER_ENGINE=auto

Expand Down
3 changes: 3 additions & 0 deletions .github/actions/detect-changes/action.yml
Original file line number Diff line number Diff line change
Expand Up @@ -48,6 +48,9 @@ outputs:
installer:
description: Run the PowerShell installer tests on a Windows runner.
value: ${{ steps.classify.outputs.installer }}
desktop_updater:
description: Run the Windows desktop-update hand-off (windows.ps1) integration tests.
value: ${{ steps.classify.outputs.desktop_updater }}
rust:
description: Run `cargo test` for the Tauri bootstrap installer.
value: ${{ steps.classify.outputs.rust }}
Expand Down
33 changes: 33 additions & 0 deletions .github/workflows/case-collision-check.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
name: Case Collision Check

# Rejects PRs that track two files whose paths differ only by case
# (README.md vs readme.md, src/Foo.py vs SRC/foo.py).
#
# Linux is case-sensitive; Windows and macOS (default) are not. A
# case-colliding pair lives fine in a Linux checkout and silently breaks
# every clone on a case-insensitive host — the filesystem can hold only
# one of them, so checkout fails or whichever wins overwrites the other.
# Git won't prevent the pair from landing (it only warns at checkout time,
# on a case-insensitive FS, for the client doing the checkout), so the only
# enforcement point is CI, on Linux, against the index.
#
# Runs unconditionally (no change-classifier gate): a collision can ship in
# any kind of PR — docs, JS, config, not just Python — so gating on a
# language lane would be the same "passive rule that cannot enforce a
# policy" trap the infographic check exists to close.

on:
workflow_call:

permissions:
contents: read

jobs:
check-case-collisions:
runs-on: ubuntu-latest
timeout-minutes: 5
steps:
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2

- name: Run case-collision checker
run: python3 scripts/check-case-collisions.py
34 changes: 26 additions & 8 deletions .github/workflows/ci.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@ jobs:
uv_lock: ${{ steps.classify.outputs.uv_lock }}
npm_lock: ${{ steps.classify.outputs.npm_lock }}
installer: ${{ steps.classify.outputs.installer }}
desktop_updater: ${{ steps.classify.outputs.desktop_updater }}
rust: ${{ steps.classify.outputs.rust }}
docker_meta: ${{ steps.classify.outputs.docker_meta }}
mcp_catalog: ${{ steps.classify.outputs.mcp_catalog }}
Expand Down Expand Up @@ -84,6 +85,11 @@ jobs:
needs: detect
if: needs.detect.outputs.python == 'true'
uses: ./.github/workflows/tests-os.yml
with:
# The Windows lane spawns the real desktop-update hand-off script
# (tests/test_desktop_update_windows_*.py) only when that surface
# changed; unit-level windows_only tests always run.
desktop_updater: ${{ needs.detect.outputs.desktop_updater == 'true' }}

lint:
name: Python lints
Expand Down Expand Up @@ -122,14 +128,14 @@ jobs:
# Tests-only PRs (~17% of commits) skip this 5-minute job — the longest
# single job in the workflow — while still running the full pytest lanes.
#
# ⛔ TEMPORARILY DISABLED (Aug 2, 2026, Teknium) — the suite is red on
# every PR and on main itself since the Aug 1 night engines/npm churn
# (#76499 → #76562 → #76575): the mock-backend Electron window never
# gets a title, so boot/chat/setup/interim specs all fail identically
# regardless of the PR's diff (verified on #76573 and the docs-only
# #76582). Tracking issue: #76627 (assigned: Ari). To re-enable,
# delete the `false &&` below — nothing else changed.
if: ${{ false && (needs.detect.outputs.python_prod == 'true' || needs.detect.outputs.frontend == 'true') }}
# Re-disabled (Sep 2026): the Sep 1 re-enable is still incredibly flaky.
# Keep this a bare `if: false`. The earlier
# `${{ false && (... || ...) }}` form on this reusable-workflow job made
# GitHub's workflow parser fail at startup ("An unexpected error has
# occurred") — every ci.yaml run repo-wide dispatched 0 jobs from
# 24f5a60ed1 until this line changed. To re-enable, restore:
# if: ${{ needs.detect.outputs.python_prod == 'true' || needs.detect.outputs.frontend == 'true' }}
if: false
uses: ./.github/workflows/e2e-desktop.yml

docs-site:
Expand Down Expand Up @@ -166,6 +172,16 @@ jobs:
needs: detect
uses: ./.github/workflows/infographic-check.yml

profile-artifact-check:
name: Profile artifact check
needs: detect
uses: ./.github/workflows/profile-artifact-check.yml

case-collision-check:
name: Check no case-colliding filenames
needs: detect
uses: ./.github/workflows/case-collision-check.yml

lockfile-diff:
name: package-lock.json diff
needs: detect
Expand Down Expand Up @@ -228,8 +244,10 @@ jobs:
- history-check
- contributor-check
- uv-lockfile
- case-collision-check
- lockfile-diff
- docker-lint
- profile-artifact-check
- supply-chain
- review-labels
- osv-scanner
Expand Down
6 changes: 6 additions & 0 deletions .github/workflows/docker.yml
Original file line number Diff line number Diff line change
Expand Up @@ -94,6 +94,9 @@ jobs:
- name: Checkout code
uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2

- name: Reject profile exports in the build context
run: python3 scripts/ci/check_profile_archive_boundary.py

# Retry once on transient Docker Hub / buildkit pull failures
# (connection reset, auth token timeout, rate limiting). The action
# generates a unique builder name per invocation so the retry doesn't
Expand Down Expand Up @@ -206,6 +209,9 @@ jobs:
- name: Checkout trusted source
uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2

- name: Reject profile exports in the build context
run: python3 scripts/ci/check_profile_archive_boundary.py

# Retry once on transient Docker Hub / buildkit pull failures.
# See build job for rationale; same pattern.
- name: Set up Docker Buildx
Expand Down
8 changes: 8 additions & 0 deletions .github/workflows/installer-tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -36,3 +36,11 @@ jobs:
- name: 8.3 short-path normalization (Windows PowerShell 5.1)
shell: powershell
run: powershell -NoProfile -ExecutionPolicy Bypass -File scripts/tests/test-install-ps1-longpath.ps1

- name: System Node and npm compatibility (pwsh 7)
shell: pwsh
run: pwsh -NoProfile -ExecutionPolicy Bypass -File scripts/tests/test-install-ps1-node-compatibility.ps1

- name: System Node and npm compatibility (Windows PowerShell 5.1)
shell: powershell
run: powershell -NoProfile -ExecutionPolicy Bypass -File scripts/tests/test-install-ps1-node-compatibility.ps1
21 changes: 21 additions & 0 deletions .github/workflows/profile-artifact-check.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
name: Profile Artifact Boundary

# A reusable, unconditional guard for the incident class in #92457. Ignore
# files reduce accidental staging; this job is the enforcement boundary that
# still catches `git add -f` and generated files present during a build.

on:
workflow_call:

permissions:
contents: read

jobs:
check-profile-artifacts:
name: Reject profile archives
runs-on: ubuntu-latest
timeout-minutes: 5
steps:
- uses: actions/checkout@de0fac2e4500dabe0009e67214ff5f5447ce83dd # v6.0.2
- name: Reject profile exports in the checkout
run: python3 scripts/ci/check_profile_archive_boundary.py
27 changes: 27 additions & 0 deletions .github/workflows/tests-os.yml
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,19 @@ name: OS-specific tests

on:
workflow_call:
inputs:
desktop_updater:
description: >-
Run the Windows desktop-update hand-off integration tests
(tests/test_desktop_update_windows_*.py). These spawn the real
scripts/desktop-update/windows.ps1 and poll its loopback server, so
they carry process-timing noise a shared runner amplifies; the
caller gates them on the classifier's desktop_updater lane so a PR
that never touched that surface cannot be failed by it. Push /
dispatch runs fail open (classifier sets every lane true).
type: boolean
required: false
default: true

permissions:
contents: read
Expand Down Expand Up @@ -134,9 +147,23 @@ jobs:
# would therefore abort the script on any non-zero exit and the
# exit-5 branch below would be unreachable dead code — the job
# would still fail red, but the diagnostic would never print.
# Desktop-update hand-off integration tests spawn the real
# windows.ps1; deselect them unless the PR touched that surface
# (see the workflow_call input). ``--ignore-glob`` keeps the file
# list above intact, so a renamed test file still trips the
# zero-tests guard rather than silently vanishing.
# (bash 3.2 on the macOS runner: an empty array under ``set -u`` is
# an unbound-variable error, hence the ``${arr[@]+...}`` idiom.)
EXTRA_ARGS=()
if [ "${{ inputs.desktop_updater }}" != "true" ]; then
echo "desktop_updater lane off: skipping tests/test_desktop_update_windows_*.py"
EXTRA_ARGS+=(--ignore-glob='*test_desktop_update_windows_*.py')
fi

status=0
uv run --no-sync python -m pytest \
"$@" \
${EXTRA_ARGS[@]+"${EXTRA_ARGS[@]}"} \
-m "${{ matrix.marker }} and not integration" \
-v --tb=short || status=$?
if [ "$status" -eq 5 ]; then
Expand Down
21 changes: 20 additions & 1 deletion .github/workflows/windows-venv-e2e.yml
Original file line number Diff line number Diff line change
Expand Up @@ -50,12 +50,31 @@ jobs:
- name: Install dependencies
uses: ./.github/actions/retry
with:
command: uv sync --locked --python 3.11 --extra dev
command: uv sync --locked --python 3.11 --extra dev --extra messaging

- name: Run venv-holder live E2E
shell: bash
run: |
set -uo pipefail
uv run --no-sync python -m pytest \
tests/hermes_cli/test_venv_holder_windows_live.py \
tests/hermes_cli/test_taskkill_identity_windows_live.py \
tests/hermes_cli/test_git_trampoline_windows_live.py \
"tests/hermes_cli/test_managed_uv.py::TestWindowsRuntimeSelfLock" \
-o addopts= -v -p no:cacheprovider

- name: Run Telegram CLOSE-WAIT reconnect live E2E (#87057)
shell: bash
run: |
set -uo pipefail
uv run --no-sync python -m pytest \
tests/gateway/test_telegram_closewait_windows_live.py \
-o addopts= -v -p no:cacheprovider

- name: Run background-executor spawn parity live E2E (#70716)
shell: bash
run: |
set -uo pipefail
uv run --no-sync python -m pytest \
tests/tools/test_process_registry_windows_live.py \
-o addopts= -v -p no:cacheprovider
12 changes: 10 additions & 2 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -99,15 +99,19 @@ apps/desktop/src/**/*.d.ts
!apps/desktop/src/global.d.ts
!apps/desktop/src/vite-env.d.ts

# Repo-root build/debug artifacts that must never be committed
# Build/debug artifacts that must never be committed
/log.txt
/sqlite_leak_fix.png
/*.png.bak
/default.tar.gz
*.tar.gz
*.tgz
apps/shared/src/**/*.js
apps/shared/src/**/*.js.map
apps/shared/src/**/*.d.ts
apps/desktop/release/
# stage-and-swap Desktop rebuild output (#86443); removed after the swap, but
# a killed build must not leave the checkout dirty
apps/desktop/.staging-*/
*.tsbuildinfo

# Web UI assets — synced from @nous-research/ui at build time via
Expand Down Expand Up @@ -212,3 +216,7 @@ native/fts5_cjk/*.so
# interrupted; consumed by launch-time recovery. Never commit it (was tracked
# by accident via 3a69e34702, removed in the #72002 salvage).
.lazy-refresh-incomplete
.skills_prompt_snapshot.json

# Disposable profile created by scripts/probe_active_session_exclusivity.py
.probe-home/
1 change: 1 addition & 0 deletions SOUL.md
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
You are Hermes Agent, built by Nous Research. Be direct: match the length of your reply to the weight of the ask — a one-line question gets a one-line answer, and finished work gets a short report of what changed, what's verified, and what's left, never a replay of the process. No filler ("Great question," "I'd be happy to"), no restating the request back, no re-summarizing what you already said, no narrating tool calls the user can see. Plain claims over adjectives; when unsure, say so plainly. Agree because it's right, not because the user said it. Depth is earned — give it when the user asks for detail, teaches, or the stakes demand it, not by default.
22 changes: 18 additions & 4 deletions acp_adapter/tools.py
Original file line number Diff line number Diff line change
Expand Up @@ -274,13 +274,27 @@ def _format_todo_result(result: Optional[str]) -> Optional[str]:
"cancelled": "✗",
}
lines = ["**Todo list**", ""]
for item in data["todos"]:
if not isinstance(item, dict):
continue
todos = [t for t in data["todos"] if isinstance(t, dict)]
ids = {str(t.get("id") or "") for t in todos}

def _depth(item: Dict[str, Any]) -> int:
depth, seen = 0, set()
node: Optional[Dict[str, Any]] = item
by_id = {str(t.get("id") or ""): t for t in todos}
while node is not None:
parent = str(node.get("parent") or "")
if not parent or parent not in ids or parent in seen:
break
seen.add(parent)
depth += 1
node = by_id.get(parent)
return min(depth, 4)

for item in todos:
status = str(item.get("status") or "pending")
content = str(item.get("content") or item.get("id") or "").strip()
if content:
lines.append(f"- {icon.get(status, '•')} {content}")
lines.append(f"{' ' * _depth(item)}- {icon.get(status, '•')} {content}")
if summary:
cancelled = summary.get("cancelled", 0)
lines.extend([
Expand Down
Loading
Loading