[codex-analytics] add session source to client metadata (#17374)

## Summary

Adds `thread_source` field to the existing Codex turn metadata sent to
Responses API
- Sends `thread_source: "user"` for user-initiated sessions: CLI, VS
Code, and Exec
- Sends `thread_source: "subagent"` for subagent sessions
- Omits `thread_source` for MCP, custom, and unknown session sources
- Uses the existing turn metadata transport:
  - HTTP requests send through the `x-codex-turn-metadata` header
- WebSocket `response.create` requests send through
`client_metadata["x-codex-turn-metadata"]`

## Testing
- `cargo test -p codex-protocol
session_source_thread_source_name_classifies_user_and_subagent_sources`
- `cargo test -p codex-core turn_metadata_state`
- `cargo test -p codex-core --test responses_headers
responses_stream_includes_turn_metadata_header_for_git_workspace_e2e --
--nocapture`
This commit is contained in:
marksteinbrick-oai
2026-04-14 08:55:12 -07:00
committed by GitHub
parent f030ab62eb
commit 61fe23159e
8 changed files with 94 additions and 13 deletions

View File

@@ -437,6 +437,12 @@ async fn responses_stream_includes_turn_metadata_header_for_git_workspace_e2e()
.and_then(serde_json::Value::as_str),
Some("none")
);
assert_eq!(
initial_parsed
.get("thread_source")
.and_then(serde_json::Value::as_str),
Some("user")
);
let git_config_global = cwd.join("empty-git-config");
std::fs::write(&git_config_global, "").expect("write empty git config");
@@ -528,6 +534,18 @@ async fn responses_stream_includes_turn_metadata_header_for_git_workspace_e2e()
.get("turn_id")
.and_then(serde_json::Value::as_str)
.expect("second turn_id should be present");
assert_eq!(
first_parsed
.get("thread_source")
.and_then(serde_json::Value::as_str),
Some("user")
);
assert_eq!(
second_parsed
.get("thread_source")
.and_then(serde_json::Value::as_str),
Some("user")
);
assert_eq!(
first_turn_id, second_turn_id,
"requests should share turn_id"