Description
The clone() helper in models.config.mjs:116-118 uses structuredClone() and is called in every getter function:
export function clone(value) {
return value === undefined ? undefined : structuredClone(value);
}
Called from:
getModelLimit() (line 131) — clones { context: N, output: N }
getModelCost() (line 152, 156) — clones { input: N, output: N, cache_read: N, cache_write: N }
getModelVariants() (line 163) — clones variant objects
getModelOptions() (line 170) — clones { reasoningEffort: "none" }
Analysis
structuredClone() is designed for deep-cloning complex objects with circular references, typed arrays, Maps, Sets, etc. Here it's used on flat objects with 2-5 numeric/string fields.
In processModels(), these cloned objects are immediately assigned to models[displayName] and never mutated afterwards. The clone exists purely as defensive programming against a mutation that never happens.
Impact
structuredClone() is ~10-50x slower than object spread for small flat objects.
- With 15+ supported models, that's 60+ unnecessary
structuredClone calls per run.
- In practice, the total wall-clock impact is sub-millisecond, so this is a code quality issue, not a performance bottleneck.
Proposed fix
Option A: Replace structuredClone with spread for flat objects:
export function clone(value) {
return value === undefined ? undefined : { ...value };
}
Option B: Remove clone() entirely — the objects from SUPPORTED_MODELS are literals that are never mutated:
export function getModelLimit(displayName, apiModel = null) {
const config = getModelConfig(displayName);
if (config?.limit) return config.limit;
// ...
}
Option C: Keep clone() but document why defensive copying is needed (if there's a downstream mutation scenario I'm not seeing).
Acceptance criteria
🤖 Generated with Claude Code
Description
The
clone()helper inmodels.config.mjs:116-118usesstructuredClone()and is called in every getter function:Called from:
getModelLimit()(line 131) — clones{ context: N, output: N }getModelCost()(line 152, 156) — clones{ input: N, output: N, cache_read: N, cache_write: N }getModelVariants()(line 163) — clones variant objectsgetModelOptions()(line 170) — clones{ reasoningEffort: "none" }Analysis
structuredClone()is designed for deep-cloning complex objects with circular references, typed arrays, Maps, Sets, etc. Here it's used on flat objects with 2-5 numeric/string fields.In
processModels(), these cloned objects are immediately assigned tomodels[displayName]and never mutated afterwards. The clone exists purely as defensive programming against a mutation that never happens.Impact
structuredClone()is ~10-50x slower than object spread for small flat objects.structuredClonecalls per run.Proposed fix
Option A: Replace
structuredClonewith spread for flat objects:Option B: Remove
clone()entirely — the objects fromSUPPORTED_MODELSare literals that are never mutated:Option C: Keep
clone()but document why defensive copying is needed (if there's a downstream mutation scenario I'm not seeing).Acceptance criteria
structuredClone()is replaced with a lighter-weight approach or removed.SUPPORTED_MODELSvalues are not mutated by any code path (verify or add a freeze-based test).🤖 Generated with Claude Code