feat: 为 WebSocket 消息添加时间戳字段,确保消息的时间信息可用
This commit is contained in:
parent
02339465b6
commit
bf66c00950
@ -66,6 +66,7 @@ impl OutputAdapter for WebSocketOutputAdapter {
|
|||||||
outbounds.push(WsOutbound::Error {
|
outbounds.push(WsOutbound::Error {
|
||||||
code: error.code,
|
code: error.code,
|
||||||
message: error.message,
|
message: error.message,
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
});
|
});
|
||||||
return outbounds;
|
return outbounds;
|
||||||
}
|
}
|
||||||
@ -77,7 +78,7 @@ impl OutputAdapter for WebSocketOutputAdapter {
|
|||||||
id: response.request_id.to_string(),
|
id: response.request_id.to_string(),
|
||||||
content: msg.content.clone(),
|
content: msg.content.clone(),
|
||||||
role: "assistant".to_string(),
|
role: "assistant".to_string(),
|
||||||
attachments: Vec::new(), subagent_task_id: None,
|
attachments: Vec::new(), subagent_task_id: None, timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
},
|
},
|
||||||
MessageKind::Notification => {
|
MessageKind::Notification => {
|
||||||
// 根据元数据判断具体类型
|
// 根据元数据判断具体类型
|
||||||
@ -97,7 +98,7 @@ impl OutputAdapter for WebSocketOutputAdapter {
|
|||||||
id: response.request_id.to_string(),
|
id: response.request_id.to_string(),
|
||||||
content: msg.content.clone(),
|
content: msg.content.clone(),
|
||||||
role: "assistant".to_string(),
|
role: "assistant".to_string(),
|
||||||
attachments: Vec::new(), subagent_task_id: None,
|
attachments: Vec::new(), subagent_task_id: None, timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
} else if let Some(session_id) = response.metadata.get("session_id") {
|
} else if let Some(session_id) = response.metadata.get("session_id") {
|
||||||
@ -136,7 +137,7 @@ impl OutputAdapter for WebSocketOutputAdapter {
|
|||||||
id: response.request_id.to_string(),
|
id: response.request_id.to_string(),
|
||||||
content: msg.content.clone(),
|
content: msg.content.clone(),
|
||||||
role: "assistant".to_string(),
|
role: "assistant".to_string(),
|
||||||
attachments: Vec::new(), subagent_task_id: None,
|
attachments: Vec::new(), subagent_task_id: None, timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
} else if let Some(sessions_json) = response.metadata.get("sessions") {
|
} else if let Some(sessions_json) = response.metadata.get("sessions") {
|
||||||
@ -154,7 +155,7 @@ impl OutputAdapter for WebSocketOutputAdapter {
|
|||||||
id: response.request_id.to_string(),
|
id: response.request_id.to_string(),
|
||||||
content: msg.content.clone(),
|
content: msg.content.clone(),
|
||||||
role: "assistant".to_string(),
|
role: "assistant".to_string(),
|
||||||
attachments: Vec::new(), subagent_task_id: None,
|
attachments: Vec::new(), subagent_task_id: None, timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
} else if let Some(topics_json) = response.metadata.get("topics") {
|
} else if let Some(topics_json) = response.metadata.get("topics") {
|
||||||
@ -173,7 +174,7 @@ impl OutputAdapter for WebSocketOutputAdapter {
|
|||||||
id: response.request_id.to_string(),
|
id: response.request_id.to_string(),
|
||||||
content: msg.content.clone(),
|
content: msg.content.clone(),
|
||||||
role: "assistant".to_string(),
|
role: "assistant".to_string(),
|
||||||
attachments: Vec::new(), subagent_task_id: None,
|
attachments: Vec::new(), subagent_task_id: None, timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
@ -182,19 +183,20 @@ impl OutputAdapter for WebSocketOutputAdapter {
|
|||||||
id: response.request_id.to_string(),
|
id: response.request_id.to_string(),
|
||||||
content: msg.content.clone(),
|
content: msg.content.clone(),
|
||||||
role: "assistant".to_string(),
|
role: "assistant".to_string(),
|
||||||
attachments: Vec::new(), subagent_task_id: None,
|
attachments: Vec::new(), subagent_task_id: None, timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
MessageKind::Error => WsOutbound::Error {
|
MessageKind::Error => WsOutbound::Error {
|
||||||
code: "RESPONSE_ERROR".to_string(),
|
code: "RESPONSE_ERROR".to_string(),
|
||||||
message: msg.content.clone(),
|
message: msg.content.clone(),
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
},
|
},
|
||||||
_ => WsOutbound::AssistantResponse {
|
_ => WsOutbound::AssistantResponse {
|
||||||
id: response.request_id.to_string(),
|
id: response.request_id.to_string(),
|
||||||
content: msg.content.clone(),
|
content: msg.content.clone(),
|
||||||
role: "assistant".to_string(),
|
role: "assistant".to_string(),
|
||||||
attachments: Vec::new(), subagent_task_id: None,
|
attachments: Vec::new(), subagent_task_id: None, timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
},
|
},
|
||||||
};
|
};
|
||||||
outbounds.push(outbound);
|
outbounds.push(outbound);
|
||||||
|
|||||||
@ -235,6 +235,7 @@ async fn handle_socket(ws: WebSocket, state: Arc<GatewayState>) {
|
|||||||
tracing::warn!(error = %e, session_id = %current_session_id, "Failed to handle inbound message");
|
tracing::warn!(error = %e, session_id = %current_session_id, "Failed to handle inbound message");
|
||||||
let _ = sender
|
let _ = sender
|
||||||
.send(WsOutbound::Error {
|
.send(WsOutbound::Error {
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
code:"SESSION_ERROR".to_string(),
|
code:"SESSION_ERROR".to_string(),
|
||||||
message: e.to_string(),
|
message: e.to_string(),
|
||||||
})
|
})
|
||||||
@ -245,6 +246,7 @@ async fn handle_socket(ws: WebSocket, state: Arc<GatewayState>) {
|
|||||||
tracing::warn!(error = %e, "Failed to parse inbound message");
|
tracing::warn!(error = %e, "Failed to parse inbound message");
|
||||||
let _ = sender
|
let _ = sender
|
||||||
.send(WsOutbound::Error {
|
.send(WsOutbound::Error {
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
code:"PARSE_ERROR".to_string(),
|
code:"PARSE_ERROR".to_string(),
|
||||||
message: e.to_string(),
|
message: e.to_string(),
|
||||||
})
|
})
|
||||||
@ -334,6 +336,7 @@ async fn handle_inbound(
|
|||||||
// 不是命令,返回错误
|
// 不是命令,返回错误
|
||||||
let _ = sender
|
let _ = sender
|
||||||
.send(WsOutbound::Error {
|
.send(WsOutbound::Error {
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
code: "INVALID_COMMAND".to_string(),
|
code: "INVALID_COMMAND".to_string(),
|
||||||
message: "Invalid command payload".to_string(),
|
message: "Invalid command payload".to_string(),
|
||||||
})
|
})
|
||||||
@ -343,6 +346,7 @@ async fn handle_inbound(
|
|||||||
Err(e) => {
|
Err(e) => {
|
||||||
let _ = sender
|
let _ = sender
|
||||||
.send(WsOutbound::Error {
|
.send(WsOutbound::Error {
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
code: "PARSE_ERROR".to_string(),
|
code: "PARSE_ERROR".to_string(),
|
||||||
message: e.to_string(),
|
message: e.to_string(),
|
||||||
})
|
})
|
||||||
@ -707,6 +711,7 @@ fn chat_message_to_ws_outbound(msg: &crate::bus::ChatMessage) -> Option<WsOutbou
|
|||||||
content: format!("{}\nargs: {}", tool_call.name, tool_call.arguments),
|
content: format!("{}\nargs: {}", tool_call.name, tool_call.arguments),
|
||||||
role: msg.role.clone(),
|
role: msg.role.clone(),
|
||||||
subagent_task_id: None,
|
subagent_task_id: None,
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -717,6 +722,7 @@ fn chat_message_to_ws_outbound(msg: &crate::bus::ChatMessage) -> Option<WsOutbou
|
|||||||
role: msg.role.clone(),
|
role: msg.role.clone(),
|
||||||
attachments: Vec::new(),
|
attachments: Vec::new(),
|
||||||
subagent_task_id: None,
|
subagent_task_id: None,
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
"tool" => {
|
"tool" => {
|
||||||
@ -730,6 +736,7 @@ fn chat_message_to_ws_outbound(msg: &crate::bus::ChatMessage) -> Option<WsOutbou
|
|||||||
role: msg.role.clone(),
|
role: msg.role.clone(),
|
||||||
subagent_task_id: None,
|
subagent_task_id: None,
|
||||||
duration_ms: msg.tool_duration_ms,
|
duration_ms: msg.tool_duration_ms,
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
}),
|
}),
|
||||||
ToolMessageState::PendingUserAction => Some(WsOutbound::ToolPending {
|
ToolMessageState::PendingUserAction => Some(WsOutbound::ToolPending {
|
||||||
id: msg.id.clone(),
|
id: msg.id.clone(),
|
||||||
@ -739,6 +746,7 @@ fn chat_message_to_ws_outbound(msg: &crate::bus::ChatMessage) -> Option<WsOutbou
|
|||||||
role: msg.role.clone(),
|
role: msg.role.clone(),
|
||||||
resume_hint: "完成外部操作后,直接发一条继续消息即可。".to_string(),
|
resume_hint: "完成外部操作后,直接发一条继续消息即可。".to_string(),
|
||||||
subagent_task_id: None,
|
subagent_task_id: None,
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
}),
|
}),
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -748,6 +756,7 @@ fn chat_message_to_ws_outbound(msg: &crate::bus::ChatMessage) -> Option<WsOutbou
|
|||||||
role: msg.role.clone(),
|
role: msg.role.clone(),
|
||||||
attachments,
|
attachments,
|
||||||
subagent_task_id: None,
|
subagent_task_id: None,
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
}),
|
}),
|
||||||
_ => None,
|
_ => None,
|
||||||
}
|
}
|
||||||
|
|||||||
@ -2,6 +2,14 @@ pub mod ws_adapter;
|
|||||||
|
|
||||||
use serde::{Deserialize, Serialize};
|
use serde::{Deserialize, Serialize};
|
||||||
|
|
||||||
|
/// 当前时间戳(秒),用于填充消息的 timestamp 字段
|
||||||
|
pub fn now_timestamp() -> i64 {
|
||||||
|
std::time::SystemTime::now()
|
||||||
|
.duration_since(std::time::UNIX_EPOCH)
|
||||||
|
.unwrap_or_default()
|
||||||
|
.as_secs() as i64
|
||||||
|
}
|
||||||
|
|
||||||
#[derive(Debug, Clone, Serialize, Deserialize)]
|
#[derive(Debug, Clone, Serialize, Deserialize)]
|
||||||
pub struct SessionSummary {
|
pub struct SessionSummary {
|
||||||
pub session_id: String,
|
pub session_id: String,
|
||||||
@ -108,6 +116,8 @@ pub enum WsOutbound {
|
|||||||
attachments: Vec<MediaSummary>,
|
attachments: Vec<MediaSummary>,
|
||||||
#[serde(default, skip_serializing_if = "Option::is_none")]
|
#[serde(default, skip_serializing_if = "Option::is_none")]
|
||||||
subagent_task_id: Option<String>,
|
subagent_task_id: Option<String>,
|
||||||
|
#[serde(default, skip_serializing_if = "Option::is_none")]
|
||||||
|
timestamp: Option<i64>,
|
||||||
},
|
},
|
||||||
#[serde(rename = "tool_call")]
|
#[serde(rename = "tool_call")]
|
||||||
ToolCall {
|
ToolCall {
|
||||||
@ -119,6 +129,8 @@ pub enum WsOutbound {
|
|||||||
role: String,
|
role: String,
|
||||||
#[serde(default, skip_serializing_if = "Option::is_none")]
|
#[serde(default, skip_serializing_if = "Option::is_none")]
|
||||||
subagent_task_id: Option<String>,
|
subagent_task_id: Option<String>,
|
||||||
|
#[serde(default, skip_serializing_if = "Option::is_none")]
|
||||||
|
timestamp: Option<i64>,
|
||||||
},
|
},
|
||||||
#[serde(rename = "tool_result")]
|
#[serde(rename = "tool_result")]
|
||||||
ToolResult {
|
ToolResult {
|
||||||
@ -131,6 +143,8 @@ pub enum WsOutbound {
|
|||||||
subagent_task_id: Option<String>,
|
subagent_task_id: Option<String>,
|
||||||
#[serde(default, skip_serializing_if = "Option::is_none")]
|
#[serde(default, skip_serializing_if = "Option::is_none")]
|
||||||
duration_ms: Option<u64>,
|
duration_ms: Option<u64>,
|
||||||
|
#[serde(default, skip_serializing_if = "Option::is_none")]
|
||||||
|
timestamp: Option<i64>,
|
||||||
},
|
},
|
||||||
#[serde(rename = "tool_pending")]
|
#[serde(rename = "tool_pending")]
|
||||||
ToolPending {
|
ToolPending {
|
||||||
@ -142,9 +156,16 @@ pub enum WsOutbound {
|
|||||||
resume_hint: String,
|
resume_hint: String,
|
||||||
#[serde(default, skip_serializing_if = "Option::is_none")]
|
#[serde(default, skip_serializing_if = "Option::is_none")]
|
||||||
subagent_task_id: Option<String>,
|
subagent_task_id: Option<String>,
|
||||||
|
#[serde(default, skip_serializing_if = "Option::is_none")]
|
||||||
|
timestamp: Option<i64>,
|
||||||
},
|
},
|
||||||
#[serde(rename = "error")]
|
#[serde(rename = "error")]
|
||||||
Error { code: String, message: String },
|
Error {
|
||||||
|
code: String,
|
||||||
|
message: String,
|
||||||
|
#[serde(default, skip_serializing_if = "Option::is_none")]
|
||||||
|
timestamp: Option<i64>,
|
||||||
|
},
|
||||||
#[serde(rename = "task_started")]
|
#[serde(rename = "task_started")]
|
||||||
TaskStarted {
|
TaskStarted {
|
||||||
task_id: String,
|
task_id: String,
|
||||||
|
|||||||
@ -93,6 +93,7 @@ pub(crate) fn ws_outbound_from_outbound_message(message: &OutboundMessage) -> Ve
|
|||||||
role: message.role.clone(),
|
role: message.role.clone(),
|
||||||
attachments,
|
attachments,
|
||||||
subagent_task_id: message.metadata.get("subagent_task_id").cloned(),
|
subagent_task_id: message.metadata.get("subagent_task_id").cloned(),
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
}]
|
}]
|
||||||
}
|
}
|
||||||
OutboundEventKind::ToolCall => vec![WsOutbound::ToolCall {
|
OutboundEventKind::ToolCall => vec![WsOutbound::ToolCall {
|
||||||
@ -109,6 +110,7 @@ pub(crate) fn ws_outbound_from_outbound_message(message: &OutboundMessage) -> Ve
|
|||||||
content: message.content.clone(),
|
content: message.content.clone(),
|
||||||
role: message.role.clone(),
|
role: message.role.clone(),
|
||||||
subagent_task_id: message.metadata.get("subagent_task_id").cloned(),
|
subagent_task_id: message.metadata.get("subagent_task_id").cloned(),
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
}],
|
}],
|
||||||
OutboundEventKind::ToolResult => vec![WsOutbound::ToolResult {
|
OutboundEventKind::ToolResult => vec![WsOutbound::ToolResult {
|
||||||
id: message
|
id: message
|
||||||
@ -124,6 +126,7 @@ pub(crate) fn ws_outbound_from_outbound_message(message: &OutboundMessage) -> Ve
|
|||||||
.metadata
|
.metadata
|
||||||
.get("tool_duration_ms")
|
.get("tool_duration_ms")
|
||||||
.and_then(|v| v.parse().ok()),
|
.and_then(|v| v.parse().ok()),
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
}],
|
}],
|
||||||
OutboundEventKind::ToolPending => vec![WsOutbound::ToolPending {
|
OutboundEventKind::ToolPending => vec![WsOutbound::ToolPending {
|
||||||
id: message
|
id: message
|
||||||
@ -136,10 +139,12 @@ pub(crate) fn ws_outbound_from_outbound_message(message: &OutboundMessage) -> Ve
|
|||||||
role: message.role.clone(),
|
role: message.role.clone(),
|
||||||
resume_hint: TOOL_PENDING_RESUME_HINT.to_string(),
|
resume_hint: TOOL_PENDING_RESUME_HINT.to_string(),
|
||||||
subagent_task_id: message.metadata.get("subagent_task_id").cloned(),
|
subagent_task_id: message.metadata.get("subagent_task_id").cloned(),
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
}],
|
}],
|
||||||
OutboundEventKind::ErrorNotification => vec![WsOutbound::Error {
|
OutboundEventKind::ErrorNotification => vec![WsOutbound::Error {
|
||||||
code: "AGENT_ERROR".to_string(),
|
code: "AGENT_ERROR".to_string(),
|
||||||
message: message.content.clone(),
|
message: message.content.clone(),
|
||||||
|
timestamp: Some(crate::protocol::now_timestamp()),
|
||||||
}],
|
}],
|
||||||
OutboundEventKind::TaskStarted => vec![WsOutbound::TaskStarted {
|
OutboundEventKind::TaskStarted => vec![WsOutbound::TaskStarted {
|
||||||
task_id: message.metadata.get("task_id").cloned().unwrap_or_default(),
|
task_id: message.metadata.get("task_id").cloned().unwrap_or_default(),
|
||||||
|
|||||||
@ -168,7 +168,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: msg.id,
|
id: msg.id,
|
||||||
role: role as ChatMessage['role'],
|
role: role as ChatMessage['role'],
|
||||||
content: msg.content,
|
content: msg.content,
|
||||||
timestamp: Date.now(),
|
timestamp: (message as any).timestamp ?? Math.floor(Date.now() / 1000),
|
||||||
type: 'message',
|
type: 'message',
|
||||||
attachments: msg.attachments,
|
attachments: msg.attachments,
|
||||||
subagentTaskId: msg.subagent_task_id,
|
subagentTaskId: msg.subagent_task_id,
|
||||||
@ -180,7 +180,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: msg.id,
|
id: msg.id,
|
||||||
role: 'tool',
|
role: 'tool',
|
||||||
content: msg.content,
|
content: msg.content,
|
||||||
timestamp: Date.now(),
|
timestamp: (message as any).timestamp ?? Math.floor(Date.now() / 1000),
|
||||||
type: 'tool_call',
|
type: 'tool_call',
|
||||||
toolName: msg.tool_name,
|
toolName: msg.tool_name,
|
||||||
toolCallId: msg.tool_call_id,
|
toolCallId: msg.tool_call_id,
|
||||||
@ -194,7 +194,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: msg.id,
|
id: msg.id,
|
||||||
role: 'tool',
|
role: 'tool',
|
||||||
content: msg.content,
|
content: msg.content,
|
||||||
timestamp: Date.now(),
|
timestamp: (message as any).timestamp ?? Math.floor(Date.now() / 1000),
|
||||||
type: 'tool_result',
|
type: 'tool_result',
|
||||||
toolName: msg.tool_name,
|
toolName: msg.tool_name,
|
||||||
toolCallId: msg.tool_call_id,
|
toolCallId: msg.tool_call_id,
|
||||||
@ -208,7 +208,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: msg.id,
|
id: msg.id,
|
||||||
role: 'tool',
|
role: 'tool',
|
||||||
content: `${msg.content}\n\n${msg.resume_hint}`,
|
content: `${msg.content}\n\n${msg.resume_hint}`,
|
||||||
timestamp: Date.now(),
|
timestamp: (message as any).timestamp ?? Math.floor(Date.now() / 1000),
|
||||||
type: 'tool_pending',
|
type: 'tool_pending',
|
||||||
toolName: msg.tool_name,
|
toolName: msg.tool_name,
|
||||||
toolCallId: msg.tool_call_id,
|
toolCallId: msg.tool_call_id,
|
||||||
@ -220,7 +220,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: generateMessageId(),
|
id: generateMessageId(),
|
||||||
role: 'assistant',
|
role: 'assistant',
|
||||||
content: `Error: ${message.message}`,
|
content: `Error: ${message.message}`,
|
||||||
timestamp: Date.now(),
|
timestamp: (message as any).timestamp ?? Math.floor(Date.now() / 1000),
|
||||||
type: 'message',
|
type: 'message',
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -394,7 +394,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: msg.id,
|
id: msg.id,
|
||||||
role,
|
role,
|
||||||
content: msg.content,
|
content: msg.content,
|
||||||
timestamp: Date.now(),
|
timestamp: (message as any).timestamp ?? Math.floor(Date.now() / 1000),
|
||||||
type: 'message',
|
type: 'message',
|
||||||
attachments: msg.attachments,
|
attachments: msg.attachments,
|
||||||
},
|
},
|
||||||
@ -411,7 +411,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: msg.id,
|
id: msg.id,
|
||||||
role: 'tool',
|
role: 'tool',
|
||||||
content: msg.content,
|
content: msg.content,
|
||||||
timestamp: Date.now(),
|
timestamp: (message as any).timestamp ?? Math.floor(Date.now() / 1000),
|
||||||
type: 'tool_call',
|
type: 'tool_call',
|
||||||
toolName: msg.tool_name,
|
toolName: msg.tool_name,
|
||||||
toolCallId: msg.tool_call_id,
|
toolCallId: msg.tool_call_id,
|
||||||
@ -430,7 +430,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: msg.id,
|
id: msg.id,
|
||||||
role: 'tool',
|
role: 'tool',
|
||||||
content: msg.content,
|
content: msg.content,
|
||||||
timestamp: Date.now(),
|
timestamp: (message as any).timestamp ?? Math.floor(Date.now() / 1000),
|
||||||
type: 'tool_result',
|
type: 'tool_result',
|
||||||
toolName: msg.tool_name,
|
toolName: msg.tool_name,
|
||||||
toolCallId: msg.tool_call_id,
|
toolCallId: msg.tool_call_id,
|
||||||
@ -449,7 +449,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: msg.id,
|
id: msg.id,
|
||||||
role: 'tool',
|
role: 'tool',
|
||||||
content: `${msg.content}\n\n${msg.resume_hint}`,
|
content: `${msg.content}\n\n${msg.resume_hint}`,
|
||||||
timestamp: Date.now(),
|
timestamp: (message as any).timestamp ?? Math.floor(Date.now() / 1000),
|
||||||
type: 'tool_pending',
|
type: 'tool_pending',
|
||||||
toolName: msg.tool_name,
|
toolName: msg.tool_name,
|
||||||
toolCallId: msg.tool_call_id,
|
toolCallId: msg.tool_call_id,
|
||||||
@ -465,7 +465,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: generateMessageId(),
|
id: generateMessageId(),
|
||||||
role: 'assistant',
|
role: 'assistant',
|
||||||
content: (message as { type: 'execution_cancelled'; message: string }).message,
|
content: (message as { type: 'execution_cancelled'; message: string }).message,
|
||||||
timestamp: Date.now(),
|
timestamp: (message as any).timestamp ?? Math.floor(Date.now() / 1000),
|
||||||
type: 'message',
|
type: 'message',
|
||||||
},
|
},
|
||||||
])
|
])
|
||||||
@ -480,7 +480,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: generateMessageId(),
|
id: generateMessageId(),
|
||||||
role: 'assistant',
|
role: 'assistant',
|
||||||
content: `Error: ${message.message}`,
|
content: `Error: ${message.message}`,
|
||||||
timestamp: Date.now(),
|
timestamp: (message as any).timestamp ?? Math.floor(Date.now() / 1000),
|
||||||
type: 'message',
|
type: 'message',
|
||||||
},
|
},
|
||||||
])
|
])
|
||||||
@ -513,7 +513,7 @@ export function useChat(): UseChatReturn {
|
|||||||
id: generateMessageId(),
|
id: generateMessageId(),
|
||||||
role: 'user',
|
role: 'user',
|
||||||
content,
|
content,
|
||||||
timestamp: Date.now(),
|
timestamp: Math.floor(Date.now() / 1000),
|
||||||
type: 'message',
|
type: 'message',
|
||||||
attachments: attachments || [],
|
attachments: attachments || [],
|
||||||
},
|
},
|
||||||
|
|||||||
@ -43,6 +43,7 @@ export interface AssistantResponse {
|
|||||||
role: string
|
role: string
|
||||||
attachments?: Attachment[]
|
attachments?: Attachment[]
|
||||||
subagent_task_id?: string
|
subagent_task_id?: string
|
||||||
|
timestamp?: number
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ToolCall {
|
export interface ToolCall {
|
||||||
@ -54,6 +55,7 @@ export interface ToolCall {
|
|||||||
content: string
|
content: string
|
||||||
role: string
|
role: string
|
||||||
subagent_task_id?: string
|
subagent_task_id?: string
|
||||||
|
timestamp?: number
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ToolResult {
|
export interface ToolResult {
|
||||||
@ -65,6 +67,7 @@ export interface ToolResult {
|
|||||||
role: string
|
role: string
|
||||||
subagent_task_id?: string
|
subagent_task_id?: string
|
||||||
duration_ms?: number
|
duration_ms?: number
|
||||||
|
timestamp?: number
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface ToolPending {
|
export interface ToolPending {
|
||||||
@ -76,12 +79,14 @@ export interface ToolPending {
|
|||||||
role: string
|
role: string
|
||||||
resume_hint: string
|
resume_hint: string
|
||||||
subagent_task_id?: string
|
subagent_task_id?: string
|
||||||
|
timestamp?: number
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface WsError {
|
export interface WsError {
|
||||||
type: 'error'
|
type: 'error'
|
||||||
code: string
|
code: string
|
||||||
message: string
|
message: string
|
||||||
|
timestamp?: number
|
||||||
}
|
}
|
||||||
|
|
||||||
export interface TaskStarted {
|
export interface TaskStarted {
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user