Port terminal
tool to agent2 (#35918)
Release Notes: - N/A --------- Co-authored-by: Ben Brandt <benjamin.j.brandt@gmail.com>
This commit is contained in:
parent
422e0a2eb7
commit
086ea3c619
13 changed files with 882 additions and 112 deletions
|
@ -1,5 +1,4 @@
|
|||
use crate::{SystemPromptTemplate, Template, Templates};
|
||||
use acp_thread::Diff;
|
||||
use action_log::ActionLog;
|
||||
use agent_client_protocol as acp;
|
||||
use anyhow::{Context as _, Result, anyhow};
|
||||
|
@ -802,47 +801,6 @@ impl AgentResponseEventStream {
|
|||
.ok();
|
||||
}
|
||||
|
||||
fn authorize_tool_call(
|
||||
&self,
|
||||
id: &LanguageModelToolUseId,
|
||||
title: String,
|
||||
kind: acp::ToolKind,
|
||||
input: serde_json::Value,
|
||||
) -> impl use<> + Future<Output = Result<()>> {
|
||||
let (response_tx, response_rx) = oneshot::channel();
|
||||
self.0
|
||||
.unbounded_send(Ok(AgentResponseEvent::ToolCallAuthorization(
|
||||
ToolCallAuthorization {
|
||||
tool_call: Self::initial_tool_call(id, title, kind, input),
|
||||
options: vec![
|
||||
acp::PermissionOption {
|
||||
id: acp::PermissionOptionId("always_allow".into()),
|
||||
name: "Always Allow".into(),
|
||||
kind: acp::PermissionOptionKind::AllowAlways,
|
||||
},
|
||||
acp::PermissionOption {
|
||||
id: acp::PermissionOptionId("allow".into()),
|
||||
name: "Allow".into(),
|
||||
kind: acp::PermissionOptionKind::AllowOnce,
|
||||
},
|
||||
acp::PermissionOption {
|
||||
id: acp::PermissionOptionId("deny".into()),
|
||||
name: "Deny".into(),
|
||||
kind: acp::PermissionOptionKind::RejectOnce,
|
||||
},
|
||||
],
|
||||
response: response_tx,
|
||||
},
|
||||
)))
|
||||
.ok();
|
||||
async move {
|
||||
match response_rx.await?.0.as_ref() {
|
||||
"allow" | "always_allow" => Ok(()),
|
||||
_ => Err(anyhow!("Permission to run tool denied by user")),
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
fn send_tool_call(
|
||||
&self,
|
||||
id: &LanguageModelToolUseId,
|
||||
|
@ -894,18 +852,6 @@ impl AgentResponseEventStream {
|
|||
.ok();
|
||||
}
|
||||
|
||||
fn update_tool_call_diff(&self, tool_use_id: &LanguageModelToolUseId, diff: Entity<Diff>) {
|
||||
self.0
|
||||
.unbounded_send(Ok(AgentResponseEvent::ToolCallUpdate(
|
||||
acp_thread::ToolCallUpdateDiff {
|
||||
id: acp::ToolCallId(tool_use_id.to_string().into()),
|
||||
diff,
|
||||
}
|
||||
.into(),
|
||||
)))
|
||||
.ok();
|
||||
}
|
||||
|
||||
fn send_stop(&self, reason: StopReason) {
|
||||
match reason {
|
||||
StopReason::EndTurn => {
|
||||
|
@ -979,17 +925,71 @@ impl ToolCallEventStream {
|
|||
.update_tool_call_fields(&self.tool_use_id, fields);
|
||||
}
|
||||
|
||||
pub fn update_diff(&self, diff: Entity<Diff>) {
|
||||
self.stream.update_tool_call_diff(&self.tool_use_id, diff);
|
||||
pub fn update_diff(&self, diff: Entity<acp_thread::Diff>) {
|
||||
self.stream
|
||||
.0
|
||||
.unbounded_send(Ok(AgentResponseEvent::ToolCallUpdate(
|
||||
acp_thread::ToolCallUpdateDiff {
|
||||
id: acp::ToolCallId(self.tool_use_id.to_string().into()),
|
||||
diff,
|
||||
}
|
||||
.into(),
|
||||
)))
|
||||
.ok();
|
||||
}
|
||||
|
||||
pub fn update_terminal(&self, terminal: Entity<acp_thread::Terminal>) {
|
||||
self.stream
|
||||
.0
|
||||
.unbounded_send(Ok(AgentResponseEvent::ToolCallUpdate(
|
||||
acp_thread::ToolCallUpdateTerminal {
|
||||
id: acp::ToolCallId(self.tool_use_id.to_string().into()),
|
||||
terminal,
|
||||
}
|
||||
.into(),
|
||||
)))
|
||||
.ok();
|
||||
}
|
||||
|
||||
pub fn authorize(&self, title: String) -> impl use<> + Future<Output = Result<()>> {
|
||||
self.stream.authorize_tool_call(
|
||||
&self.tool_use_id,
|
||||
title,
|
||||
self.kind.clone(),
|
||||
self.input.clone(),
|
||||
)
|
||||
let (response_tx, response_rx) = oneshot::channel();
|
||||
self.stream
|
||||
.0
|
||||
.unbounded_send(Ok(AgentResponseEvent::ToolCallAuthorization(
|
||||
ToolCallAuthorization {
|
||||
tool_call: AgentResponseEventStream::initial_tool_call(
|
||||
&self.tool_use_id,
|
||||
title,
|
||||
self.kind.clone(),
|
||||
self.input.clone(),
|
||||
),
|
||||
options: vec![
|
||||
acp::PermissionOption {
|
||||
id: acp::PermissionOptionId("always_allow".into()),
|
||||
name: "Always Allow".into(),
|
||||
kind: acp::PermissionOptionKind::AllowAlways,
|
||||
},
|
||||
acp::PermissionOption {
|
||||
id: acp::PermissionOptionId("allow".into()),
|
||||
name: "Allow".into(),
|
||||
kind: acp::PermissionOptionKind::AllowOnce,
|
||||
},
|
||||
acp::PermissionOption {
|
||||
id: acp::PermissionOptionId("deny".into()),
|
||||
name: "Deny".into(),
|
||||
kind: acp::PermissionOptionKind::RejectOnce,
|
||||
},
|
||||
],
|
||||
response: response_tx,
|
||||
},
|
||||
)))
|
||||
.ok();
|
||||
async move {
|
||||
match response_rx.await?.0.as_ref() {
|
||||
"allow" | "always_allow" => Ok(()),
|
||||
_ => Err(anyhow!("Permission to run tool denied by user")),
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -1000,7 +1000,7 @@ pub struct ToolCallEventStreamReceiver(
|
|||
|
||||
#[cfg(test)]
|
||||
impl ToolCallEventStreamReceiver {
|
||||
pub async fn expect_tool_authorization(&mut self) -> ToolCallAuthorization {
|
||||
pub async fn expect_authorization(&mut self) -> ToolCallAuthorization {
|
||||
let event = self.0.next().await;
|
||||
if let Some(Ok(AgentResponseEvent::ToolCallAuthorization(auth))) = event {
|
||||
auth
|
||||
|
@ -1008,6 +1008,18 @@ impl ToolCallEventStreamReceiver {
|
|||
panic!("Expected ToolCallAuthorization but got: {:?}", event);
|
||||
}
|
||||
}
|
||||
|
||||
pub async fn expect_terminal(&mut self) -> Entity<acp_thread::Terminal> {
|
||||
let event = self.0.next().await;
|
||||
if let Some(Ok(AgentResponseEvent::ToolCallUpdate(
|
||||
acp_thread::ToolCallUpdate::UpdateTerminal(update),
|
||||
))) = event
|
||||
{
|
||||
update.terminal
|
||||
} else {
|
||||
panic!("Expected terminal but got: {:?}", event);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue