supercode-harness 0.4.13

The optional native Supercode agent and tool harness
Documentation
//! Adapter-free receipt for the canonical SDK semantics. This test is run
//! both with the default surface features and with `--no-default-features`.

use std::path::{Path, PathBuf};
use std::sync::{Arc, Mutex};

use async_trait::async_trait;
use serde_json::json;
use supercode_harness::{
    load_session_path, Agent, ChatMessage, ChatRequest, Config, FrontendElicitationAction,
    FrontendResponse, FrontendRuntimeError, HarnessSessionService, Provider, RpcEngine,
    RuntimeSubmitError, SdkOperation, SdkRequest, SdkRuntime, SdkService, Session, SessionSource,
    Usage,
};

fn fixture() -> PathBuf {
    Path::new(env!("CARGO_MANIFEST_DIR")).join("tests/fixtures/pi_session.jsonl")
}

fn locator() -> serde_json::Value {
    json!({
        "harness":"pi",
        "session_id":"1e6f2a3b-0000-4000-8000-000000000001",
        "storage":{"kind":"file", "path":fixture()},
    })
}

#[test]
fn sdk_path_load_prefers_the_full_native_store_sidecar() {
    let nonce = std::time::SystemTime::now()
        .duration_since(std::time::UNIX_EPOCH)
        .unwrap()
        .as_nanos();
    let root = std::env::temp_dir().join(format!(
        "supercode-sdk-native-family-{}-{nonce}",
        std::process::id()
    ));
    std::fs::create_dir_all(&root).unwrap();
    let name = "continued-claude-session";
    let transcript = root.join(format!("{name}.jsonl"));
    let sidecar = root.join(format!("{name}.sidecar.jsonl"));
    let metadata = root.join(format!("{name}.meta.json"));
    let source = concat!(
        "{\"type\":\"user\",\"sessionId\":\"source-id\",",
        "\"message\":{\"role\":\"user\",\"content\":\"imported fact\"}}\n"
    );
    let imported = Session::from_claude_code_str(source).unwrap();
    let appended = [
        ChatMessage::user("continued prompt"),
        ChatMessage::assistant("continued answer"),
    ];
    std::fs::write(&sidecar, imported.to_native_jsonl_v2(&appended)).unwrap();
    std::fs::write(
        &transcript,
        serde_json::to_string(&ChatMessage::user("reduced working view")).unwrap(),
    )
    .unwrap();
    std::fs::write(metadata, "{}").unwrap();

    let loaded = load_session_path(&transcript, None).unwrap();
    assert_eq!(loaded.meta.source, SessionSource::ClaudeCode);
    assert_eq!(loaded.meta.session_id.as_deref(), Some(name));
    assert_eq!(loaded.raw[0], source.trim_end());
    assert_eq!(
        loaded
            .messages
            .iter()
            .filter_map(|message| message.content.as_deref())
            .collect::<Vec<_>>(),
        ["imported fact", "continued prompt", "continued answer"]
    );
    assert!(loaded
        .messages
        .iter()
        .all(|message| message.content.as_deref() != Some("reduced working view")));
    std::fs::remove_dir_all(root).ok();
}

struct BlockingProvider {
    entered: tokio::sync::Notify,
    release: tokio::sync::Notify,
}

struct SharedProvider(Arc<BlockingProvider>);

#[async_trait]
impl Provider for SharedProvider {
    async fn complete(
        &self,
        _request: &ChatRequest,
        on_delta: &(dyn for<'a> Fn(&'a str) + Send + Sync),
    ) -> supercode_harness::Result<(ChatMessage, Usage)> {
        self.0.entered.notify_one();
        self.0.release.notified().await;
        on_delta("adapter-free reply");
        Ok((
            ChatMessage::assistant("adapter-free reply"),
            Usage::default(),
        ))
    }
}

#[tokio::test]
async fn canonical_sdk_semantics_survive_removing_every_surface_adapter() {
    let mut service = HarnessSessionService::new();
    let loaded = service
        .execute(SdkRequest {
            operation: SdkOperation::Load,
            params: json!({"locator":locator()}),
        })
        .await
        .unwrap();
    assert_eq!(loaded["session"]["session_id"], locator()["session_id"]);
    let exported = service
        .execute(SdkRequest {
            operation: SdkOperation::Export,
            params: json!({"locator":locator(), "target_harness":"pi"}),
        })
        .await
        .unwrap();
    assert_eq!(exported["artifact"]["session_id"], locator()["session_id"]);

    let provider = Arc::new(BlockingProvider {
        entered: tokio::sync::Notify::new(),
        release: tokio::sync::Notify::new(),
    });
    let persisted = Arc::new(Mutex::new(String::new()));
    let persisted_hook = persisted.clone();
    let agent = Agent::with_provider(
        Config::builder().system_prompt("SDK-only proof").build(),
        Box::new(SharedProvider(provider.clone())),
    );
    let runtime = RpcEngine::new_named(
        agent,
        "adapter-free-stable-id",
        Some(Box::new(move |agent: &supercode_harness::SdkAgent| {
            *persisted_hook.lock().unwrap() = serde_json::to_string(agent.history()).unwrap();
        })),
    );
    let mut events = runtime.attach(50).await.unwrap();
    let active = {
        let runtime = runtime.clone();
        tokio::spawn(async move { SdkRuntime::submit(runtime.as_ref(), "one prompt".into()).await })
    };
    provider.entered.notified().await;
    assert_eq!(
        SdkRuntime::submit(runtime.as_ref(), "busy prompt".into())
            .await
            .unwrap_err(),
        FrontendRuntimeError::Submit(RuntimeSubmitError::Busy)
    );
    assert_eq!(
        SdkRuntime::respond(
            runtime.as_ref(),
            FrontendResponse::Other {
                request_id: 99,
                action: FrontendElicitationAction::Cancel,
                content: None,
            },
        )
        .await
        .unwrap_err(),
        FrontendRuntimeError::UnsupportedAction("respond")
    );
    provider.release.notify_waiters();
    assert_eq!(active.await.unwrap().unwrap(), "adapter-free reply");

    let mut sequence = Vec::new();
    loop {
        let event = events.next_event().await.unwrap();
        let terminal = event.kind == "turn_succeeded";
        sequence.push((event.sequence, event.kind));
        if terminal {
            break;
        }
    }
    assert_eq!(events.descriptor.session_id, "adapter-free-stable-id");
    assert!(sequence.windows(2).all(|pair| pair[0].0 < pair[1].0));
    assert!(persisted.lock().unwrap().contains("adapter-free reply"));
    runtime.shutdown().await;
}