use std::sync::Arc;
use std::sync::atomic::{AtomicUsize, Ordering};
use std::time::Duration;
use github_copilot_sdk::handler::ApproveAllHandler;
use github_copilot_sdk::types::{MessageOptions, SessionConfig, SessionLifecycleEventType};
use github_copilot_sdk::{Client, ClientOptions};
#[tokio::main]
async fn main() -> Result<(), github_copilot_sdk::Error> {
let client = Client::start(ClientOptions::default()).await?;
println!("[client] state: {:?}", client.state());
let mut lifecycle_rx = client.subscribe_lifecycle();
let deleted = Arc::new(AtomicUsize::new(0));
let deleted_clone = Arc::clone(&deleted);
let lifecycle_task = tokio::spawn(async move {
while let Ok(event) = lifecycle_rx.recv().await {
let summary = event
.metadata
.as_ref()
.and_then(|m| m.summary.as_deref())
.unwrap_or("<no summary>");
println!(
"[lifecycle:*] {:?} session={} summary={}",
event.event_type, event.session_id, summary,
);
if event.event_type == SessionLifecycleEventType::Deleted {
deleted_clone.fetch_add(1, Ordering::Relaxed);
}
}
});
let config = SessionConfig::default().with_handler(Arc::new(ApproveAllHandler));
let session = client.create_session(config).await?;
println!("[client] state after create: {:?}", client.state());
let mut session_rx = session.subscribe();
let session_events = Arc::new(AtomicUsize::new(0));
let session_events_clone = Arc::clone(&session_events);
let session_task = tokio::spawn(async move {
while let Ok(event) = session_rx.recv().await {
session_events_clone.fetch_add(1, Ordering::Relaxed);
println!("[session-event] {}", event.event_type);
}
});
if let Some(metadata) = client.get_session_metadata(session.id()).await? {
println!(
"[metadata] id={} modified={} summary={}",
metadata.session_id,
metadata.modified_time,
metadata.summary.as_deref().unwrap_or("<no summary>"),
);
}
session
.send_and_wait(
MessageOptions::new("Say hello in five words or fewer.")
.with_wait_timeout(Duration::from_secs(60)),
)
.await?;
session.destroy().await?;
client.force_stop();
println!("[client] state after force_stop: {:?}", client.state());
let _ = lifecycle_task.await;
let _ = session_task.await;
println!(
"\n[summary] session_events={} sessions_deleted={}",
session_events.load(Ordering::Relaxed),
deleted.load(Ordering::Relaxed),
);
Ok(())
}