{"record":{"id":"d9608e180dac79e7","repo":"JuliusBrussee/caveman","slug":"artifact-id-is-required","errorCode":null,"errorMessage":"artifact_id is required","messagePattern":"artifact_id is required","errorType":"validation","errorClass":"ValueError","httpStatus":null,"severity":"error","filePath":"packages/sdk/python/caveman_cloud/core.py","lineNumber":1195,"sourceCode":"                \"x-cave-artifact-source\": str(options[\"source\"]),\n            },\n        )\n        if response.get(\"stored\") is False:\n            return value\n        if response.get(\"stored\") is not True or not isinstance(response.get(\"artifact_id\"), str) or not response[\"artifact_id\"].strip():\n            raise RuntimeError(\"cave artifact response missing artifact_id\")\n        content_type = options.get(\"content_type\") or \"application/json\"\n        return (\n            f\"[cave-artifact id={response['artifact_id']} source={options['source']} type={content_type}]\\n\"\n            f\"summary: artifact stored.\\n\"\n            f\"retrieve: authenticated GET /sdk/v1/artifacts/{response['artifact_id']} or trace.artifacts.get(\\\"{response['artifact_id']}\\\").\\n\"\n            f\"[/cave-artifact]\"\n        )\n\n    def get_artifact(self, artifact_id: str) -> Any:\n        \"\"\"Retrieve and JSON-decode one artifact produced by :meth:`page_artifact`.\"\"\"\n        if not isinstance(artifact_id, str) or not artifact_id.strip():\n            raise ValueError(\"artifact_id is required\")\n        return self._get(f\"/sdk/v1/artifacts/{quote(artifact_id, safe='')}\")\n\n    @property\n    def artifacts(self) -> \"_Artifacts\":\n        \"\"\"Artifact handle mirroring the TS ``trace.artifacts`` namespace.\n\n        ``trace.artifacts.page(value, options)`` is the mirror-named entry point\n        for :meth:`page_artifact`; both hit ``/sdk/v1/artifacts`` with an\n        identical wire body.\n        \"\"\"\n        return _Artifacts(self)\n\n    def checkpoint(self, messages: list[Any], options: dict[str, Any]) -> dict[str, Any]:\n        # `workflow` mirrors the TS SDK body; the gateway's checkpoint.Request\n        # carries it (omitempty) so both SDKs send the identical wire.\n        return self._request(\"/sdk/v1/checkpoints\", {\"messages\": messages, \"options\": options, \"workflow\": self.workflow})\n\n    def expand(self, source_ref: str) -> dict[str, Any]:","sourceCodeStart":1177,"sourceCodeEnd":1213,"githubUrl":"https://github.com/JuliusBrussee/caveman/blob/27d5a3981a347890211bb1bf2439e5c821a63bc9/packages/sdk/python/caveman_cloud/core.py#L1177-L1213","documentation":"Error \"artifact_id is required\" thrown in JuliusBrussee/caveman.","triggerScenarios":"Thrown at packages/sdk/python/caveman_cloud/core.py:1195 when the library encounters an invalid state.","commonSituations":"See trigger scenarios.","solutions":["Pass a non-empty artifact_id."],"exampleFix":null,"handlingStrategy":null,"validationCode":null,"typeGuard":null,"tryCatchPattern":null,"preventionTips":[],"tags":[],"backgroundTag":null,"analyzedSha":"27d5a3981a347890211bb1bf2439e5c821a63bc9","analyzedAt":"2026-08-15T09:26:11.751Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}