streaming: tool as first-class streaming role in chat log
This commit is contained in:
parent
bba14ddcde
commit
4b24b33377
|
|
@ -127,7 +127,8 @@ func (sess *Session) EnsureTrailingNewline() {
|
|||
// startEventLog subscribes to the agent's "event" bus topic and writes
|
||||
// all events to the session chat log.
|
||||
func (sess *Session) startEventLog() {
|
||||
streamingRole := "" // tracks current streaming role ("assistant" or "reasoning")
|
||||
streamingRole := "" // tracks current streaming role ("assistant", "reasoning", or "tool")
|
||||
|
||||
sess.Core.Bus().Subscribe("event", func(ev agent.Event) {
|
||||
switch ev.Role {
|
||||
case "assistant", "reasoning":
|
||||
|
|
@ -144,6 +145,40 @@ func (sess *Session) startEventLog() {
|
|||
streamingRole = ev.Role
|
||||
}
|
||||
sess.AppendLog(FormatEvent(ev))
|
||||
|
||||
case "tool":
|
||||
// Tool events can stream (multiple chunks with same name) or
|
||||
// arrive as a single final result. Write header on first chunk,
|
||||
// then append content. Duplicate final result is suppressed.
|
||||
if streamingRole == "tool" {
|
||||
// Continuation of streaming tool output.
|
||||
if ev.Content != "" {
|
||||
sess.AppendLog([]byte(ev.Content))
|
||||
} else {
|
||||
// Empty content = final result marker; streaming is done.
|
||||
sess.AppendLog([]byte("\n"))
|
||||
streamingRole = ""
|
||||
}
|
||||
return
|
||||
}
|
||||
if streamingRole != "" {
|
||||
sess.AppendLog([]byte("\n"))
|
||||
streamingRole = ""
|
||||
}
|
||||
// First tool event — write header and start streaming.
|
||||
sess.AppendLog([]byte("[tool:" + ev.Name + "]\n"))
|
||||
if ev.Content != "" {
|
||||
sess.AppendLog([]byte(ev.Content))
|
||||
}
|
||||
streamingRole = "tool"
|
||||
|
||||
case "call":
|
||||
if streamingRole != "" {
|
||||
sess.AppendLog([]byte("\n"))
|
||||
streamingRole = ""
|
||||
}
|
||||
sess.AppendLog(FormatEvent(ev))
|
||||
|
||||
default:
|
||||
if streamingRole != "" {
|
||||
sess.AppendLog([]byte("\n"))
|
||||
|
|
@ -1190,8 +1225,6 @@ func FormatEvent(ev agent.Event) []byte {
|
|||
return []byte("[stalled]\n")
|
||||
case "maxsteps":
|
||||
return []byte("[maxsteps]\n" + ev.Content + "\n")
|
||||
case "exec":
|
||||
return []byte("[exec]\n" + ev.Content + "\n")
|
||||
default:
|
||||
return nil
|
||||
}
|
||||
|
|
|
|||
Reference in New Issue