agent: Implement streaming for edit file tool (#50004)

Before you mark this PR as ready for review, make sure that you have:
- [x] Added a solid test coverage and/or screenshots from doing manual
testing
- [x] Done a self-review taking into account security and performance
aspects
- [x] Aligned any UI changes with the [UI
checklist](https://github.com/zed-industries/zed/blob/main/CONTRIBUTING.md#uiux-checklist)

Release Notes:

- N/A

---------

Co-authored-by: Zed Zippy <234243425+zed-zippy[bot]@users.noreply.github.com>
This commit is contained in:
Bennet Bo Fenner 2026-02-25 23:58:25 +01:00 committed by GitHub
parent 078ab6143e
commit a2e34cb7bf
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
8 changed files with 3389 additions and 292 deletions

View file

@ -2461,6 +2461,7 @@ impl Thread {
name: tool_name.to_string(),
description: tool.description().to_string(),
input_schema: tool.input_schema(model.tool_input_format()).log_err()?,
use_input_streaming: tool.supports_input_streaming(),
})
})
.collect::<Vec<_>>()

View file

@ -100,6 +100,7 @@ macro_rules! tools {
name: T::NAME.to_string(),
description: T::description().to_string(),
input_schema: T::input_schema(LanguageModelToolSchemaFormat::JsonSchema).to_value(),
use_input_streaming: T::supports_input_streaming(),
}
}
[

File diff suppressed because it is too large Load diff

View file

@ -526,11 +526,13 @@ impl CodegenAlternative {
name: REWRITE_SECTION_TOOL_NAME.to_string(),
description: "Replaces text in <rewrite_this></rewrite_this> tags with your replacement_text.".to_string(),
input_schema: language_model::tool_schema::root_schema_for::<RewriteSectionInput>(tool_input_format).to_value(),
use_input_streaming: false,
},
LanguageModelRequestTool {
name: FAILURE_MESSAGE_TOOL_NAME.to_string(),
description: "Use this tool to provide a message to the user when you're unable to complete a task.".to_string(),
input_schema: language_model::tool_schema::root_schema_for::<FailureMessageInput>(tool_input_format).to_value(),
use_input_streaming: false,
},
];

View file

@ -906,11 +906,17 @@ pub struct ImageSource {
pub data: String,
}
fn is_false(value: &bool) -> bool {
!value
}
#[derive(Debug, Serialize, Deserialize)]
pub struct Tool {
pub name: String,
pub description: String,
pub input_schema: serde_json::Value,
#[serde(default, skip_serializing_if = "is_false")]
pub eager_input_streaming: bool,
}
#[derive(Debug, Serialize, Deserialize)]

View file

@ -431,6 +431,7 @@ pub struct LanguageModelRequestTool {
pub name: String,
pub description: String,
pub input_schema: serde_json::Value,
pub use_input_streaming: bool,
}
#[derive(Debug, PartialEq, Hash, Clone, Serialize, Deserialize)]

View file

@ -370,6 +370,7 @@ pub fn into_anthropic_count_tokens_request(
name: tool.name,
description: tool.description,
input_schema: tool.input_schema,
eager_input_streaming: tool.use_input_streaming,
})
.collect(),
tool_choice: request.tool_choice.map(|choice| match choice {
@ -713,6 +714,7 @@ pub fn into_anthropic(
name: tool.name,
description: tool.description,
input_schema: tool.input_schema,
eager_input_streaming: tool.use_input_streaming,
})
.collect(),
tool_choice: request.tool_choice.map(|choice| match choice {

View file

@ -1566,6 +1566,7 @@ mod tests {
name: "get_weather".into(),
description: "Fetches the weather".into(),
input_schema: json!({ "type": "object" }),
use_input_streaming: false,
}],
tool_choice: Some(LanguageModelToolChoice::Any),
stop: vec!["<STOP>".into()],