From 828ee6c533930e2467f130aa6985089a8f2ef94c Mon Sep 17 00:00:00 2001 From: Jef Roosens Date: Fri, 1 Apr 2022 13:29:34 +0200 Subject: [PATCH] Bad attempt at streaming a tar.gz file --- .cargo/config.toml | 4 ++ Cargo.lock | 91 ++++++++++++++++++++++++++++++++++++++++++++++ Cargo.toml | 6 ++- src/main.rs | 35 +++++++++++++++--- 4 files changed, 129 insertions(+), 7 deletions(-) create mode 100644 .cargo/config.toml diff --git a/.cargo/config.toml b/.cargo/config.toml new file mode 100644 index 0000000..d99914d --- /dev/null +++ b/.cargo/config.toml @@ -0,0 +1,4 @@ +# Used for testing locally +[env] +API_KEY = "test" +DATA_DIR = "data" diff --git a/Cargo.lock b/Cargo.lock index d8af18c..b0778bc 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -2,6 +2,12 @@ # It is not intended for manual editing. version = 3 +[[package]] +name = "adler" +version = "1.0.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f26201604c87b1e01bd3d98f8d5d9a8fcbb815e8cedb41ffccbeb4bf593a35fe" + [[package]] name = "ansi_term" version = "0.12.1" @@ -11,6 +17,19 @@ dependencies = [ "winapi", ] +[[package]] +name = "async-compression" +version = "0.3.12" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "f2bf394cfbbe876f0ac67b13b6ca819f9c9f2fb9ec67223cceb1555fbab1c31a" +dependencies = [ + "flate2", + "futures-core", + "memchr", + "pin-project-lite", + "tokio", +] + [[package]] name = "async-trait" version = "0.1.53" @@ -73,6 +92,12 @@ dependencies = [ "mime", ] +[[package]] +name = "base64" +version = "0.13.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "904dfeac50f3cdaba28fc6f57fdcddb75f49ed61346676a78c4ffe55877802fd" + [[package]] name = "bitflags" version = "1.3.2" @@ -91,6 +116,39 @@ version = "1.0.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "baf1de4339761588bc0619e3cbc0120ee582ebb74b53b4efbf79117bd2da40fd" +[[package]] +name = "crc32fast" +version = "1.3.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "b540bd8bc810d3885c6ea91e2018302f68baba2129ab3e88f32389ee9370880d" +dependencies = [ + "cfg-if", +] + +[[package]] +name = "filetime" +version = "0.2.15" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "975ccf83d8d9d0d84682850a38c8169027be83368805971cc4f238c2b245bc98" +dependencies = [ + "cfg-if", + "libc", + "redox_syscall", + "winapi", +] + +[[package]] +name = "flate2" +version = "1.0.22" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "1e6988e897c1c9c485f43b47a529cef42fde0547f9d8d41a7062518f1d8fc53f" +dependencies = [ + "cfg-if", + "crc32fast", + "libc", + "miniz_oxide", +] + [[package]] name = "fnv" version = "1.0.7" @@ -334,6 +392,16 @@ dependencies = [ "unicase", ] +[[package]] +name = "miniz_oxide" +version = "0.4.4" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a92518e98c078586bc6c934028adcca4c92a53d6a958196de835170a01d84e4b" +dependencies = [ + "adler", + "autocfg", +] + [[package]] name = "mio" version = "0.8.2" @@ -557,8 +625,10 @@ dependencies = [ name = "site-backend" version = "0.0.0" dependencies = [ + "async-compression", "axum", "hyper", + "tar", "tokio", "tower-http", "tracing", @@ -604,6 +674,17 @@ version = "0.1.1" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "20518fe4a4c9acf048008599e464deb21beeae3d3578418951a189c235a7a9a8" +[[package]] +name = "tar" +version = "0.4.38" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "4b55807c0344e1e6c04d7c965f5289c39a8d94ae23ed5c0b57aabac549f871c6" +dependencies = [ + "filetime", + "libc", + "xattr", +] + [[package]] name = "thread_local" version = "1.1.4" @@ -681,6 +762,7 @@ version = "0.2.5" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "aba3f3efabf7fb41fae8534fc20a817013dd1c12cb45441efb6c82e6556b4cd8" dependencies = [ + "base64", "bitflags", "bytes", "futures-core", @@ -889,3 +971,12 @@ name = "windows_x86_64_msvc" version = "0.34.0" source = "registry+https://github.com/rust-lang/crates.io-index" checksum = "d19538ccc21819d01deaf88d6a17eae6596a12e9aafdbb97916fb49896d89de9" + +[[package]] +name = "xattr" +version = "0.2.2" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "244c3741f4240ef46274860397c7c74e50eb23624996930e484c16679633a54c" +dependencies = [ + "libc", +] diff --git a/Cargo.toml b/Cargo.toml index d0d2248..f4e66b4 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -7,9 +7,11 @@ publish = false # See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html [dependencies] -axum = "0.5.0" +axum = { version = "0.5.0" } hyper = { version = "0.14.18", features = ["full"] } tokio = { version = "1.17.0", features = ["full"] } tracing = "0.1.32" tracing-subscriber = {version = "0.3.9", features = ["env-filter"] } -tower-http = { version = "0.2.5", features = ["fs", "trace"] } +tower-http = { version = "0.2.5", features = ["fs", "trace", "auth"] } +tar = "0.4.38" +async-compression = { version = "0.3.12", features = ["tokio", "gzip"] } diff --git a/src/main.rs b/src/main.rs index 07b17e2..60332e4 100644 --- a/src/main.rs +++ b/src/main.rs @@ -1,6 +1,14 @@ -use axum::{http::StatusCode, routing::get_service, Router}; +use async_compression::tokio::bufread::GzipDecoder; +use axum::{ + extract::BodyStream, + http::StatusCode, + routing::{get_service, post}, + Router, +}; +use hyper::{Body, Request}; use std::net::SocketAddr; -use tower_http::{services::ServeDir, trace::TraceLayer}; +use tar::Archive; +use tower_http::{auth::RequireAuthorizationLayer, services::ServeDir, trace::TraceLayer}; use tracing_subscriber::{layer::SubscriberExt, util::SubscriberInitExt}; #[tokio::main] @@ -14,10 +22,20 @@ async fn main() { .with(tracing_subscriber::fmt::layer()) .init(); + // Get required variables from env vars + let api_key = std::env::var("API_KEY").expect("No API_KEY was provided."); + let data_dir = std::env::var("DATA_DIR").expect("No DATA_DIR was provided."); + + std::fs::create_dir_all(&data_dir).unwrap(); + let app = Router::new() - .nest( - "/", - get_service(ServeDir::new("./static")).handle_error( + .route( + "/api/deploy", + post(post_deploy).layer(RequireAuthorizationLayer::bearer(&api_key)), + ) + // The fallback option is to serve the actual static files + .fallback( + get_service(ServeDir::new(format!("{}/static", data_dir))).handle_error( |error: std::io::Error| async move { ( StatusCode::INTERNAL_SERVER_ERROR, @@ -35,3 +53,10 @@ async fn main() { .await .unwrap(); } + +async fn post_deploy(body: BodyStream) { + // let tar = GzDecoder::new(body); + let tar = GzipDecoder::new(body); + let mut archive = Archive::new(tar); + archive.unpack("./static").unwrap(); +}