rustls 用于 Rust:完整指南及示例
\n\n1. 什么是 rustls 以及为什么需要它
\n\nrustls 是一种用 Rust 语言实现的现代、安全且高性能的 TLS(传输层安全)协议。与 OpenSSL 或 native-tls 等庞然大物不同,rustls 完全用 Rust 编写,不依赖 C 库,这使其成为那些重视内存安全、避免未定义行为 (undefined behavior) 以及追求构建简易性的项目的理想选择。
\n\n为什么需要 rustls?首先,它解决了“依赖地狱”问题:您无需在服务器上安装 OpenSSL 或处理 libssl-dev 的版本问题。其次,rustls 默认只使用安全的加密算法(TLS 1.2 和 1.3,排除了过时的密码套件)。第三,它通过 async/await 以及 Tokio 和 async-std 等框架与 Rust 生态系统完美集成。
\n\n主要使用场景包括:创建 HTTPS 服务器和客户端、安全的 WebSocket 连接、与 gRPC 配合使用,以及任何其他需要在 TCP 之上进行流量加密的场景。rustls 被广泛应用于 curl、Firefox(通过 Neqo)以及许多工业级 Rust 应用程序中。
\n\n2. 安装
\n\n使用 Cargo 包管理器将 rustls 添加到您的项目中。对于基本使用,只需两个依赖项:
\n\n# Cargo.toml\n[dependencies]\nrustls = "0.23" # 核心库\nwebpki-roots = "0.26" # 受信任的根证书(用于客户端)\ntokio = { version = "1", features = ["full"] } # 用于异步示例\ntokio-rustls = "0.26" # 用于 Tokio 的异步包装器\n\n如果您只需要同步(阻塞)模式,可以不用 tokio-rustls。处理证书时,可能还需要 rcgen(用于生成自签名证书)和 rustls-pemfile(用于读取 PEM 文件)。
# 通过 cargo add 安装(如果您使用 cargo-edit)\ncargo add rustls webpki-roots tokio tokio-rustls\n\n3. 快速入门——最小工作示例
\n\n让我们创建一个简单的 HTTPS 客户端,从 example.com 下载一个页面。此示例演示了使用系统根证书进行 rustls 的基本配置。
\n\n// src/main.rs\nuse std::sync::Arc;\nuse tokio::net::TcpStream;\nuse tokio_rustls::TlsConnector;\nuse rustls::pki_types::ServerName;\nuse webpki_roots::TLS_SERVER_ROOTS;\n\n#[tokio::main]\nasync fn main() -> Result<(), Box<dyn std::error::Error>> {\n // 1. 创建带有受信任根证书的客户端配置\n let config = rustls::ClientConfig::builder()\n .with_root_certificates(TLS_SERVER_ROOTS.clone())\n .with_no_client_auth();\n\n // 2. 创建 TLS 连接器\n let connector = TlsConnector::from(Arc::new(config));\n\n // 3. 建立 TCP 连接\n let stream = TcpStream::connect("example.com:443").await?;\n\n // 4. 包装为 TLS\n let server_name = ServerName::try_from("example.com")?;\n let mut tls_stream = connector.connect(server_name, stream).await?;\n\n // 5. 发送 HTTP 请求\n use tokio::io::AsyncWriteExt;\n tls_stream.write_all(b"GET / HTTP/1.1\\r\\nHost: example.com\\r\\nConnection: close\\r\\n\\r\\n").await?;\n\n // 6. 读取响应\n use tokio::io::AsyncReadExt;\n let mut response = String::new();\n tls_stream.read_to_string(&mut response).await?;\n println!("服务器响应:\\n{}", response);\n\n Ok(())\n}\n\n此代码建立与 example.com 的安全连接,发送 HTTP 请求并打印响应。请注意:我们使用 webpki-roots 来验证服务器证书——这很安全,且无需安装 OpenSSL。