fix: persist channel activation state across restarts (#432)

* fix: persist channel activation state across restarts (#392)

Channels activated via the web UI were lost on restart because
active_channel_names was only in memory. Now persist activation state
to the settings store under "activated_channels" and auto-activate
persisted channels on startup.

Co-Authored-By: Claude Opus 4.6 <[email protected]>

* fix: log warnings for channel activation load failures

Replace silent catch-all with explicit error logging when
database queries or deserialization fails for activated channels.

Addresses Gemini review feedback on PR #432.

Co-Authored-By: Claude Opus 4.6 <[email protected]>

* Apply suggestions from code review

Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com>

---------

Co-authored-by: Claude Opus 4.6 <[email protected]>
Co-authored-by: Illia Polosukhin <[email protected]>
Co-authored-by: gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com>
This commit is contained in:
Zaki Manian
2026-03-01 08:53:32 +00:00
committed by GitHub
co-authored by Claude Opus 4.6 Illia Polosukhin gemini-code-assist[bot] <176961590+gemini-code-assist[bot]@users.noreply.github.com>
parent 7b883a02c0
commit fa52df593d
2 changed files with 79 additions and 0 deletions
+25
View File
@@ -609,6 +609,8 @@ async fn async_main() -> anyhow::Result<()> {
if let Some(ref ext_mgr) = components.extension_manager
&& let Some((rt, ps, router)) = wasm_channel_runtime_state.take()
{
let active_at_startup: std::collections::HashSet<String> =
loaded_wasm_channel_names.iter().cloned().collect();
ext_mgr.set_active_channels(loaded_wasm_channel_names).await;
ext_mgr
.set_channel_runtime(
@@ -620,6 +622,29 @@ async fn async_main() -> anyhow::Result<()> {
)
.await;
tracing::info!("Channel runtime wired into extension manager for hot-activation");
// Auto-activate channels that were active in a previous session.
let persisted = ext_mgr.load_persisted_active_channels().await;
for name in &persisted {
if !active_at_startup.contains(name) {
match ext_mgr.activate(name).await {
Ok(result) => {
tracing::info!(
channel = %name,
message = %result.message,
"Auto-activated persisted channel"
);
}
Err(e) => {
tracing::warn!(
channel = %name,
error = %e,
"Failed to auto-activate persisted channel"
);
}
}
}
}
}
// Wire SSE sender into extension manager for broadcasting status events.