cmdConfigGet resolved absent keys through only the 4-key SCHEMA_DEFAULTS map, so the ~42 registry-declared configSchema defaults (including the workflow.security_enforcement security gate, default true) returned 'Key not found' (rc=1) — diverging from the runtime's own resolveConfigKey Level-4 resolver and letting '... || echo false' guards silently read the gate as disabled. Add a resolveSchemaDefault helper that layers SCHEMA_DEFAULTS over the already-imported getCapabilityConfigSchema(cwd) accessor, wired into all three absent-key branches. --default flag precedence, the legacy 4 keys, and 'Key not found' for genuinely unknown keys are preserved. Two pre-existing, security-relevant defects in the same surface, found while writing the regression tests, are fixed inline (no-defer policy): - The --default fallback path never masked secret-named keys, printing e.g. 'config-get brave_search --default <secret>' in plaintext. All six default-emission sites now route through emitResolvedDefault, which applies the same isSecretKey/maskSecret masking the found-key path uses. - Dotted-key traversal used raw bracket access, so 'config-get __proto__' / 'constructor' walked the JS prototype chain and returned internals at rc=0 instead of erroring. Each segment is now own-property-gated. Regression tests folded into tests/config-get-default.test.cjs cover registry defaults (boolean/enum/number, read live from the registry), the no-file/mid-traversal/final-undefined branches, --default and legacy precedence, prototype-pollution keys, secret masking, and the Key-not-found vs No-config-file negative cases. Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
This commit is contained in:
5
.changeset/lively-hawks-caper.md
Normal file
5
.changeset/lively-hawks-caper.md
Normal file
@@ -0,0 +1,5 @@
|
||||
---
|
||||
type: Security
|
||||
pr: 2299
|
||||
---
|
||||
**`query config-get` no longer leaks secret values or walks the prototype chain** — the `--default` fallback path printed secret-named keys (e.g. `brave_search`) in plaintext instead of masking them, and dotted-key traversal used raw property access so `config-get __proto__`/`constructor` resolved to JavaScript internals at exit 0 instead of erroring. Both absent-key resolution and traversal are now masked and own-property-gated. (#2256)
|
||||
5
.changeset/rapid-elks-rest.md
Normal file
5
.changeset/rapid-elks-rest.md
Normal file
@@ -0,0 +1,5 @@
|
||||
---
|
||||
type: Fixed
|
||||
pr: 2299
|
||||
---
|
||||
**`query config-get` now returns capability-registry defaults for absent keys** — keys declared with a default in the capability registry (e.g. `workflow.security_enforcement`, which defaults to `true`) previously reported "Key not found" (exit 1) when missing from config.json, diverging from the runtime's own resolver and letting `... || echo false` guards silently read the security gate as disabled. config-get now resolves these through the same registry defaults the runtime uses. (#2256)
|
||||
Reference in New Issue
Block a user