{"record":{"id":"c755489a13a08e21","repo":"zeroclaw-labs/zeroclaw","slug":"memory-backend-does-not-support-storeoptions","errorCode":null,"errorMessage":"memory backend '{}' does not support StoreOptions kind/pinned/tenant_id; use a backend that overrides store_with_options","messagePattern":"memory backend '(.+?)' does not support StoreOptions kind/pinned/tenant_id; use a backend that overrides store_with_options","errorType":"exception","errorClass":"anyhow::Error","httpStatus":null,"severity":"error","filePath":"crates/zeroclaw-api/src/memory_traits.rs","lineNumber":561,"sourceCode":"        self.store(key, content, category, session_id).await\n    }\n\n    /// Store a memory entry with the full additive metadata surface.\n    ///\n    /// Default delegates through the existing metadata method for namespace and\n    /// importance only. Backends that do not override this must fail explicitly\n    /// when callers pass typed/full metadata, rather than silently discarding\n    /// data needed by later typed-memory readers.\n    async fn store_with_options(\n        &self,\n        key: &str,\n        content: &str,\n        category: MemoryCategory,\n        session_id: Option<&str>,\n        options: StoreOptions,\n    ) -> anyhow::Result<()> {\n        if options.requires_full_options_storage() {\n            anyhow::bail!(\n                \"memory backend '{}' does not support StoreOptions kind/pinned/tenant_id; use a backend that overrides store_with_options\",\n                self.name()\n            );\n        }\n        self.store_with_metadata(\n            key,\n            content,\n            category,\n            session_id,\n            options.namespace.as_deref(),\n            options.importance,\n        )\n        .await\n    }\n\n    /// Store a memory entry with full metadata and an explicit agent UUID.\n    ///\n    /// The compatibility default preserves agent attribution through the","sourceCodeStart":543,"sourceCodeEnd":579,"githubUrl":"https://github.com/zeroclaw-labs/zeroclaw/blob/88bb9c8533fc57ed7a03e36ca7c9ed2bf8336dcc/crates/zeroclaw-api/src/memory_traits.rs#L543-L579","documentation":"install_global_subscriber is the single logging entry point for daemon binaries: it stacks LogCaptureLayer under an alias-prefixed stderr formatter and calls tracing::subscriber::set_global_default. tracing allows exactly one global default per process; set_global_default returns Err when one is already installed, and this expect converts that into a panic. The crate already ships non-panicking siblings — try_install_capture_subscriber and try_install_line_sink_for_tests — which ignore the same error.","triggerScenarios":"Calling install_global_subscriber a second time, or calling it after anything else installed a global subscriber: tracing_subscriber::fmt::init() in another crate or test harness, env_logger's tracing bridge, or an embedding application that sets its own default.","commonSituations":"Integration test suites where an earlier test initialized logging; a dependency that calls init() itself; embedding zeroclaw in a host app that already configures tracing; a refactor that moves the install call onto a path executed more than once (e.g. per-agent instead of per-process).","solutions":["Install exactly once at process start; guard the call with std::sync::Once or check tracing::dispatcher::has_been_set() first.","For secondary or embedded contexts use zeroclaw_log::try_install_capture_subscriber(), which ignores an already-set default.","In tests, prefer per-test scoped subscribers (tracing::subscriber::with_default) or the crate's try_install_line_sink_for_tests().","Grep the dependency graph for set_global_default, fmt::init, or env_logger init to find the competing installer."],"exampleFix":"// before\nzeroclaw_log::install_global_subscriber(None, \"info\", false);\nzeroclaw_log::install_global_subscriber(None, \"info\", true); // second call panics\n\n// after\nstatic LOG_INIT: std::sync::Once = std::sync::Once::new();\nLOG_INIT.call_once(|| zeroclaw_log::install_global_subscriber(None, \"info\", false));","handlingStrategy":"validation","validationCode":"// Before installing:\nif !tracing::dispatcher::has_been_set() {\n    zeroclaw_log::install_global_subscriber(None, \"info\", false);\n} else {\n    zeroclaw_log::try_install_capture_subscriber(); // non-panicking fallback\n}","typeGuard":null,"tryCatchPattern":"// If third-party code may race you to the global default:\nlet r = std::panic::catch_unwind(|| {\n    zeroclaw_log::install_global_subscriber(None, \"info\", false);\n});\nif r.is_err() {\n    // another subscriber won the race; keep it and continue with its output\n}","preventionTips":["Initialize logging in main() before spawning tasks, exactly once","Never call subscriber installation from library code","Check has_been_set() when embedding zeroclaw in a larger process","Prefer the try_* variants in shared processes and test harnesses","Grep dependencies for fmt::init()/set_global_default when this panic appears"],"tags":["rust","tracing","logging","global-state","initialization","panic"],"backgroundTag":"tracing-global-subscriber-already-set","analyzedSha":"88bb9c8533fc57ed7a03e36ca7c9ed2bf8336dcc","analyzedAt":"2026-08-23T01:07:41.857Z","schemaVersion":2},"datasetVersion":"2026-08-23T08:06:27.607Z"}