{"record":{"id":"193af0218c60a527","repo":"xai-org/x-algorithm","slug":"unused-kv-pairs-k","errorCode":null,"errorMessage":"Unused KV pairs: {k}","messagePattern":"Unused KV pairs: (.+?)","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"phoenix/xrex/configs/config_loader.py","lineNumber":60,"sourceCode":"def get_config_module(mod_name: str) -> dict[str, Config]:\n    try:\n        return importlib.import_module(f\"xrex.configs.{mod_name}\")\n    except ImportError as e:\n        raise ValueError(\n            f\"No config module found {mod_name!r} under 'xrex.configs', \"\n            f\"or {mod_name!r} has another import issue: {traceback.format_exc()}\"\n        ) from e\n\n\ndef replace_cli_subs(config: Any, kvs: list[str]) -> tuple[Any, dict[str, list[str]]]:\n    return xai_configlib.replace_cli_subs(config, kvs, PRESETS)\n\n\ndef replace_and_validate_cli_subs(config: Any, kvs: list[str]) -> Any:\n    config, used = xai_configlib.replace_cli_subs(config, kvs, PRESETS)\n    for k, v in used.items():\n        if not v:\n            raise ValueError(f\"Unused KV pairs: {k}\")\n        elif len(v) > 1:\n            logger.warning(f\"{k} matches multiple paths: {v}\")\n    return config\n\n\n_DEFAULT_AOT_CACHE_DIR = \"/tmp/jax_aot_cache/\"\n\n\ndef _apply_deployment_defaults(config: Config) -> Config:\n    if settings.AOT_CACHE_DIR and getattr(config, \"aot_cache_dir\", None) == (\n        _DEFAULT_AOT_CACHE_DIR\n    ):\n        config.aot_cache_dir = settings.AOT_CACHE_DIR\n    return config\n\n\ndef get_named_config(name: str) -> Config:\n    if \":\" in name:","sourceCodeStart":42,"sourceCodeEnd":78,"githubUrl":"https://github.com/xai-org/x-algorithm/blob/24c60942c5c5fdad3a6addffb4c6e6d2f228f04f/phoenix/xrex/configs/config_loader.py#L42-L78","documentation":"replace_and_validate_cli_subs applies CLI overrides and then verifies every provided key actually matched a path in the config. Keys that matched zero paths raise this 'Unused KV pairs' ValueError; keys matching multiple paths only log a warning.","triggerScenarios":"Passing 'lr=1e-4' when the config has no field whose path matches 'lr' (e.g. it's nested as optimizer.lr), or a typo'd key.","commonSituations":"Config schema refactors renaming fields, overrides written for a different config class, or wrong nesting level in the dotted key.","solutions":["Use the fully dotted path matching the config structure ('optimizer.lr=1e-4')","Fix typos in the key","After schema changes, update launch scripts' override lists"],"exampleFix":"# before\nreplace_and_validate_cli_subs(cfg, [\"lr=1e-4\"])  # field is cfg.optimizer.lr\n# after\nreplace_and_validate_cli_subs(cfg, [\"optimizer.lr=1e-4\"])","handlingStrategy":"validation","validationCode":"# dry-run: check each key matches at least one path\nimport dataclasses\n\ndef paths(obj, prefix=\"\"):\n    for f in dataclasses.fields(obj):\n        p = f\"{prefix}.{f.name}\" if prefix else f.name\n        v = getattr(obj, f.name)\n        yield p\n        if dataclasses.is_dataclass(v) and not isinstance(v, type):\n            yield from paths(v, p)\n\nall_paths = set(paths(config))\nunused = [kv for kv in kvs if kv.split(\"=\",1)[0] not in all_paths]\nassert not unused, f\"Unused overrides: {unused}\"","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Use full dotted paths in overrides","Re-validate override lists after schema refactors"],"tags":["config","cli","validation","unused-keys"],"backgroundTag":"unknown-config-key","analyzedSha":"24c60942c5c5fdad3a6addffb4c6e6d2f228f04f","analyzedAt":"2026-08-28T11:40:14.686Z","schemaVersion":2},"datasetVersion":"2026-08-28T16:17:29.566Z"}