use std::{ ffi::OsStr, path::{ Component, Path, }, }; use maplit::*; use tokio::runtime::Runtime; #[test] fn pretty_print_bytes () { for (input_after, expected_before, expected_after) in vec! [ (1, "0 B", "1 B"), (1024, "1023 B", "1 KiB"), (1024 + 512, "1 KiB", "2 KiB"), (1023 * 1024 + 512, "1023 KiB", "1 MiB"), ((1024 + 512) * 1024, "1 MiB", "2 MiB"), (1023 * 1024 * 1024 + 512 * 1024, "1023 MiB", "1 GiB"), ((1024 + 512) * 1024 * 1024, "1 GiB", "2 GiB"), ].into_iter () { let actual = super::pretty_print_bytes (input_after - 1); assert_eq! (&actual, expected_before); let actual = super::pretty_print_bytes (input_after); assert_eq! (&actual, expected_after); } } #[test] fn i_hate_paths () { let mut components = Path::new ("/home/user").components (); assert_eq! (components.next (), Some (Component::RootDir)); assert_eq! (components.next (), Some (Component::Normal (OsStr::new ("home")))); assert_eq! (components.next (), Some (Component::Normal (OsStr::new ("user")))); assert_eq! (components.next (), None); let mut components = Path::new ("./home/user").components (); assert_eq! (components.next (), Some (Component::CurDir)); assert_eq! (components.next (), Some (Component::Normal (OsStr::new ("home")))); assert_eq! (components.next (), Some (Component::Normal (OsStr::new ("user")))); assert_eq! (components.next (), None); let mut components = Path::new (".").components (); assert_eq! (components.next (), Some (Component::CurDir)); assert_eq! (components.next (), None); } #[test] fn file_server () { use std::path::PathBuf; #[cfg (test)] use always_equal::test::AlwaysEqual; use ptth_core::{ http_serde::Method, }; use super::*; tracing_subscriber::fmt ().try_init ().ok (); let rt = Runtime::new ().expect ("Can't create runtime"); rt.block_on (async { let file_server_root = PathBuf::from ("./"); let headers = Default::default (); { use internal::Response::*; use crate::file_server::FileServerError; let bad_passwords_path = "/files/src/bad_passwords.txt"; for (uri_path, expected) in vec! [ ("/", Root), ("/files", NotFound), ("/files/?", InvalidQuery), ("/files/src", Redirect ("src/".to_string ())), ("/files/src/?", InvalidQuery), (bad_passwords_path, ServeFile (internal::ServeFileParams { send_body: true, range: range::ValidParsed { range: 0..1_048_576, range_requested: false, }, file: AlwaysEqual::testing_blank (), })), ("/files/test/test.md", ServeFile (internal::ServeFileParams { send_body: true, range: range::ValidParsed { range: 0..144, range_requested: false, }, file: AlwaysEqual::testing_blank (), })), ] { let resp = internal::serve_all ( &file_server_root, Method::Get, uri_path, &headers, None ).await; assert_eq! (resp.expect ("This block only tests Ok (_) responses"), expected); } for (uri_path, checker) in vec! [ ("/ ", |e| match e { FileServerError::InvalidUri (_) => (), e => panic! ("Expected InvalidUri, got {:?}", e), }), ] { let resp = internal::serve_all ( &file_server_root, Method::Get, uri_path, &headers, None ).await; checker (resp.unwrap_err ()); } let resp = internal::serve_all ( &file_server_root, Method::Get, bad_passwords_path, &hashmap! { "range".into () => b"bytes=0-2000000".to_vec (), }, None ).await; assert_eq! (resp.expect ("Should be Ok (_)"), RangeNotSatisfiable (1_048_576)); let resp = internal::serve_all ( &file_server_root, Method::Head, bad_passwords_path, &headers, None ).await; assert_eq! (resp.expect ("Should be Ok (_)"), ServeFile (internal::ServeFileParams { send_body: false, range: range::ValidParsed { range: 0..1_048_576, range_requested: false, }, file: AlwaysEqual::testing_blank (), })); } }); } #[test] fn parse_uri () { assert! (http::Uri::from_maybe_shared ("/").is_ok ()); }