Implemented AutoTLS via RustTLS

This commit is contained in:
2026-03-10 16:20:19 +00:00
parent 588b610e08
commit bf16ff40f9
7 changed files with 411 additions and 35 deletions

View File

@@ -38,15 +38,40 @@ pub struct FurumiClient {
}
impl FurumiClient {
/// Connects to the Furumi-ng server with an optional bearer token.
pub async fn connect(addr: &str, token: &str) -> Result<Self> {
let endpoint = Endpoint::from_shared(addr.to_string())
/// Connects to the Furumi-ng server.
///
/// - `addr`: Server URL. Use `https://` for TLS, `http://` for plaintext.
/// - `token`: Bearer token for auth (empty = no auth).
/// - `tls_ca_pem`: Optional CA certificate PEM bytes for verifying the server.
/// If using TLS without a CA cert, pass `None` (uses system roots).
pub async fn connect(addr: &str, token: &str, tls_ca_pem: Option<Vec<u8>>) -> Result<Self> {
// Install ring as the default crypto provider for rustls
let _ = rustls::crypto::ring::default_provider().install_default();
let mut endpoint = Endpoint::from_shared(addr.to_string())
.map_err(|e| ClientError::Internal(format!("Invalid URI: {}", e)))?
.timeout(Duration::from_secs(30))
.concurrency_limit(256)
.tcp_keepalive(Some(Duration::from_secs(60)))
.http2_keep_alive_interval(Duration::from_secs(60));
// Configure TLS if using https://
if addr.starts_with("https://") {
let mut tls_config = tonic::transport::ClientTlsConfig::new()
.domain_name("furumi-ng");
if let Some(ca_pem) = tls_ca_pem {
info!("TLS enabled with server CA certificate");
tls_config = tls_config
.ca_certificate(tonic::transport::Certificate::from_pem(ca_pem));
} else {
info!("TLS enabled with system root certificates");
}
endpoint = endpoint.tls_config(tls_config)
.map_err(|e| ClientError::Internal(format!("TLS config error: {}", e)))?;
}
info!("Connecting to {}", addr);
let channel = endpoint.connect().await?;
@@ -58,7 +83,7 @@ impl FurumiClient {
let attr_cache = Cache::builder()
.max_capacity(100_000)
.time_to_live(Duration::from_secs(5)) // short TTL to catch up changes quickly
.time_to_live(Duration::from_secs(5))
.build();
Ok(Self { client, attr_cache })