max / makenotwork
- Co-Authored-By
- Claude Opus 5 (1M context) <noreply@anthropic.com>
- Claude-Session
- https://claude.ai/code/session_01P8ostB2UmZJGj5WjSHRSot
1 file changed,
+33 insertions,
-2 deletions
| @@ -913,7 +913,16 @@ | |||
| 913 | 913 | }; | |
| 914 | 914 | ||
| 915 | 915 | let carried = Carried::of(&mut parts).await; | |
| 916 | - | match answer(&viewer, &carried) { | |
| 916 | + | ||
| 917 | + | // On a blocking thread. See `served` for why. | |
| 918 | + | let answered = match tokio::task::spawn_blocking(move || answer(&viewer, &carried)) | |
| 919 | + | .await | |
| 920 | + | { | |
| 921 | + | Ok(answered) => answered, | |
| 922 | + | Err(_) => return axum::http::StatusCode::INTERNAL_SERVER_ERROR.into_response(), | |
| 923 | + | }; | |
| 924 | + | ||
| 925 | + | match answered { | |
| 917 | 926 | Ok(markup) => ( | |
| 918 | 927 | [(quasi_axum::htmx::RETARGET, format!("#{region}"))], | |
| 919 | 928 | axum::response::Html(markup), | |
| @@ -1068,7 +1077,29 @@ | |||
| 1068 | 1077 | }; | |
| 1069 | 1078 | ||
| 1070 | 1079 | let carried = Carried::of(&mut parts).await; | |
| 1071 | - | match answer(&viewer, &carried) { | |
| 1080 | + | ||
| 1081 | + | // On a blocking thread, for the reason `quasi_axum` dispatches | |
| 1082 | + | // every other screen on one: `answer` reaches the database | |
| 1083 | + | // through `Viewer::block_on`, and `block_on` from a runtime | |
| 1084 | + | // worker panics with "Cannot start a runtime from within a | |
| 1085 | + | // runtime". This mount is the one dispatch in the tree that is | |
| 1086 | + | // ours rather than the adapter's, so it is the one place that | |
| 1087 | + | // has to say so. | |
| 1088 | + | let held = (viewer, carried); | |
| 1089 | + | let (answered, held) = match tokio::task::spawn_blocking(move || { | |
| 1090 | + | let outcome = answer(&held.0, &held.1); | |
| 1091 | + | (outcome, held) | |
| 1092 | + | }) | |
| 1093 | + | .await | |
| 1094 | + | { | |
| 1095 | + | Ok(answered) => answered, | |
| 1096 | + | // A panic in the answer. Reported as ours, because it is, | |
| 1097 | + | // and the same way the adapter reports one. | |
| 1098 | + | Err(_) => return axum::http::StatusCode::INTERNAL_SERVER_ERROR.into_response(), | |
| 1099 | + | }; | |
| 1100 | + | let viewer = held.0; | |
| 1101 | + | ||
| 1102 | + | match answered { | |
| 1072 | 1103 | Ok(Served { screen, markup }) => { | |
| 1073 | 1104 | axum::response::Html(renderer(&viewer).served(&screen, &markup)) | |
| 1074 | 1105 | .into_response() |