fix(codex): dernier agent_message = Final (bootstrap canal)
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@ -219,22 +219,40 @@ impl AgentSession for CodexExecSession {
|
||||
|
||||
let mut events = Vec::new();
|
||||
let mut captured_id = None;
|
||||
'lines: for line in &raw_lines {
|
||||
// Fix canal (B2, bootstrap) : un tour `codex exec` peut émettre PLUSIEURS
|
||||
// `agent_message` — un préambule (« je vais… ») puis la conclusion. On ne coupe
|
||||
// donc plus au premier : on retient le **dernier** `agent_message` comme unique
|
||||
// `Final` terminal (la conclusion du tour), et on dégrade les précédents en
|
||||
// activité non terminale (readiness préservée). Ainsi le demandeur reçoit la
|
||||
// conclusion, pas le préambule. Absence d'`agent_message` ⇒ aucun `Final`
|
||||
// (no-reply inchangé).
|
||||
let mut last_final: Option<String> = None;
|
||||
for line in &raw_lines {
|
||||
let parsed = parse_event(line)?;
|
||||
if let Some(id) = parsed.conversation_id {
|
||||
captured_id = Some(id);
|
||||
}
|
||||
// Le `Final` est **terminal** (contrat de port) : on arrête d'émettre dès
|
||||
// qu'on l'a vu, pour qu'aucun heartbeat de fin (`turn.completed` postérieur)
|
||||
// ne le suive dans le flux.
|
||||
for event in parsed.events {
|
||||
let is_final = matches!(event, ReplyEvent::Final { .. });
|
||||
events.push(event);
|
||||
if is_final {
|
||||
break 'lines;
|
||||
match event {
|
||||
ReplyEvent::Final { content } => {
|
||||
// Un `agent_message` précédemment retenu est supersédé : il devient
|
||||
// une activité non terminale, on garde le plus récent en conclusion.
|
||||
if last_final.is_some() {
|
||||
events.push(ReplyEvent::ToolActivity {
|
||||
label: "agent_message".to_owned(),
|
||||
});
|
||||
}
|
||||
last_final = Some(content);
|
||||
}
|
||||
other => events.push(other),
|
||||
}
|
||||
}
|
||||
}
|
||||
// Le dernier `agent_message` retenu est le seul `Final` terminal, émis en fin de
|
||||
// flux (après les heartbeats/activités du tour).
|
||||
if let Some(content) = last_final {
|
||||
events.push(ReplyEvent::Final { content });
|
||||
}
|
||||
if let Some(id) = captured_id {
|
||||
*self.conversation_id.lock().expect("mutex sain") = Some(id);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user