main
tag: launch-2026-06-01
tag: magicmirror-v0.1.1
tag: magicmirror-v0.3.0
tag: mnw-cli-v0.1.2
tag: mnw-cli-v0.1.3
tag: mnw-cli-v0.1.4
tag: pom-v0.4.1
tag: pom-v0.4.2
tag: pom-v0.4.3
tag: pom-v0.4.4
tag: pom-v0.4.5
tag: wam-v0.3.0
tag: wam-v0.3.1
Files
Commits
Tags
Notes
Issues
server: fix test harness for spawn_pool shutdown-receiver signature
The Run 17 Resilience change gave spawn_pool a shutdown receiver and a
JoinHandle return; the integration + load test harnesses still called the old
no-arg form. Add spawn_pool_detached() (retains the shutdown sender so the pool
runs for the test's lifetime) and point the harness AppState/WorkerContext
builders at it.
Co-Authored-By
Claude Opus 4.8 <noreply@anthropic.com>
3 files changed,
+16 insertions,
-3 deletions
97
97
(BackgroundTx { tx }, handle)
98
98
}
99
99
100
+
/// Spawn a background pool with no external shutdown wiring, for test harnesses
101
+
/// and embeddings that manage lifecycle purely via `AppState` drop. The shutdown
102
+
/// sender is retained internally (its `changed()` never fires), so the pool
103
+
/// drains only when every `BackgroundTx` clone is dropped and the channel closes.
104
+
pub fn spawn_pool_detached() -> BackgroundTx {
105
+
let (tx, rx) = watch::channel(());
106
+
// Deliberately keep the sender alive so the drainer's shutdown arm never
107
+
// fires; the pool then behaves exactly as it did before shutdown draining
108
+
// existed (runs until the queue closes). Only reachable off the request path.
109
+
std::mem::forget(tx);
110
+
spawn_pool(rx).0
111
+
}
112
+
100
113
/// Acquire a permit and spawn `task`, releasing the permit when it finishes.
101
114
async fn run_task(sem: &Arc<Semaphore>, task: BoxFuture) {
102
115
let Ok(permit) = sem.clone().acquire_owned().await else {
400
400
makenotwork::constants::GIT_SMART_HTTP_MAX_CONCURRENT,
401
401
)),
402
402
page_view_tx: makenotwork::db::page_views::spawn_batcher(pool.clone()),
403
-
bg: makenotwork::background::spawn_pool(),
403
+
bg: makenotwork::background::spawn_pool_detached(),
404
404
};
405
405
406
406
// Capture scan deps before `build_app` consumes `state`.
547
547
pipeline: deps.pipeline.clone(),
548
548
scan_semaphore: deps.semaphore.clone(),
549
549
wam: None,
550
-
bg: makenotwork::background::spawn_pool(),
550
+
bg: makenotwork::background::spawn_pool_detached(),
551
551
// No Cloudflare purge in tests; quarantine still deletes from origin.
552
552
cloudflare: None,
553
553
cdn_base_url: None,
138
138
makenotwork::constants::GIT_SMART_HTTP_MAX_CONCURRENT,
139
139
)),
140
140
page_view_tx: makenotwork::db::page_views::spawn_batcher(pool.clone()),
141
-
bg: makenotwork::background::spawn_pool(),
141
+
bg: makenotwork::background::spawn_pool_detached(),
142
142
};
143
143
144
144
let app = build_app(state, session_layer);