fix(cli): invalidate per-instance config caches on global config update - #7179
fix(cli): invalidate per-instance config caches on global config update#7179kilo-code-bot[bot] wants to merge 1 commit into
Conversation
Config.updateGlobal() was only resetting the global lazy cache but not the per-instance State entries (Config.state, Agent.state, Provider.state, etc.). This meant active instances served stale config data — e.g. after changing default provider or model settings via the VS Code settings panel, the server would continue returning the old values until restart. Add State.resetCaches() which clears all cache-only State entries (those without dispose callbacks) across all instances. This invalidates derived state so it gets re-computed on next access, while preserving side-effectful resources like MCP connections, sessions, and file watchers.
| export function resetCaches() { | ||
| for (const entries of recordsByKey.values()) { | ||
| for (const [init, entry] of entries) { | ||
| if (entry.dispose) continue |
There was a problem hiding this comment.
WARNING: dispose is not a safe proxy for cache-only state
This also deletes long-lived per-instance stores that intentionally have no disposer, including SessionStatus.state, FileTime.state, InstructionPrompt.state, Bus.state, and Env.state. After a global config update, active sessions can lose busy status, read/write locks, subscriptions, and env overrides even though this change is meant to preserve session state.
| // Provider.state, etc.) so they re-read the updated global config on next access. | ||
| // Only cache entries without dispose callbacks are cleared — side-effectful state | ||
| // like sessions, MCP connections, and file watchers are preserved. | ||
| State.resetCaches() |
There was a problem hiding this comment.
WARNING: Config-backed services with disposers will not reload
State.resetCaches() only invalidates entries without a dispose callback. Services like MCP.state, LSP.state, and FileWatcher.state read Config.get() during initialization and do have disposers, so they keep running with the old global config. Changes like enabling/disabling MCP or LSP servers, or updating watcher ignore rules, will not take effect until the instance is fully disposed.
Code Review SummaryStatus: 2 Issues Found | Recommendation: Address before merge Fix these issues in Kilo Cloud Overview
Issue Details (click to expand)WARNING
Other Observations (not in diff)Issues found in unchanged code that cannot receive inline comments: None. Files Reviewed (2 files)
Reviewed by gpt-5.4-20260305 · 638,923 tokens |
Summary
Config.updateGlobal()— active instances now pick up global config changes (modes, providers, models, etc.) without requiring a server restartState.resetCaches()which clears all cache-onlyInstance.stateentries across all instances without tearing down side-effectful resourcesProblem
PR #7172 correctly removed
Instance.disposeAll()fromConfig.updateGlobal()to stop it from destroying sessions, MCP connections, and in-flight operations on every config change. However, this left a gap:global.reset()only invalidates the process-wide global config lazy cache, not the per-instanceConfig.state(or downstream caches likeAgent.state,Provider.state, etc.) that merge global config at initialization time.This meant that after a global config change via the VS Code settings panel (e.g. changing default agent, provider, or model), the server's HTTP endpoints (
/config,/app/agents,/app/providers) would continue returning stale cached data. The extension would re-fetch after theglobal.disposedSSE event, but get back the old values.As noted by the review bot on #7172: comment
Fix
State.resetCaches()iterates all instance state maps and deletes entries that have no dispose callback. These are the 18 "pure cache" entries (Config, Agent, Provider, Tool, Skill, Command, Format, Plugin, etc.) that are safe to drop and will be re-computed on next access. The 9 entries with dispose callbacks (Prompt sessions, MCP connections, LSP clients, PTY processes, file watchers, etc.) are preserved.The flow after the fix: