use crate::error::{FossilError, Result};
use crate::repo::Repository;
#[derive(Debug, Clone, PartialEq)]
pub enum SyncProtocol {
Quic,
}
pub struct SyncBuilder<'a> {
repo: &'a Repository,
url: Option<String>,
username: Option<String>,
password: Option<String>,
}
impl<'a> SyncBuilder<'a> {
pub(crate) fn new(repo: &'a Repository) -> Self {
Self {
repo,
url: None,
username: None,
password: None,
}
}
pub fn to(mut self, url: &str) -> Self {
self.url = Some(url.to_string());
self
}
pub fn from(mut self, url: &str) -> Self {
self.url = Some(url.to_string());
self
}
pub fn with(mut self, url: &str) -> Self {
self.url = Some(url.to_string());
self
}
pub fn url(self, url: &str) -> Self {
self.with(url)
}
pub fn auth(mut self, username: &str, password: &str) -> Self {
self.username = Some(username.to_string());
self.password = Some(password.to_string());
self
}
pub fn username(mut self, username: &str) -> Self {
self.username = Some(username.to_string());
self
}
pub fn password(mut self, password: &str) -> Self {
self.password = Some(password.to_string());
self
}
fn normalize_url(url: &str) -> String {
if url.starts_with("quic://") {
url.replacen("quic://", "", 1)
} else {
url.to_string()
}
}
pub fn push(self) -> Result<SyncResult> {
self.execute()
}
pub fn pull(self) -> Result<SyncResult> {
self.execute()
}
pub fn execute(self) -> Result<SyncResult> {
let url = self
.url
.ok_or_else(|| FossilError::InvalidArtifact("sync URL is required".to_string()))?;
let normalized_url = Self::normalize_url(&url);
#[cfg(feature = "sync-quic")]
{
use crate::sync::QuicClient;
use std::path::PathBuf;
let rt = tokio::runtime::Runtime::new()
.map_err(|e| FossilError::SyncError(e.to_string()))?;
let stats = rt.block_on(async {
QuicClient::sync(self.repo, &PathBuf::new(), &normalized_url).await
})?;
Ok(SyncResult {
artifacts_sent: stats.artifacts_sent,
artifacts_received: stats.artifacts_received,
protocol: SyncProtocol::Quic,
})
}
#[cfg(not(feature = "sync-quic"))]
{
let _ = (normalized_url, self.repo);
Err(FossilError::InvalidArtifact(
"QUIC sync requires 'sync-quic' feature".to_string(),
))
}
}
}
#[derive(Debug)]
pub struct SyncResult {
pub artifacts_sent: usize,
pub artifacts_received: usize,
pub protocol: SyncProtocol,
}