From e15a870713ff825dc010126d54bff2969446e02f Mon Sep 17 00:00:00 2001 From: Ali MJ Al-Nasrawy Date: Fri, 8 Oct 2021 21:24:02 +0300 Subject: Bump actix-web to v4.0-beta.9 --- src/main.rs | 4 ---- 1 file changed, 4 deletions(-) (limited to 'src') diff --git a/src/main.rs b/src/main.rs index d5cac00..5f4f7a8 100644 --- a/src/main.rs +++ b/src/main.rs @@ -9,10 +9,6 @@ use actix_files::NamedFile; use actix_web::web; use actix_web::{http::header::ContentType, Responder}; use actix_web::{middleware, App, HttpRequest, HttpResponse}; -use actix_web_httpauth::middleware::HttpAuthentication; -use anyhow::Result; -use clap::{crate_version, IntoApp, Parser}; -use clap_generate::generate; use log::{error, warn}; use qrcodegen::{QrCode, QrCodeEcc}; use yansi::{Color, Paint}; -- cgit v1.2.3 From 00598acb2197b8f86dd03c0d79e016882b6a96cd Mon Sep 17 00:00:00 2001 From: jikstra Date: Tue, 28 Dec 2021 00:28:27 +0100 Subject: Bump actix-web to v4.0-beta.15 Co-authored-by: Ali MJ Al-Nasrawy --- src/archive.rs | 2 +- src/config.rs | 29 +++++++++++++++++++++++++---- src/errors.rs | 22 +++++++++++----------- src/file_upload.rs | 15 ++++++--------- src/listing.rs | 6 +++--- src/main.rs | 14 ++++++++++---- 6 files changed, 56 insertions(+), 32 deletions(-) (limited to 'src') diff --git a/src/archive.rs b/src/archive.rs index ed33925..29f60c1 100644 --- a/src/archive.rs +++ b/src/archive.rs @@ -1,4 +1,4 @@ -use actix_web::http::ContentEncoding; +use actix_web::http::header::ContentEncoding; use libflate::gzip::Encoder; use serde::Deserialize; use std::fs::File; diff --git a/src/config.rs b/src/config.rs index fda2f84..9bb6928 100644 --- a/src/config.rs +++ b/src/config.rs @@ -11,7 +11,7 @@ use anyhow::{Context, Result}; use http::HeaderMap; #[cfg(feature = "tls")] -use rustls::internal::pemfile::{certs, pkcs8_private_keys}; +use rustls_pemfile::{certs, pkcs8_private_keys}; use crate::{args::CliArgs, auth::RequiredAuth}; @@ -156,7 +156,6 @@ impl MiniserveConfig { let tls_rustls_server_config = if let (Some(tls_cert), Some(tls_key)) = (args.tls_cert, args.tls_key) { - let mut server_config = rustls::ServerConfig::new(rustls::NoClientAuth::new()); let cert_file = &mut BufReader::new( File::open(&tls_cert) .context(format!("Couldn't access TLS certificate {:?}", tls_cert))?, @@ -164,10 +163,32 @@ impl MiniserveConfig { let key_file = &mut BufReader::new( File::open(&tls_key).context(format!("Couldn't access TLS key {:?}", tls_key))?, ); - let cert_chain = certs(cert_file).map_err(|_| anyhow!("Couldn't load certificates"))?; + let cert_chain = match rustls_pemfile::read_one(cert_file) { + Ok(item) => match item { + Some(item) => match item { + rustls_pemfile::Item::X509Certificate(item) => item, + _ => return Err(anyhow!("Certfile is not a X509Certificate")), + }, + None => { + return Err(anyhow!( + "Certfile does not contain any recognized certificates" + )) + } + }, + _ => return Err(anyhow!("Could not read certfile")), + }; let mut keys = pkcs8_private_keys(key_file).map_err(|_| anyhow!("Couldn't load private key"))?; - server_config.set_single_cert(cert_chain, keys.remove(0))?; + let server_config = rustls::ServerConfig::builder() + .with_safe_default_cipher_suites() + .with_safe_default_kx_groups() + .with_safe_default_protocol_versions() + .unwrap() + .with_no_client_auth() + .with_single_cert( + vec![rustls::Certificate(cert_chain)], + rustls::PrivateKey(keys.remove(0)), + )?; Some(server_config) } else { None diff --git a/src/errors.rs b/src/errors.rs index c6fcce3..70bad5c 100644 --- a/src/errors.rs +++ b/src/errors.rs @@ -1,6 +1,6 @@ use crate::{renderer::render_error, MiniserveConfig}; use actix_web::{ - body::AnyBody, + body::{BoxBody, MessageBody}, dev::{ResponseHead, Service, ServiceRequest, ServiceResponse}, http::{header, StatusCode}, HttpRequest, HttpResponse, ResponseError, @@ -134,13 +134,15 @@ where } } -fn map_error_page(req: &HttpRequest, head: &mut ResponseHead, body: AnyBody) -> AnyBody { - let error_msg = match &body { - AnyBody::Bytes(bytes) => match std::str::from_utf8(bytes) { - Ok(msg) => msg, - _ => return body, - }, - _ => return body, +fn map_error_page<'a>(req: &HttpRequest, head: &mut ResponseHead, body: BoxBody) -> BoxBody { + let error_msg = match body.try_into_bytes() { + Ok(bytes) => bytes, + Err(body) => return body, + }; + + let error_msg = match std::str::from_utf8(&error_msg) { + Ok(msg) => msg, + _ => return BoxBody::new(error_msg), }; let conf = req.app_data::().unwrap(); @@ -155,9 +157,7 @@ fn map_error_page(req: &HttpRequest, head: &mut ResponseHead, body: AnyBody) -> header::HeaderValue::from_static("text/html; charset=utf-8"), ); - render_error(error_msg, head.status, conf, return_address) - .into_string() - .into() + BoxBody::new(render_error(error_msg, head.status, conf, return_address).into_string()) } pub fn log_error_chain(description: String) { diff --git a/src/file_upload.rs b/src/file_upload.rs index 5009f36..0d4b8a5 100644 --- a/src/file_upload.rs +++ b/src/file_upload.rs @@ -43,15 +43,12 @@ async fn handle_multipart( path: PathBuf, overwrite_files: bool, ) -> Result { - let filename = field - .content_disposition() - .and_then(|cd| cd.get_filename().map(String::from)) - .ok_or_else(|| { - ContextualError::ParseError( - "HTTP header".to_string(), - "Failed to retrieve the name of the file to upload".to_string(), - ) - })?; + let filename = field.content_disposition().get_filename().ok_or_else(|| { + ContextualError::ParseError( + "HTTP header".to_string(), + "Failed to retrieve the name of the file to upload".to_string(), + ) + })?; let filename = sanitize_path(Path::new(&filename), false).ok_or_else(|| { ContextualError::InvalidPathError("Invalid file name to upload".to_string()) diff --git a/src/listing.rs b/src/listing.rs index 9273025..58703c0 100644 --- a/src/listing.rs +++ b/src/listing.rs @@ -1,7 +1,7 @@ -use actix_web::body::Body; +use actix_web::body::BoxBody; use actix_web::dev::ServiceResponse; use actix_web::web::Query; -use actix_web::{HttpRequest, HttpResponse}; +use actix_web::{HttpMessage, HttpRequest, HttpResponse}; use bytesize::ByteSize; use percent_encoding::{percent_decode_str, utf8_percent_encode}; use qrcodegen::{QrCode, QrCodeEcc}; @@ -225,7 +225,7 @@ pub fn directory_listing( .body(qr_to_svg_string(&qr, 2)), Err(err) => { log::error!("URL is invalid (too long?): {:?}", err); - HttpResponse::UriTooLong().body(Body::Empty) + HttpResponse::UriTooLong().finish() } }; return Ok(ServiceResponse::new(req.clone(), res)); diff --git a/src/main.rs b/src/main.rs index 5f4f7a8..fcd01ab 100644 --- a/src/main.rs +++ b/src/main.rs @@ -6,9 +6,15 @@ use std::thread; use std::time::Duration; use actix_files::NamedFile; +use actix_web::body::BoxBody; +use actix_web::middleware::Compat; use actix_web::web; use actix_web::{http::header::ContentType, Responder}; use actix_web::{middleware, App, HttpRequest, HttpResponse}; +use actix_web_httpauth::middleware::HttpAuthentication; +use anyhow::Result; +use clap::{crate_version, IntoApp, Parser}; +use clap_generate::generate; use log::{error, warn}; use qrcodegen::{QrCode, QrCodeEcc}; use yansi::{Color, Paint}; @@ -194,7 +200,7 @@ async fn run(miniserve_config: MiniserveConfig) -> Result<(), ContextualError> { web::scope(inside_config.random_route.as_deref().unwrap_or("")) .wrap(middleware::Condition::new( !inside_config.auth.is_empty(), - HttpAuthentication::basic(auth::handle_auth), + Compat::new(HttpAuthentication::basic(auth::handle_auth)), )) .configure(|c| configure_app(c, &inside_config)), ) @@ -292,7 +298,7 @@ fn create_tcp_listener(addr: SocketAddr) -> io::Result { fn configure_header(conf: &MiniserveConfig) -> middleware::DefaultHeaders { conf.header.iter().flatten().fold( middleware::DefaultHeaders::new(), - |headers, (header_name, header_value)| headers.header(header_name, header_value), + |headers, (header_name, header_value)| headers.add((header_name, header_value)), ) } @@ -353,14 +359,14 @@ async fn favicon() -> impl Responder { let logo = include_str!("../data/logo.svg"); HttpResponse::Ok() .insert_header(ContentType(mime::IMAGE_SVG)) - .message_body(logo.into()) + .body(logo) } async fn css() -> impl Responder { let css = include_str!(concat!(env!("OUT_DIR"), "/style.css")); HttpResponse::Ok() .insert_header(ContentType(mime::TEXT_CSS)) - .message_body(css.into()) + .message_body(BoxBody::new(css)) } // Prints to the console two inverted QrCodes side by side. -- cgit v1.2.3 From dd665a4c7e97a8a7513f38ad9293cd8edbe136df Mon Sep 17 00:00:00 2001 From: Ali MJ Al-Nasrawy Date: Sat, 5 Feb 2022 23:30:47 +0300 Subject: update to actix-web v4.0-rc.2 --- src/config.rs | 37 ++++++++++++++----------------------- src/errors.rs | 9 +++++---- src/listing.rs | 7 +++---- src/main.rs | 8 ++++---- 4 files changed, 26 insertions(+), 35 deletions(-) (limited to 'src') diff --git a/src/config.rs b/src/config.rs index 9bb6928..ccff7e3 100644 --- a/src/config.rs +++ b/src/config.rs @@ -11,7 +11,7 @@ use anyhow::{Context, Result}; use http::HeaderMap; #[cfg(feature = "tls")] -use rustls_pemfile::{certs, pkcs8_private_keys}; +use rustls_pemfile as pemfile; use crate::{args::CliArgs, auth::RequiredAuth}; @@ -163,31 +163,22 @@ impl MiniserveConfig { let key_file = &mut BufReader::new( File::open(&tls_key).context(format!("Couldn't access TLS key {:?}", tls_key))?, ); - let cert_chain = match rustls_pemfile::read_one(cert_file) { - Ok(item) => match item { - Some(item) => match item { - rustls_pemfile::Item::X509Certificate(item) => item, - _ => return Err(anyhow!("Certfile is not a X509Certificate")), - }, - None => { - return Err(anyhow!( - "Certfile does not contain any recognized certificates" - )) - } - }, - _ => return Err(anyhow!("Could not read certfile")), - }; - let mut keys = - pkcs8_private_keys(key_file).map_err(|_| anyhow!("Couldn't load private key"))?; + let cert_chain = pemfile::certs(cert_file).context("Reading cert file")?; + let key = pemfile::read_all(key_file) + .context("Reading private key file")? + .into_iter() + .filter_map(|item| match item { + pemfile::Item::RSAKey(key) | pemfile::Item::PKCS8Key(key) => Some(key), + _ => None, + }) + .next() + .ok_or(anyhow!("No supported private key in file"))?; let server_config = rustls::ServerConfig::builder() - .with_safe_default_cipher_suites() - .with_safe_default_kx_groups() - .with_safe_default_protocol_versions() - .unwrap() + .with_safe_defaults() .with_no_client_auth() .with_single_cert( - vec![rustls::Certificate(cert_chain)], - rustls::PrivateKey(keys.remove(0)), + cert_chain.into_iter().map(rustls::Certificate).collect(), + rustls::PrivateKey(key), )?; Some(server_config) } else { diff --git a/src/errors.rs b/src/errors.rs index 70bad5c..5f55514 100644 --- a/src/errors.rs +++ b/src/errors.rs @@ -109,18 +109,19 @@ impl ResponseError for ContextualError { } /// Middleware to convert plain-text error responses to user-friendly web pages -pub fn error_page_middleware( +pub fn error_page_middleware( req: ServiceRequest, srv: &S, ) -> impl Future> + 'static where - S: Service, + S: Service, Error = actix_web::Error>, + B: MessageBody + 'static, S::Future: 'static, { let fut = srv.call(req); async { - let res = fut.await?; + let res = fut.await?.map_into_boxed_body(); if (res.status().is_client_error() || res.status().is_server_error()) && res.headers().get(header::CONTENT_TYPE).map(AsRef::as_ref) @@ -134,7 +135,7 @@ where } } -fn map_error_page<'a>(req: &HttpRequest, head: &mut ResponseHead, body: BoxBody) -> BoxBody { +fn map_error_page(req: &HttpRequest, head: &mut ResponseHead, body: BoxBody) -> BoxBody { let error_msg = match body.try_into_bytes() { Ok(bytes) => bytes, Err(body) => return body, diff --git a/src/listing.rs b/src/listing.rs index 58703c0..9e02598 100644 --- a/src/listing.rs +++ b/src/listing.rs @@ -1,4 +1,3 @@ -use actix_web::body::BoxBody; use actix_web::dev::ServiceResponse; use actix_web::web::Query; use actix_web::{HttpMessage, HttpRequest, HttpResponse}; @@ -15,7 +14,8 @@ use crate::archive::ArchiveMethod; use crate::auth::CurrentUser; use crate::errors::{self, ContextualError}; use crate::renderer; -use percent_encode_sets::PATH_SEGMENT; + +use self::percent_encode_sets::PATH_SEGMENT; /// "percent-encode sets" as defined by WHATWG specs: /// https://url.spec.whatwg.org/#percent-encoded-bytes @@ -157,7 +157,6 @@ pub fn directory_listing( let extensions = req.extensions(); let current_user: Option<&CurrentUser> = extensions.get::(); - use actix_web::dev::BodyEncoding; let conf = req.app_data::().unwrap(); let serve_path = req.path(); @@ -358,7 +357,7 @@ pub fn directory_listing( req.clone(), HttpResponse::Ok() .content_type(archive_method.content_type()) - .encoding(archive_method.content_encoding()) + .append_header(archive_method.content_encoding()) .append_header(("Content-Transfer-Encoding", "binary")) .append_header(( "Content-Disposition", diff --git a/src/main.rs b/src/main.rs index 5b239e4..7f1944f 100644 --- a/src/main.rs +++ b/src/main.rs @@ -6,8 +6,6 @@ use std::thread; use std::time::Duration; use actix_files::NamedFile; -use actix_web::body::BoxBody; -use actix_web::middleware::Compat; use actix_web::web; use actix_web::{http::header::ContentType, Responder}; use actix_web::{middleware, App, HttpRequest, HttpResponse}; @@ -200,7 +198,9 @@ async fn run(miniserve_config: MiniserveConfig) -> Result<(), ContextualError> { web::scope(inside_config.random_route.as_deref().unwrap_or("")) .wrap(middleware::Condition::new( !inside_config.auth.is_empty(), - Compat::new(HttpAuthentication::basic(auth::handle_auth)), + actix_web::middleware::Compat::new(HttpAuthentication::basic( + auth::handle_auth, + )), )) .configure(|c| configure_app(c, &inside_config)), ) @@ -366,7 +366,7 @@ async fn css() -> impl Responder { let css = include_str!(concat!(env!("OUT_DIR"), "/style.css")); HttpResponse::Ok() .insert_header(ContentType(mime::TEXT_CSS)) - .message_body(BoxBody::new(css)) + .body(css) } // Prints to the console two inverted QrCodes side by side. -- cgit v1.2.3