fix(config): copy all ServerConfig fields in CopyServerConfig#741
Conversation
CopyServerConfig was hand-copying a subset of ServerConfig fields and had drifted as new fields were added — it silently omitted EnabledTools, DisabledTools, ReconnectOnUse, HealthCheckInterval, ToolDiscoveryInterval, SourceRegistryID, SourceRegistryProvenance, and AuthBroker. Because MergeServerConfig starts from CopyServerConfig(base), any config merge/patch (e.g. upstream_servers patch, the Web UI server-config edit) round-trips the server through CopyServerConfig and drops these fields. The user-visible symptom: editing an unrelated field on a server that has a disabled_tools / enabled_tools allowlist, a reconnect-on-use flag, or per-server health/discovery cadence overrides silently wipes those settings. Copy the missing fields: scalars and slices directly (deep-copying the allowlist slices like Args), the *Duration overrides by value (matching the AutoApproveToolChanges pattern), and the AuthBroker block by value (a no-op empty stub in the personal edition). Tests: TestCopyServerConfig_PreservesAllowlistAndOverrides asserts each field is copied and that slices/pointers are independent of the source; TestMergeServerConfig_PreservesDisabledToolsOnUnrelatedPatch is the end-to-end regression for the patch path. Note: the same record<->config field mapping is hand-duplicated in the storage layer (SaveUpstreamServer / GetUpstreamServer / ListUpstreamServers / ListQuarantinedUpstreamServers); ListQuarantinedUpstreamServers has drifted similarly. A follow-up could collapse all of these onto a single helper to prevent the next field from drifting again. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
|
Codecov Report❌ Patch coverage is
📢 Thoughts on this report? Let us know! |
There was a problem hiding this comment.
✅ Gatekeeper approval — Codex review verdict: ACCEPT.
This approval is posted automatically by the MCPProxy Gatekeeper App on behalf of the Codex reviewer (verdict of record lives in the Paperclip review thread). Author≠approver satisfied; QA + CI gates enforced separately.
Auto-approved per Model B (MCP-1249).
|
Thank you, @electrolob — really nice fix. 🙏 A reviewer enumerated all 26
Verified locally: Merging now. Two optional, non-blocking notes for the future: (1) in the server edition, |
There was a problem hiding this comment.
APPROVE — Claude Code review. All 26 ServerConfig fields copied; slices/maps/pointers deep-copied (non-aliasing asserted by new tests); *Duration/*bool by value; build-tagged AuthBroker handled. go build + config/storage tests (incl -tags server) pass, gofmt clean. Non-blocking nits: server-edition AuthBroker.Scopes shallow (low impact); reflection completeness test suggested. Community PR by @electrolob.
Problem
CopyServerConfig(internal/config/merge.go) hand-copies a subset ofServerConfigfields and has drifted as new fields were added. It silently omits 8 fields:EnabledTools,DisabledTools,ReconnectOnUse,HealthCheckInterval,ToolDiscoveryInterval,SourceRegistryID,SourceRegistryProvenance, andAuthBroker(onlyAutoApproveToolChangeswas kept current).Because
MergeServerConfigstarts fromCopyServerConfig(base), any config merge/patch (e.g.upstream_serverspatch, the Web UI server-config edit) round-trips the server throughCopyServerConfigand drops these fields.User-visible symptom: editing an unrelated field on a server that has a
disabled_tools/enabled_toolsallowlist (orreconnect_on_use, or per-server health/discovery cadence overrides) silently wipes those settings.Fix
Copy the missing fields:
ReconnectOnUse,SourceRegistryID,SourceRegistryProvenance) in the struct literal;EnabledTools,DisabledTools) deep-copied likeArgs;*Durationoverrides (HealthCheckInterval,ToolDiscoveryInterval) by value, matching the existingAutoApproveToolChangespattern;AuthBrokerblock by value (a no-op empty stub in the personal edition).Tests
TestCopyServerConfig_PreservesAllowlistAndOverrides— asserts each field is copied, and that the slices/pointers are independent of the source (deep copy).TestMergeServerConfig_PreservesDisabledToolsOnUnrelatedPatch— end-to-end regression: an unrelated patch must not wipe a server'sdisabled_tools.Follow-up (not in this PR)
The same record↔config field mapping is hand-duplicated in the storage layer (
SaveUpstreamServer/GetUpstreamServer/ListUpstreamServers/ListQuarantinedUpstreamServers), andListQuarantinedUpstreamServershas drifted similarly (missingAutoApproveToolChanges,LauncherWaitTimeout, and the spec-074 intervals). Collapsing all of these onto a single helper would prevent the next field from drifting again — happy to do that in a separate PR if you'd like.