supercode-cli 0.4.6

supercode — a lightweight, fully-customizable AI coding agent CLI in Rust. Any model via OpenRouter; natively continues Claude Code and Codex sessions.
//! CLI-level acceptance test for TR-2 dev/05 (SPEC.md TR-2.md): a
//! retry-heavy fixture (the same failing-test output repeated) minted
//! through `resume --reduced`, then inspected through `sessions
//! show-reductions` (C4) — the "measured demo" + "inspect stats (C7
//! surface) attributes them under the new kind" acceptance criterion.
//!
//! Follows the `reductions_cli.rs` idiom exactly: spawn the built
//! `supercode` binary against an unreachable `--base-url`, fully offline.

use std::path::{Path, PathBuf};
use std::process::{Command, Output};

fn bin() -> PathBuf {
    PathBuf::from(env!("CARGO_BIN_EXE_supercode"))
}

fn fresh_home(tag: &str) -> PathBuf {
    let nanos = std::time::SystemTime::now()
        .duration_since(std::time::UNIX_EPOCH)
        .unwrap()
        .as_nanos();
    let dir = std::env::temp_dir().join(format!(
        "supercode-tr2-{tag}-{}-{nanos}",
        std::process::id()
    ));
    std::fs::create_dir_all(&dir).unwrap();
    dir
}

fn run(home: &Path, extra: &[&str]) -> Output {
    let mut args = vec!["--api-key", "x", "--base-url", "http://127.0.0.1:1"];
    args.extend_from_slice(extra);
    Command::new(bin())
        .env("SUPERCODE_HOME", home)
        .env_remove("OPENROUTER_API_KEY")
        .env_remove("OPENAI_API_KEY")
        .env_remove("ANTHROPIC_API_KEY")
        .args(&args)
        .stdin(std::process::Stdio::null())
        .stdout(std::process::Stdio::piped())
        .stderr(std::process::Stdio::piped())
        .output()
        .expect("failed to spawn the supercode binary")
}

fn stdout(out: &Output) -> String {
    String::from_utf8_lossy(&out.stdout).into_owned()
}
fn stderr(out: &Output) -> String {
    String::from_utf8_lossy(&out.stderr).into_owned()
}

/// A "retry-heavy" Claude Code session JSONL: the SAME `cargo test` failure
/// output repeated across 6 `bash` tool results (identical content, distinct
/// `tool_use_id`s) — TR-2.md dev/05's fixture shape ("same failing test
/// output x5"). Each output is 2,000 bytes: comfortably over the 256B TR-2
/// savings floor, comfortably under the 8,192B default A7 trigger, so the
/// savings this test measures are attributable to TR-2 alone. With the
/// default `protect_last_n_tool_results = 3`, the OLDEST 3 (of 6) occurrences
/// are eligible for dedup: the very first stays canonical (full), the next
/// two become `DuplicateOutput` stubs; the newest 3 stay full (protected).
/// Returns `(path, duplicated_output_len)` — the exact byte length of the
/// repeated failure output, so callers can assert the CLI's byte figures
/// EXACTLY rather than merely checking kind presence.
fn write_retry_fixture(dir: &Path) -> (PathBuf, usize) {
    let sid = "77777777-8888-9999-aaaa-bbbbbbbbbbbb";
    let mut lines: Vec<String> = Vec::new();
    lines.push(
        serde_json::json!({
            "type": "user",
            "message": {"role": "user", "content": "why does cargo test keep failing?"},
            "uuid": "u0", "parentUuid": null,
            "timestamp": "2026-07-07T18:38:00.000Z", "sessionId": sid,
            "cwd": "/tmp/proj", "userType": "external",
        })
        .to_string(),
    );
    let failure = format!(
        "running 1 test\ntest it_works ... FAILED\n\n{}\ntest result: FAILED. 0 passed; 1 failed\n",
        "assertion failed: left == right\n".repeat(60)
    );
    assert!(failure.len() > 256 && failure.len() < 8192);
    for i in 0..6 {
        let tool_id = format!("toolu_{i:02}");
        lines.push(
            serde_json::json!({
                "type": "assistant",
                "message": {"role": "assistant", "content": [
                    {"type": "tool_use", "id": tool_id, "name": "bash", "input": {"command": "cargo test"}}
                ]},
                "uuid": format!("a{i}"),
                "parentUuid": if i == 0 { "u0".to_string() } else { format!("t{}", i - 1) },
                "timestamp": "2026-07-07T18:38:01.000Z", "sessionId": sid,
            })
            .to_string(),
        );
        lines.push(
            serde_json::json!({
                "type": "user",
                "message": {"role": "user", "content": [
                    {"tool_use_id": tool_id, "type": "tool_result", "content": [{"type": "text", "text": failure}]}
                ]},
                "uuid": format!("t{i}"), "parentUuid": format!("a{i}"),
                "timestamp": "2026-07-07T18:38:02.000Z", "sessionId": sid,
                "toolUseResult": {"status": "completed"},
            })
            .to_string(),
        );
    }
    let path = dir.join("retry_heavy_session.jsonl");
    std::fs::write(&path, lines.join("\n") + "\n").unwrap();
    (path, failure.len())
}

