use libsql::Connection;
use std::sync::atomic::{AtomicU64, Ordering};
use tracing::debug;
static NEXT_CONNECTION_ID: AtomicU64 = AtomicU64::new(1);
pub fn generate_connection_id() -> u64 {
NEXT_CONNECTION_ID.fetch_add(1, Ordering::Relaxed)
}
#[derive(Debug)]
pub struct PooledConnection {
id: u64,
connection: Connection,
created_at: std::time::Instant,
last_used: std::time::Instant,
}
impl PooledConnection {
pub fn new(connection: Connection) -> Self {
let id = generate_connection_id();
let now = std::time::Instant::now();
debug!("Creating pooled connection with ID {}", id);
Self {
id,
connection,
created_at: now,
last_used: now,
}
}
pub fn id(&self) -> u64 {
self.id
}
pub fn connection(&self) -> &Connection {
&self.connection
}
pub fn connection_mut(&mut self) -> &mut Connection {
&mut self.connection
}
pub fn touch(&mut self) {
self.last_used = std::time::Instant::now();
}
pub fn age(&self) -> std::time::Duration {
self.created_at.elapsed()
}
pub fn idle_time(&self) -> std::time::Duration {
self.last_used.elapsed()
}
pub fn into_inner(self) -> Connection {
self.connection
}
pub async fn validate(&self) -> anyhow::Result<()> {
self.connection
.query("SELECT 1", ())
.await
.map_err(|e| anyhow::anyhow!("Connection validation failed: {}", e))?;
Ok(())
}
}
#[cfg(test)]
mod tests {
use super::*;
#[test]
fn test_connection_id_generation() {
let id1 = generate_connection_id();
let id2 = generate_connection_id();
assert!(
id2 > id1,
"Connection IDs should be monotonically increasing"
);
}
}