{"record":{"id":"a2f7beb144d11d5c","repo":"langchain-ai/deepagents","slug":"plugin-state-file-path-detail","errorCode":null,"errorMessage":"Plugin state file {path} {detail}","messagePattern":"Plugin state file (.+?) (.+?)","errorType":"exception","errorClass":"PluginStateError","httpStatus":null,"severity":"error","filePath":"libs/code/deepagents_code/plugins/store.py","lineNumber":175,"sourceCode":"\ndef _marketplaces_path() -> Path:\n    return _state_dir() / \"plugin_marketplaces.json\"\n\n\ndef _plugin_state_path() -> Path:\n    return _state_dir() / \"plugin_state.json\"\n\n\ndef _installed_plugins_path() -> Path:\n    return _state_dir() / \"installed_plugins.json\"\n\n\ndef _invalid_state(\n    path: Path, detail: str, *, strict: bool, cause: Exception | None = None\n) -> dict[str, Any]:\n    msg = f\"Plugin state file {path} {detail}\"\n    if strict:\n        raise PluginStateError(msg) from cause\n    logger.warning(\"%s\", msg)\n    return {}\n\n\ndef _load_json(\n    path: Path,\n    *,\n    max_version: int = _STORAGE_VERSION,\n    strict: bool = False,\n) -> dict[str, Any]:\n    if not path.exists():\n        return {}\n    try:\n        data = json.loads(path.read_text(encoding=\"utf-8\"))\n    except (OSError, UnicodeDecodeError, json.JSONDecodeError) as exc:\n        return _invalid_state(\n            path, f\"could not be read: {exc}\", strict=strict, cause=exc\n        )","sourceCodeStart":157,"sourceCodeEnd":193,"githubUrl":"https://github.com/langchain-ai/deepagents/blob/a1af029e6e73cb17c36bff823d227747b28e91e1/libs/code/deepagents_code/plugins/store.py#L157-L193","documentation":"_invalid_state is the central reporter for corrupt or invalid plugin state files (store.py). In strict mode it raises PluginStateError with 'Plugin state file {path} {detail}'; in non-strict mode it logs a warning and returns {} so the caller proceeds with empty state. Whether you get an exception depends entirely on the strict flag chosen by _load_json's caller.","triggerScenarios":"Calling state-loading APIs whose _load_json strict=True path encounters invalid content: unparseable JSON, wrong top-level type, or missing required fields — _invalid_state then raises PluginStateError with a detail describing the exact problem.","commonSituations":"A partially written state file after a crash or kill during save; manual editing of the state JSON; version upgrades changing the state schema; disk corruption or a state file replaced by an empty/HTML file.","solutions":["Read the `detail` in the message, fix the specific malformation (JSON syntax, type, or field) at the given path.","Delete or rename the corrupt state file so the store regenerates a fresh one (you lose cached state, not plugins).","If the schema changed after an upgrade, migrate the file to the new format or regenerate it."],"exampleFix":"// before: hand-edited state missing required keys\n{ \"installed\": [\"lint@team\"] }\n// after: restore proper structure or remove the file and let it regenerate\nrm ~/.deepagents/plugin_state.json","handlingStrategy":"try-catch","validationCode":"import json\nfrom pathlib import Path\n\ndef state_file_ok(path: Path) -> bool:\n    try:\n        return isinstance(json.loads(path.read_text(encoding=\"utf-8\")), dict)\n    except (json.JSONDecodeError, OSError):\n        return False","typeGuard":"def is_state_dict(raw: object) -> TypeGuard[dict]:\n    return isinstance(raw, dict)","tryCatchPattern":"from deepagents_code.plugins.store import PluginStateError\ntry:\n    state = load_state(path)\nexcept PluginStateError as exc:\n    logger.warning(\"Discarding corrupt state: %s\", exc)\n    path.rename(path.with_suffix(\".corrupt\"))\n    state = {}","preventionTips":["Write state atomically (tmp file + os.replace) to survive crashes mid-write.","Never hand-edit state files; use the library's save APIs.","Back up or version the state schema and migrate on upgrades instead of editing in place."],"tags":["state","corruption","json","persistence"],"backgroundTag":"corrupt-state-file","analyzedSha":"a1af029e6e73cb17c36bff823d227747b28e91e1","analyzedAt":"2026-08-29T11:43:24.718Z","schemaVersion":2},"datasetVersion":"2026-08-29T12:17:43.993Z"}