mirror of
https://github.com/openai/codex.git
synced 2026-11-08 20:40:33 +00:00
## Why Memory summaries should preserve task history and the scope of user corrections and preferences without turning task-specific instructions into general claims about the user. ## What changed - Give memory v2 dedicated extraction prompts that emphasize chronological task history, evidence provenance, and uncertainty, with working directory and branch hints. - Require only `rollout_summary` and `rollout_slug` for v2, store an empty raw memory, and redact secrets before truncating summaries with a 9,000-byte budget. - Split v2 input into memory context messages while preserving the v1 prompts and output contract. ## Testing Extend startup tests to check v2 output storage, schema, branch hints, and redaction before truncation. Verify that budgeted input preserves human and agent evidence in order, omits media payloads and lower-priority noise, and keeps message chunks bounded. GitOrigin-RevId: 89e1c797450bd8f8e192fbe7161b5159bff8f931
84 lines
2.7 KiB
Rust
84 lines
2.7 KiB
Rust
//! Version-specific extraction contracts; v2 never decodes raw memory.
|
|
|
|
use codex_protocol::MemoryVersion;
|
|
use codex_secrets::redact_secrets;
|
|
use codex_utils_output_truncation::TruncationPolicy;
|
|
use codex_utils_output_truncation::truncate_text;
|
|
use serde::Deserialize;
|
|
use serde_json::Value;
|
|
use serde_json::json;
|
|
|
|
pub(crate) struct StageOneOutput {
|
|
pub(crate) raw_memory: Option<String>,
|
|
pub(crate) rollout_summary: String,
|
|
pub(crate) rollout_slug: Option<String>,
|
|
}
|
|
|
|
#[derive(Deserialize)]
|
|
#[serde(deny_unknown_fields)]
|
|
struct LegacyOutput {
|
|
raw_memory: String,
|
|
rollout_summary: String,
|
|
#[serde(default)]
|
|
rollout_slug: Option<String>,
|
|
}
|
|
|
|
#[derive(Deserialize)]
|
|
#[serde(deny_unknown_fields)]
|
|
struct SummaryOutput {
|
|
rollout_summary: String,
|
|
rollout_slug: String,
|
|
}
|
|
|
|
impl StageOneOutput {
|
|
pub(crate) fn parse(source: &str, version: MemoryVersion) -> serde_json::Result<Self> {
|
|
let (raw_memory, rollout_summary, rollout_slug) = match version {
|
|
MemoryVersion::V1 => {
|
|
let output: LegacyOutput = serde_json::from_str(source)?;
|
|
(
|
|
Some(output.raw_memory),
|
|
output.rollout_summary,
|
|
output.rollout_slug,
|
|
)
|
|
}
|
|
MemoryVersion::V2 => {
|
|
let output: SummaryOutput = serde_json::from_str(source)?;
|
|
(None, output.rollout_summary, Some(output.rollout_slug))
|
|
}
|
|
};
|
|
let mut rollout_summary = redact_secrets(rollout_summary);
|
|
if version == MemoryVersion::V2 {
|
|
rollout_summary = truncate_text(&rollout_summary, TruncationPolicy::Bytes(9_000));
|
|
}
|
|
Ok(Self {
|
|
raw_memory: raw_memory.map(redact_secrets),
|
|
rollout_summary,
|
|
rollout_slug: rollout_slug.map(redact_secrets),
|
|
})
|
|
}
|
|
}
|
|
|
|
pub(crate) fn output_schema(version: MemoryVersion) -> Value {
|
|
match version {
|
|
MemoryVersion::V1 => json!({
|
|
"type": "object",
|
|
"properties": {
|
|
"rollout_summary": { "type": "string" },
|
|
"rollout_slug": { "type": ["string", "null"] },
|
|
"raw_memory": { "type": "string" }
|
|
},
|
|
"required": ["rollout_summary", "rollout_slug", "raw_memory"],
|
|
"additionalProperties": false
|
|
}),
|
|
MemoryVersion::V2 => json!({
|
|
"type": "object",
|
|
"properties": {
|
|
"rollout_summary": { "type": "string" },
|
|
"rollout_slug": { "type": "string" }
|
|
},
|
|
"required": ["rollout_summary", "rollout_slug"],
|
|
"additionalProperties": false
|
|
}),
|
|
}
|
|
}
|