Last active
April 9, 2023 14:47
-
-
Save phongphan/ec2d4c3cb2e75cd01367e58633c77bb6 to your computer and use it in GitHub Desktop.
axum mTLS using openssl
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
use axum::{extract::ConnectInfo, response::Html, routing::get, Router}; | |
use axum_server::tls_openssl::OpenSSLConfig; | |
use openssl::ssl::{SslAcceptor, SslFiletype, SslMethod, SslVerifyMode}; | |
use openssl::x509::{ | |
store::{X509Store, X509StoreBuilder}, | |
X509, | |
}; | |
use std::{net::SocketAddr, path::PathBuf}; | |
#[tokio::main] | |
async fn main() { | |
// openssl | |
let mut tls_builder = SslAcceptor::mozilla_modern_v5(SslMethod::tls()).unwrap(); | |
tls_builder | |
.set_certificate_file( | |
PathBuf::from(env!("CARGO_MANIFEST_DIR")) | |
.join("certs") | |
.join("server_cert.crt"), | |
SslFiletype::PEM, | |
) | |
.unwrap(); | |
tls_builder | |
.set_private_key_file( | |
PathBuf::from(env!("CARGO_MANIFEST_DIR")) | |
.join("certs") | |
.join("server_pk.key"), | |
SslFiletype::PEM, | |
) | |
.unwrap(); | |
tls_builder.check_private_key().unwrap(); | |
// client verifier | |
// set options to make sure to validate the peer aka mtls | |
let trusted_client_cert_bytes = std::fs::read( | |
PathBuf::from(env!("CARGO_MANIFEST_DIR")) | |
.join("certs") | |
.join("client_cert.crt"), | |
) | |
.unwrap(); | |
let trusted_client_cert = X509::from_pem(&trusted_client_cert_bytes).unwrap(); | |
let mut builder = X509StoreBuilder::new().unwrap(); | |
let _ = builder.add_cert(trusted_client_cert); | |
let store: X509Store = builder.build(); | |
let mut verify_mode = SslVerifyMode::empty(); | |
verify_mode.set(SslVerifyMode::PEER, true); | |
verify_mode.set(SslVerifyMode::FAIL_IF_NO_PEER_CERT, true); | |
tls_builder.set_verify_cert_store(store).unwrap(); | |
tls_builder.set_verify(verify_mode); | |
// openssl | |
let app = Router::new().route("/", get(handler)); | |
let cfg = OpenSSLConfig::try_from(tls_builder).unwrap(); | |
let addr = SocketAddr::from(([127, 0, 0, 1], 3000)); | |
println!("listening on {}", addr); | |
axum_server::bind_openssl(addr, cfg) | |
.serve(app.into_make_service_with_connect_info::<SocketAddr>()) | |
.await | |
.unwrap(); | |
} | |
async fn handler(ConnectInfo(addr): ConnectInfo<SocketAddr>) -> Html<String> { | |
Html(format!("<h1>Hello, world! {}", addr.to_string())) | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment