mirror of
https://github.com/openai/codex.git
synced 2026-10-27 18:48:37 +00:00
## Why Detached launches truncate stderr logs, losing details from previous failures. Updater handoffs can also leave existing writers with stale offsets after truncation. ## What changed - Record daemon lifecycle and update stages with timings, outcomes, and typed OS errors, omitting error messages and context. - Preserve the last 256 KiB of nonempty stderr logs before truncation and use append handles to prevent gaps during handoff. Preservation failures do not block launch. - Attach current and previous updater log tails when log inclusion is enabled for a report, with a 512 KiB total limit and legacy filename fallback. Skip missing, empty, and nonregular files. ## Testing Add regression coverage for diagnostic error redaction, bounded log preservation, append behavior during handoff, attachment selection, and updater logs in captured report uploads. GitOrigin-RevId: 918317022ab9dcfd1b13d676872706c77e9ffbb2
56 lines
1.8 KiB
Rust
56 lines
1.8 KiB
Rust
use super::*;
|
|
use codex_protocol::ThreadId;
|
|
use pretty_assertions::assert_eq;
|
|
|
|
#[test]
|
|
fn collects_bounded_tails_and_skips_missing_empty_and_nonregular_files() -> io::Result<()> {
|
|
let home = std::env::temp_dir().join(format!("codex-feedback-daemon-{}", ThreadId::new()));
|
|
let directory = home.join("app-server-daemon");
|
|
assert!(daemon_log_attachments(&home).is_empty());
|
|
fs::create_dir_all(&directory)?;
|
|
let bytes = vec![b'x'; MAX_LOG_BYTES as usize + 100];
|
|
fs::write(directory.join("daemon.stderr.log"), b"already included")?;
|
|
fs::write(directory.join("daemon-updater.stderr.log"), &bytes)?;
|
|
fs::write(
|
|
directory.join("daemon.stderr.log.previous"),
|
|
b"failed restart",
|
|
)?;
|
|
fs::write(
|
|
directory.join("app-server-updater.stderr.log"),
|
|
b"legacy updater",
|
|
)?;
|
|
fs::write(
|
|
directory.join("app-server-updater.stderr.log.previous"),
|
|
b"previous updater",
|
|
)?;
|
|
fs::create_dir(directory.join("app-server.stderr.log.previous"))?;
|
|
let attachments = daemon_log_attachments(&home);
|
|
let actual: Vec<_> = attachments
|
|
.into_iter()
|
|
.map(|attachment| {
|
|
(
|
|
attachment.filename,
|
|
attachment.content_type,
|
|
attachment.buffer,
|
|
)
|
|
})
|
|
.collect();
|
|
assert_eq!(
|
|
actual,
|
|
vec![
|
|
(
|
|
"daemon-updater.stderr.log".to_string(),
|
|
Some("text/plain".to_string()),
|
|
bytes[100..].to_vec()
|
|
),
|
|
(
|
|
"app-server-updater.stderr.log.previous".to_string(),
|
|
Some("text/plain".to_string()),
|
|
b"previous updater".to_vec()
|
|
),
|
|
]
|
|
);
|
|
fs::remove_dir_all(home)?;
|
|
Ok(())
|
|
}
|