@@ -2,7 +2,7 @@ mod certificate;
22mod signal;
33mod tracker;
44
5- use std:: { net:: SocketAddr , str:: FromStr , time:: Duration } ;
5+ use std:: { net:: SocketAddr , str:: FromStr , sync :: Arc , time:: Duration } ;
66
77use axum:: {
88 body:: Body ,
@@ -74,14 +74,20 @@ pub async fn run(args: Args) -> Result<()> {
7474 // Spawn a task to gracefully shutdown server.
7575 tokio:: spawn ( signal:: graceful_shutdown ( handle. clone ( ) ) ) ;
7676
77- // Load TLS configuration
77+ // Load TLS configuration with HTTP/2 ALPN preference
7878 let tls_config = match ( args. tls_cert . as_ref ( ) , args. tls_key . as_ref ( ) ) {
79- ( Some ( cert) , Some ( key) ) => RustlsConfig :: from_pem_chain_file ( cert, key) . await ,
79+ ( Some ( cert_path) , Some ( key_path) ) => {
80+ // Load certificate and key from files
81+ let cert_pem = std:: fs:: read ( cert_path) ?;
82+ let key_pem = std:: fs:: read ( key_path) ?;
83+ create_rustls_config_with_h2_alpn ( cert_pem, key_pem) . await ?
84+ }
8085 _ => {
81- let ( cert, key) = certificate:: get_self_signed_cert ( ) ?;
82- RustlsConfig :: from_pem ( cert, key) . await
86+ // Generate self-signed certificate
87+ let ( cert_pem, key_pem) = certificate:: get_self_signed_cert ( ) ?;
88+ create_rustls_config_with_h2_alpn ( cert_pem, key_pem) . await ?
8389 }
84- } ? ;
90+ } ;
8591
8692 // Use TLS configuration to create a secure server
8793 let mut server = axum_server:: bind_rustls ( args. bind , tls_config) ;
@@ -105,6 +111,45 @@ impl IntoResponse for Error {
105111 }
106112}
107113
114+ /// Create RustlsConfig with HTTP/2 ALPN preference
115+ async fn create_rustls_config_with_h2_alpn (
116+ cert_pem : Vec < u8 > ,
117+ key_pem : Vec < u8 > ,
118+ ) -> Result < RustlsConfig > {
119+ use tokio_rustls:: rustls:: {
120+ pki_types:: { CertificateDer , PrivateKeyDer } ,
121+ ServerConfig ,
122+ } ;
123+
124+ // Parse certificates/PK
125+ let certs: Vec < CertificateDer > = rustls_pemfile:: certs ( & mut cert_pem. as_slice ( ) )
126+ . collect :: < std:: result:: Result < Vec < _ > , _ > > ( )
127+ . map_err ( |e| Error :: Other ( format ! ( "Failed to parse certificate: {}" , e) ) ) ?;
128+
129+ let key: PrivateKeyDer = rustls_pemfile:: private_key ( & mut key_pem. as_slice ( ) )
130+ . map_err ( |e| Error :: Other ( format ! ( "Failed to parse private key: {}" , e) ) ) ?
131+ . ok_or_else ( || Error :: Other ( "No private key found" . to_string ( ) ) ) ?;
132+
133+ // Create server config with ALPN protocols (HTTP/2 first)
134+ let config = ServerConfig :: builder ( )
135+ . with_no_client_auth ( )
136+ . with_single_cert ( certs, key)
137+ . map_err ( |e| Error :: Other ( format ! ( "Failed to create TLS config: {}" , e) ) ) ?;
138+
139+ // Set ALPN protocols with HTTP/2 preference
140+ let mut config = config;
141+ config. alpn_protocols = vec ! [
142+ b"h2" . to_vec( ) ,
143+ b"http/1.1" . to_vec( ) ,
144+ b"http/1.0" . to_vec( ) ,
145+ b"http/0.9" . to_vec( ) ,
146+ ] ;
147+
148+ tracing:: info!( "TLS configured with ALPN protocols: h2 (HTTP/2), http/1.1, http/1.0, http/0.9" ) ;
149+
150+ Ok ( RustlsConfig :: from_config ( Arc :: new ( config) ) )
151+ }
152+
108153#[ inline]
109154pub async fn track (
110155 Extension ( ConnectInfo ( addr) ) : Extension < ConnectInfo < SocketAddr > > ,
0 commit comments