Repository navigation
fix(frontend): render the chat template off the async runtime #15092
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. Weβll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -1380,6 +1380,19 @@ fn parse_embedding_add_special_tokens(value: &str) -> Option<bool> { | |
| parse_bool_opt(value) | ||
| } | ||
|
|
||
| /// Run CPU-bound preprocessing off the async runtime. On the multi-thread runtime | ||
| /// `block_in_place` hands this worker to the blocking pool, so the I/O tasks that | ||
| /// share the runtime keep draining sockets while a long conversation renders; | ||
| /// under load a synchronous render here can leave request bodies unread for | ||
| /// tens of seconds. Falls back to inline on the current-thread runtime, where | ||
| /// `block_in_place` is not available. | ||
| fn off_runtime<T>(f: impl FnOnce() -> T) -> T { | ||
| match tokio::runtime::Handle::try_current().map(|h| h.runtime_flavor()) { | ||
| Ok(tokio::runtime::RuntimeFlavor::MultiThread) => tokio::task::block_in_place(f), | ||
| _ => f(), | ||
| } | ||
| } | ||
|
|
||
| fn embedding_add_special_tokens_env() -> Result<Option<bool>> { | ||
| match std::env::var(EMBEDDING_ADD_SPECIAL_TOKENS_ENV) { | ||
| Ok(value) => match parse_embedding_add_special_tokens(&value) { | ||
|
|
@@ -2782,7 +2795,7 @@ impl OpenAIPreprocessor { | |
| let template_start = Instant::now(); | ||
| let formatted_prompt = { | ||
| let _nvtx = dynamo_nvtx_range!("preprocess.template"); | ||
| self.apply_template(request) | ||
| off_runtime(|| self.apply_template(request)) | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. π©Ί Stability & Availability | π‘ Minor | β‘ Quick win π Supported by static analysisπ Script executed: sed -n '1360,1410p' lib/llm/src/preprocessor.rs
sed -n '2760,2820p' lib/llm/src/preprocessor.rs
rg -n 'pub (async )?fn preprocess_request|struct OpenAIPreprocessor|fn apply_template|off_runtime|spawn_local|LocalSet' lib Cargo.toml
rg -n 'tokio\s*=|tokio =' Cargo.toml lib/*/Cargo.tomlRepository: ai-dynamo/dynamo Length of output: 6672 Use a
Because π€ Prompt for AI Agents |
||
| .with_context(|| "Failed to apply prompt template")? | ||
| }; | ||
| TEMPLATE_SECONDS.observe(template_start.elapsed().as_secs_f64()); | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
RuntimeFlavor::MultiThreadis also reported while a future is running in a TokioLocalSet, whereblock_in_placeis explicitly disallowed and panics. Sincepreprocess_requestis public and previously rendered inline, callers using a multithread runtime plusLocalSetnow crash whenever a chat template is applied.π€ AI Fix
Replace this
block_in_placepath with an async offload that is valid in local tasks, such as owning the render inputs and awaitingspawn_blocking, and add a LocalSet regression test.