mirror of
https://github.com/openai/codex.git
synced 2026-10-19 17:28:46 +00:00
Preserve turn attribution across recovery and compaction (#51402)
## Why Recovering an interrupted turn replaced its original trigger with `retry` and restored only its root lineage from model context. Turns suspended before that context was written could lose their attribution entirely. ## What changed - Persist regular-turn attribution in `TurnStartedEvent` and compaction resume metadata, including the trigger, parent and root turn IDs, and initiating agent path. - Restore matching attribution during recovery, keep unknown triggers absent, and retain the model-context root fallback for older records. - Reconstruct attribution from surviving turns across rollback and late completion or abort events, and clear inherited attribution when spawning a forked agent. ## Testing Add coverage for repeated cold recovery, suspension before context persistence, legacy rollouts, fresh attribution on subsequent turns, compaction checkpoints, rollback, and late terminal events. GitOrigin-RevId: 85b5763e8fbd48a1ea2c07cfda8196e63c2cd33a
This commit is contained in:
@@ -1164,6 +1164,7 @@ mod tests {
|
||||
live_thread
|
||||
.append_items(&[RolloutItem::EventMsg(EventMsg::TurnStarted(
|
||||
TurnStartedEvent {
|
||||
turn_attribution: None,
|
||||
turn_id: "turn-1".to_string(),
|
||||
root_turn_id: None,
|
||||
trace_id: None,
|
||||
|
||||
@@ -219,6 +219,7 @@ async fn fork_version_stops_before_older_segments_once_resolved() {
|
||||
compacted.resume_metadata = Some(codex_rollout::CompactionResumeMetadata {
|
||||
multi_agent_version: Some(MultiAgentVersion::V2),
|
||||
last_started_turn_id: None,
|
||||
turn_attribution: None,
|
||||
previous_turn_settings: None,
|
||||
});
|
||||
append_items(
|
||||
@@ -616,6 +617,7 @@ fn append_items(path: &Path, items: impl IntoIterator<Item = RolloutItem>) {
|
||||
|
||||
fn turn_started(turn_id: &str) -> RolloutItem {
|
||||
RolloutItem::EventMsg(EventMsg::TurnStarted(TurnStartedEvent {
|
||||
turn_attribution: None,
|
||||
turn_id: turn_id.to_string(),
|
||||
root_turn_id: None,
|
||||
trace_id: None,
|
||||
|
||||
@@ -321,6 +321,7 @@ async fn turn_ids(store: &LocalThreadStore, thread_id: ThreadId) -> Vec<String>
|
||||
|
||||
fn turn_started(turn_id: &str) -> RolloutItem {
|
||||
RolloutItem::EventMsg(EventMsg::TurnStarted(TurnStartedEvent {
|
||||
turn_attribution: None,
|
||||
turn_id: turn_id.to_string(),
|
||||
root_turn_id: None,
|
||||
trace_id: None,
|
||||
|
||||
@@ -345,6 +345,7 @@ impl LegacyRolloutCanonicalizer {
|
||||
writer,
|
||||
timestamp,
|
||||
RolloutItem::EventMsg(EventMsg::TurnStarted(TurnStartedEvent {
|
||||
turn_attribution: None,
|
||||
turn_id,
|
||||
root_turn_id: None,
|
||||
trace_id: None,
|
||||
|
||||
@@ -227,6 +227,7 @@ fn item_completed(turn_id: &str, item_id: &str) -> RolloutItem {
|
||||
|
||||
fn started(turn_id: &str) -> RolloutItem {
|
||||
RolloutItem::EventMsg(EventMsg::TurnStarted(TurnStartedEvent {
|
||||
turn_attribution: None,
|
||||
turn_id: turn_id.to_string(),
|
||||
root_turn_id: None,
|
||||
trace_id: None,
|
||||
|
||||
@@ -2832,6 +2832,7 @@ async fn create_paginated_subagent_thread(
|
||||
|
||||
fn turn_started(turn_id: &str) -> RolloutItem {
|
||||
RolloutItem::EventMsg(EventMsg::TurnStarted(TurnStartedEvent {
|
||||
turn_attribution: None,
|
||||
turn_id: turn_id.to_string(),
|
||||
root_turn_id: None,
|
||||
trace_id: None,
|
||||
|
||||
@@ -712,6 +712,7 @@ mod tests {
|
||||
let update = sync
|
||||
.observe_appended_items(&[RolloutItem::EventMsg(EventMsg::TurnStarted(
|
||||
TurnStartedEvent {
|
||||
turn_attribution: None,
|
||||
turn_id: "turn-1".to_string(),
|
||||
root_turn_id: None,
|
||||
trace_id: None,
|
||||
|
||||
Reference in New Issue
Block a user