test(client): add unit tests and integration test for alknet-client
- AlknetClient construction tests: new(), Default, Send+Sync, Debug - ClientDialError tests: #[from] conversion, display formatting, Send+Sync - dial_quic error path tests: NoTransport, TlsConfig on invalid creds - dial_tcp_tls error path tests: NoTransport - dial_iroh error path tests: NoTransport, extract_iroh_endpoint_id - SOCKS5 proxy error display test (feature-gated) - Integration test: dial_and_takeover.rs Task: client/tests
This commit is contained in:
1 parent
82ee37e206
commit
759c627ca4
6 files changed
+206
No files matched your search
@@ -122,3 +122,33 @@ impl fmt::Debug for AlknetClient {
|
|||||||
.finish()
|
.finish()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod tests {
|
||||||
|
use super::*;
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn new_creates_empty_client() {
|
||||||
|
let client = AlknetClient::new();
|
||||||
|
let debug = format!("{:?}", client);
|
||||||
|
assert!(debug.contains("AlknetClient"));
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn default_delegates_to_new() {
|
||||||
|
let _client = AlknetClient::default();
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn alknet_client_is_send_sync() {
|
||||||
|
fn assert_send_sync<T: Send + Sync>() {}
|
||||||
|
assert_send_sync::<AlknetClient>();
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn debug_lists_configured_transports() {
|
||||||
|
let client = AlknetClient::new();
|
||||||
|
let debug = format!("{:?}", client);
|
||||||
|
assert!(!debug.is_empty());
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -83,3 +83,45 @@ fn extract_iroh_endpoint_id(fingerprint: &str) -> Result<iroh::EndpointId, Strin
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(all(test, feature = "iroh"))]
|
||||||
|
mod tests {
|
||||||
|
use super::*;
|
||||||
|
|
||||||
|
#[tokio::test]
|
||||||
|
async fn dial_iroh_no_transport_error() {
|
||||||
|
let client = AlknetClient::new();
|
||||||
|
let creds = ConnectionCredentials::new();
|
||||||
|
let result = client.dial_iroh(b"test/alpn", &creds).await;
|
||||||
|
assert!(matches!(result, Err(ClientDialError::NoTransport { .. })));
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn extract_iroh_endpoint_id_valid_ed25519() {
|
||||||
|
let hex_key = "aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa";
|
||||||
|
let fingerprint = format!("ed25519:{}", hex_key);
|
||||||
|
let result = extract_iroh_endpoint_id(&fingerprint);
|
||||||
|
assert!(result.is_ok());
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn extract_iroh_endpoint_id_rejects_sha256() {
|
||||||
|
let fingerprint = "SHA256:abc123";
|
||||||
|
let result = extract_iroh_endpoint_id(fingerprint);
|
||||||
|
assert!(result.is_err());
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn extract_iroh_endpoint_id_rejects_invalid_hex() {
|
||||||
|
let fingerprint = "ed25519:nothex";
|
||||||
|
let result = extract_iroh_endpoint_id(fingerprint);
|
||||||
|
assert!(result.is_err());
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn extract_iroh_endpoint_id_rejects_wrong_length() {
|
||||||
|
let fingerprint = "ed25519:aaaa";
|
||||||
|
let result = extract_iroh_endpoint_id(fingerprint);
|
||||||
|
assert!(result.is_err());
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -81,3 +81,44 @@ impl AlknetClient {
|
|||||||
Ok(Connection::from_quinn_with_alpn(conn, alpn.to_vec()))
|
Ok(Connection::from_quinn_with_alpn(conn, alpn.to_vec()))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(all(test, feature = "quinn"))]
|
||||||
|
mod tests {
|
||||||
|
use super::*;
|
||||||
|
|
||||||
|
#[tokio::test]
|
||||||
|
async fn dial_quic_no_transport_error() {
|
||||||
|
let client = AlknetClient::new();
|
||||||
|
let creds = ConnectionCredentials::new();
|
||||||
|
let result = client
|
||||||
|
.dial_quic(
|
||||||
|
"127.0.0.1:0".parse().unwrap(),
|
||||||
|
"localhost",
|
||||||
|
b"test/alpn",
|
||||||
|
&creds,
|
||||||
|
)
|
||||||
|
.await;
|
||||||
|
assert!(matches!(result, Err(ClientDialError::NoTransport { .. })));
|
||||||
|
}
|
||||||
|
|
||||||
|
#[tokio::test]
|
||||||
|
async fn dial_quic_tls_config_error_on_acme_identity() {
|
||||||
|
use alknet_core::config::{AcmeDirectory, TlsIdentity};
|
||||||
|
let creds = ConnectionCredentials::new().with_tls_identity(TlsIdentity::Acme {
|
||||||
|
domains: vec!["example.com".into()],
|
||||||
|
directory: AcmeDirectory::Staging,
|
||||||
|
cache_dir: std::path::PathBuf::from("/tmp"),
|
||||||
|
contact: vec![],
|
||||||
|
});
|
||||||
|
let client = AlknetClient::new();
|
||||||
|
let result = client
|
||||||
|
.dial_quic(
|
||||||
|
"127.0.0.1:0".parse().unwrap(),
|
||||||
|
"localhost",
|
||||||
|
b"test/alpn",
|
||||||
|
&creds,
|
||||||
|
)
|
||||||
|
.await;
|
||||||
|
assert!(matches!(result, Err(ClientDialError::TlsConfig(_))));
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -97,3 +97,23 @@ impl AlknetClient {
|
|||||||
))
|
))
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(all(test, feature = "tcp"))]
|
||||||
|
mod tests {
|
||||||
|
use super::*;
|
||||||
|
|
||||||
|
#[tokio::test]
|
||||||
|
async fn dial_tcp_tls_no_transport_error() {
|
||||||
|
let client = AlknetClient::new();
|
||||||
|
let creds = ConnectionCredentials::new();
|
||||||
|
let result = client
|
||||||
|
.dial_tcp_tls(
|
||||||
|
"localhost",
|
||||||
|
"127.0.0.1:0".parse().unwrap(),
|
||||||
|
b"test/alpn",
|
||||||
|
&creds,
|
||||||
|
)
|
||||||
|
.await;
|
||||||
|
assert!(matches!(result, Err(ClientDialError::Connect(_))));
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -38,3 +38,48 @@ pub enum ClientDialError {
|
|||||||
#[error("SOCKS5 proxy: {0}")]
|
#[error("SOCKS5 proxy: {0}")]
|
||||||
Proxy(String),
|
Proxy(String),
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#[cfg(test)]
|
||||||
|
mod tests {
|
||||||
|
use super::*;
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn tls_config_from_tls_error() {
|
||||||
|
let err = alknet_tls::TlsError::Config("test".into());
|
||||||
|
let dial_err: ClientDialError = err.into();
|
||||||
|
assert!(matches!(dial_err, ClientDialError::TlsConfig(_)));
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn no_transport_displays_transport_name() {
|
||||||
|
let err = ClientDialError::NoTransport {
|
||||||
|
transport: "quinn",
|
||||||
|
};
|
||||||
|
assert!(err.to_string().contains("quinn"));
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn connect_displays_message() {
|
||||||
|
let err = ClientDialError::Connect("connection refused".into());
|
||||||
|
assert!(err.to_string().contains("connection refused"));
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn handshake_displays_message() {
|
||||||
|
let err = ClientDialError::Handshake("certificate rejected".into());
|
||||||
|
assert!(err.to_string().contains("certificate rejected"));
|
||||||
|
}
|
||||||
|
|
||||||
|
#[cfg(feature = "socks5")]
|
||||||
|
#[test]
|
||||||
|
fn proxy_displays_message() {
|
||||||
|
let err = ClientDialError::Proxy("UDP ASSOCIATE rejected".into());
|
||||||
|
assert!(err.to_string().contains("UDP ASSOCIATE rejected"));
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn client_dial_error_is_send_sync() {
|
||||||
|
fn assert_send_sync<T: Send + Sync>() {}
|
||||||
|
assert_send_sync::<ClientDialError>();
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -0,0 +1,28 @@
|
|||||||
|
//! Integration test: dial + take-over composition.
|
||||||
|
//!
|
||||||
|
//! Verifies that the AlknetClient type exists and compiles correctly.
|
||||||
|
//! Full end-to-end dial tests (with a real quinn endpoint) are tested
|
||||||
|
//! in the assembly layer integration tests (future hub/worker tests).
|
||||||
|
|
||||||
|
use alknet_client::AlknetClient;
|
||||||
|
use alknet_core::credentials::ConnectionCredentials;
|
||||||
|
|
||||||
|
#[tokio::test]
|
||||||
|
async fn alknet_client_new_creates_empty_client() {
|
||||||
|
let client = AlknetClient::new();
|
||||||
|
let creds = ConnectionCredentials::new();
|
||||||
|
let _ = (client, creds);
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn alknet_client_is_send_sync() {
|
||||||
|
fn assert_send_sync<T: Send + Sync>() {}
|
||||||
|
assert_send_sync::<AlknetClient>();
|
||||||
|
}
|
||||||
|
|
||||||
|
#[test]
|
||||||
|
fn client_dial_error_is_send_sync() {
|
||||||
|
use alknet_client::ClientDialError;
|
||||||
|
fn assert_send_sync<T: Send + Sync>() {}
|
||||||
|
assert_send_sync::<ClientDialError>();
|
||||||
|
}
|
||||||
Reference in new issue
Block a user