/// Render `n` with `,` thousands separators — mirrors the CLI's own
/// `commas`/`format_commas` so byte-figure assertions can be exact.
fn commas(n: usize) -> String {
    let digits = n.to_string();
    let mut out = String::new();
    for (i, b) in digits.bytes().enumerate() {
        if i > 0 && (digits.len() - i) % 3 == 0 {
            out.push(',');
        }
        out.push(b as char);
    }
    out
}

fn mint_reduced_session(home: &Path, fixture: &Path) -> String {
    let out = run(home, &["resume", fixture.to_str().unwrap(), "--reduced"]);
    let err = stderr(&out);
    let line = err
        .lines()
        .find(|l| l.contains("full copy:"))
        .unwrap_or_else(|| panic!("no `full copy:` line in:\n{err}"));
    let sidecar_path = line.split("full copy:").nth(1).unwrap().trim();
    Path::new(sidecar_path)
        .file_name()
        .unwrap()
        .to_str()
        .unwrap()
        .strip_suffix(".sidecar.jsonl")
        .unwrap()
        .to_string()
}

#[test]
fn retry_heavy_fixture_shows_duplicate_savings_attributed_under_the_new_kind() {
    let home = fresh_home("retry-heavy");
    let (fixture, dup_len) = write_retry_fixture(&home);
    let name = mint_reduced_session(&home, &fixture);

    // ---- JSON surface: the persisted log carries exactly 2 DuplicateOutput
    // records (dev/01-style count, applied to a real 6-occurrence fixture),
    // each with the fixture's EXACT duplicated-output byte length. ----
    let json_out = run(&home, &["sessions", "show-reductions", &name, "--json"]);
    assert!(
        json_out.status.success(),
        "show-reductions --json must succeed: {}",
        stderr(&json_out)
    );
    let log: serde_json::Value = serde_json::from_str(&stdout(&json_out)).unwrap();
    let reductions = log["reductions"].as_array().unwrap();
    let dup_rows: Vec<&serde_json::Value> = reductions
        .iter()
        .filter(|r| r["kind"].get("DuplicateOutput").is_some())
        .collect();
    assert_eq!(
        dup_rows.len(),
        2,
        "expected exactly 2 DuplicateOutput records (oldest 3 minus 1 canonical, \
         newest 3 protected): {reductions:#?}"
    );
    for row in &dup_rows {
        assert_eq!(
            row["kind"]["DuplicateOutput"]["original_bytes"]
                .as_u64()
                .unwrap(),
            dup_len as u64,
            "each record's byte figure must equal the fixture's duplicated \
             output length exactly: {row:#?}"
        );
    }
    // No other kind fired (all 6 outputs are well under the A7 trigger).
    assert_eq!(
        reductions.len(),
        dup_rows.len(),
        "only DuplicateOutput should have fired on this fixture: {reductions:#?}"
    );

    // ---- Table surface (C4 `show-reductions`): each record renders under
    // the `duplicate` stub kind with the EXACT byte figure, and the header's
    // view% shows real savings. ----
    let table_out = run(&home, &["sessions", "show-reductions", &name]);
    assert!(table_out.status.success());
    let table = stdout(&table_out);
    // The kind column renders the `duplicate` stub token, and the byte
    // column the exact (comma-formatted) duplicated-output length, for
    // exactly the two records.
    let duplicate_kind_rows = table
        .lines()
        .filter(|l| l.contains("duplicate") && l.contains(&format!("{} B", commas(dup_len))))
        .count();
    assert_eq!(
        duplicate_kind_rows,
        dup_rows.len(),
        "both records must render under the `duplicate` kind with {} B:\n{table}",
        commas(dup_len)
    );
    // The header reports a view percentage strictly under 100 -- real
    // savings, not just a record count.
    let header = table
        .lines()
        .find(|l| l.contains("reductions ·"))
        .expect("must have the reductions header line");
    assert!(
        header.contains("%)"),
        "header must report a view percentage: {header}"
    );
    assert!(
        !header.contains("(100%)"),
        "duplicate savings must move the view percentage below 100%: {header}"
    );

    // ---- inspect stats (C7 surface, dev/05's second clause): the stats
    // panel attributes the savings under the new kind using the same durable
    // marginal accounting as the JSON log. The raw original-byte figure was
    // already checked above; this surface must report actual serialized-view
    // savings after placeholder overhead, not the larger gross input claim.
    let attribution = log["attribution"].as_object().unwrap();
    let duplicate_attribution = attribution["passes"]
        .as_array()
        .unwrap()
        .iter()
        .find(|row| row["kind"] == "duplicate")
        .expect("durable attribution must contain the duplicate pass");
    assert_eq!(duplicate_attribution["candidate_count"], 2);
    assert_eq!(duplicate_attribution["applied_count"], 2);
    assert_eq!(duplicate_attribution["suppressed_by_later_pass_count"], 0);
    assert_eq!(
        duplicate_attribution["marginal_saved_bytes"], attribution["aggregate_saved_bytes"],
        "with no other pass applied, duplicate marginal savings are the aggregate"
    );
    assert_eq!(
        duplicate_attribution["retained_bytes"], attribution["view_bytes"],
        "with no later pass, duplicate retained bytes are the final view bytes"
    );
    let insp = run(&home, &["inspect", &name]);
    assert!(
        insp.status.success(),
        "inspect must succeed: {}",
        stderr(&insp)
    );
    let insp_text = stdout(&insp);
    let duplicate_stat_line = insp_text
        .lines()
        .find(|l| l.contains("· duplicate"))
        .unwrap_or_else(|| panic!("inspect stats must have a `· duplicate` line:\n{insp_text}"));
    let marginal_saved_bytes = duplicate_attribution["marginal_saved_bytes"]
        .as_u64()
        .unwrap() as usize;
    let retained_bytes = duplicate_attribution["retained_bytes"].as_u64().unwrap() as usize;
    assert!(
        duplicate_stat_line.contains("2 candidates / 2 applied / 0 later-pass suppressed")
            && duplicate_stat_line.contains(&format!("{} retained B", commas(retained_bytes)))
            && duplicate_stat_line.contains(&format!("{} B / ", commas(marginal_saved_bytes))),
        "the duplicate stats line must match durable marginal attribution: \
         {duplicate_stat_line}"
    );

    // ---- convert (C7): zero sentinel leaks, full fidelity restored. ----
    let out_path = home.join("as-codex.jsonl");
    let conv = run(
        &home,
        &[
            "convert",
            &name,
            "--to",
            "codex",
            "-o",
            out_path.to_str().unwrap(),
        ],
    );
    assert!(
        conv.status.success(),
        "convert must succeed: {}",
        stderr(&conv)
    );
    let written = std::fs::read_to_string(&out_path).unwrap();
    assert_eq!(
        written.matches("sc-reduced").count(),
        0,
        "export must contain zero 'sc-reduced' occurrences (A11 purity)"
    );
    let err = stderr(&conv);
    assert!(
        err.contains("fidelity: full"),
        "missing fidelity line: {err}"
    );
    assert!(
        err.contains("stubs rehydrated"),
        "missing stub count: {err}"
    );

    std::fs::remove_dir_all(&home).ok();
}