From a499cb2064aa8d6746e6cb2f85b51a4e62adbd6c Mon Sep 17 00:00:00 2001 From: Tangent Wantwight Date: Wed, 10 Jun 2020 00:36:43 -0400 Subject: [PATCH] Serve client files from server via RustEmbed, so they can be embedded for deployment. --- Cargo.lock | 61 +++++++++++++++++++++++++++++++++++++++++++++++++---- Cargo.toml | 2 ++ src/main.rs | 33 +++++++++++++++++++++++++++-- 3 files changed, 90 insertions(+), 6 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index db5a5ea..e32ba23 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -48,13 +48,14 @@ dependencies = [ "anyhow 1.0.28 (registry+https://github.com/rust-lang/crates.io-index)", "env_logger 0.7.1 (registry+https://github.com/rust-lang/crates.io-index)", "futures 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)", - "futures-util 0.3.5 (registry+https://github.com/rust-lang/crates.io-index)", "log 0.4.8 (registry+https://github.com/rust-lang/crates.io-index)", + "mime_guess 2.0.3 (registry+https://github.com/rust-lang/crates.io-index)", + "rust-embed 5.5.1 (registry+https://github.com/rust-lang/crates.io-index)", "serde 1.0.110 (registry+https://github.com/rust-lang/crates.io-index)", "serde_json 1.0.53 (registry+https://github.com/rust-lang/crates.io-index)", "structopt 0.3.14 (registry+https://github.com/rust-lang/crates.io-index)", "tokio 0.2.20 (registry+https://github.com/rust-lang/crates.io-index)", - "warp 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)", + "warp 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)", ] [[package]] @@ -893,6 +894,35 @@ dependencies = [ "winapi 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)", ] +[[package]] +name = "rust-embed" +version = "5.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "rust-embed-impl 5.5.1 (registry+https://github.com/rust-lang/crates.io-index)", + "rust-embed-utils 5.0.0 (registry+https://github.com/rust-lang/crates.io-index)", + "walkdir 2.3.1 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "rust-embed-impl" +version = "5.5.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "quote 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)", + "rust-embed-utils 5.0.0 (registry+https://github.com/rust-lang/crates.io-index)", + "syn 1.0.19 (registry+https://github.com/rust-lang/crates.io-index)", + "walkdir 2.3.1 (registry+https://github.com/rust-lang/crates.io-index)", +] + +[[package]] +name = "rust-embed-utils" +version = "5.0.0" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "walkdir 2.3.1 (registry+https://github.com/rust-lang/crates.io-index)", +] + [[package]] name = "ryu" version = "1.0.4" @@ -903,6 +933,14 @@ name = "safemem" version = "0.3.3" source = "registry+https://github.com/rust-lang/crates.io-index" +[[package]] +name = "same-file" +version = "1.0.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "winapi-util 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", +] + [[package]] name = "scoped-tls" version = "1.0.0" @@ -1241,6 +1279,16 @@ name = "version_check" version = "0.9.1" source = "registry+https://github.com/rust-lang/crates.io-index" +[[package]] +name = "walkdir" +version = "2.3.1" +source = "registry+https://github.com/rust-lang/crates.io-index" +dependencies = [ + "same-file 1.0.6 (registry+https://github.com/rust-lang/crates.io-index)", + "winapi 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)", + "winapi-util 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)", +] + [[package]] name = "want" version = "0.3.0" @@ -1252,7 +1300,7 @@ dependencies = [ [[package]] name = "warp" -version = "0.2.2" +version = "0.2.3" source = "registry+https://github.com/rust-lang/crates.io-index" dependencies = [ "bytes 0.5.4 (registry+https://github.com/rust-lang/crates.io-index)", @@ -1432,8 +1480,12 @@ dependencies = [ "checksum regex 1.3.7 (registry+https://github.com/rust-lang/crates.io-index)" = "a6020f034922e3194c711b82a627453881bc4682166cabb07134a10c26ba7692" "checksum regex-syntax 0.6.17 (registry+https://github.com/rust-lang/crates.io-index)" = "7fe5bd57d1d7414c6b5ed48563a2c855d995ff777729dcd91c369ec7fea395ae" "checksum remove_dir_all 0.5.2 (registry+https://github.com/rust-lang/crates.io-index)" = "4a83fa3702a688b9359eccba92d153ac33fd2e8462f9e0e3fdf155239ea7792e" +"checksum rust-embed 5.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "3a17890cbd0fae97c2006fa1ecec9554946443c319f4dd8cd8d3b92031725161" +"checksum rust-embed-impl 5.5.1 (registry+https://github.com/rust-lang/crates.io-index)" = "60cacc306d294556771c6e92737ba7e6be0264144bc46dd713a14ef384b0d6b8" +"checksum rust-embed-utils 5.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "97655158074ccb2d2cfb1ccb4c956ef0f4054e43a2c1e71146d4991e6961e105" "checksum ryu 1.0.4 (registry+https://github.com/rust-lang/crates.io-index)" = "ed3d612bc64430efeb3f7ee6ef26d590dce0c43249217bddc62112540c7941e1" "checksum safemem 0.3.3 (registry+https://github.com/rust-lang/crates.io-index)" = "ef703b7cb59335eae2eb93ceb664c0eb7ea6bf567079d843e09420219668e072" +"checksum same-file 1.0.6 (registry+https://github.com/rust-lang/crates.io-index)" = "93fc1dc3aaa9bfed95e02e6eadabb4baf7e3078b0bd1b4d7b6b0b68378900502" "checksum scoped-tls 1.0.0 (registry+https://github.com/rust-lang/crates.io-index)" = "ea6a9290e3c9cf0f18145ef7ffa62d68ee0bf5fcd651017e586dc7fd5da448c2" "checksum serde 1.0.110 (registry+https://github.com/rust-lang/crates.io-index)" = "99e7b308464d16b56eba9964e4972a3eee817760ab60d88c3f86e1fecb08204c" "checksum serde_derive 1.0.110 (registry+https://github.com/rust-lang/crates.io-index)" = "818fbf6bfa9a42d3bfcaca148547aa00c7b915bec71d1757aa2d44ca68771984" @@ -1475,8 +1527,9 @@ dependencies = [ "checksum vec_map 0.8.2 (registry+https://github.com/rust-lang/crates.io-index)" = "f1bddf1187be692e79c5ffeab891132dfb0f236ed36a43c7ed39f1165ee20191" "checksum version_check 0.1.5 (registry+https://github.com/rust-lang/crates.io-index)" = "914b1a6776c4c929a602fafd8bc742e06365d4bcbe48c30f9cca5824f70dc9dd" "checksum version_check 0.9.1 (registry+https://github.com/rust-lang/crates.io-index)" = "078775d0255232fb988e6fccf26ddc9d1ac274299aaedcedce21c6f72cc533ce" +"checksum walkdir 2.3.1 (registry+https://github.com/rust-lang/crates.io-index)" = "777182bc735b6424e1a57516d35ed72cb8019d85c8c9bf536dccb3445c1a2f7d" "checksum want 0.3.0 (registry+https://github.com/rust-lang/crates.io-index)" = "1ce8a968cb1cd110d136ff8b819a556d6fb6d919363c61534f6860c7eb172ba0" -"checksum warp 0.2.2 (registry+https://github.com/rust-lang/crates.io-index)" = "54cd1e2b3eb3539284d88b76a9afcf5e20f2ef2fab74db5b21a1c30d7d945e82" +"checksum warp 0.2.3 (registry+https://github.com/rust-lang/crates.io-index)" = "0e95175b7a927258ecbb816bdada3cc469cb68593e7940b96a60f4af366a9970" "checksum wasi 0.9.0+wasi-snapshot-preview1 (registry+https://github.com/rust-lang/crates.io-index)" = "cccddf32554fecc6acb585f82a32a72e28b48f8c4c1883ddfeeeaa96f7d8e519" "checksum winapi 0.2.8 (registry+https://github.com/rust-lang/crates.io-index)" = "167dc9d6949a9b857f3451275e911c3f44255842c1f7a76f33c55103a909087a" "checksum winapi 0.3.8 (registry+https://github.com/rust-lang/crates.io-index)" = "8093091eeb260906a183e6ae1abdba2ef5ef2257a21801128899c3fc699229c6" diff --git a/Cargo.toml b/Cargo.toml index e50a984..a596671 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -9,6 +9,8 @@ anyhow = "1" env_logger = "0.7" futures = "0.3" log = "0.4" +mime_guess = "2" +rust-embed = "5" structopt = "0.3" serde = {version = "1", features = ["derive"]} serde_json = "1" diff --git a/src/main.rs b/src/main.rs index 0f97999..87133ec 100644 --- a/src/main.rs +++ b/src/main.rs @@ -8,12 +8,16 @@ use net::{ server::{run_client, Handle, Server}, ClientMessage, ServerMessage, }; +use rust_embed::RustEmbed; use serde_json::{from_str, to_string}; use std::net::ToSocketAddrs; use stream::FuturesUnordered; use structopt::StructOpt; -use warp::{path, serve, ws, ws::Ws, Filter}; +use warp::{ + http::HeaderValue, path, reject, reply::Response, serve, ws, ws::Ws, Filter, Rejection, Reply, +}; use ws::{Message, WebSocket}; +use path::Tail; pub mod net; @@ -26,6 +30,10 @@ struct Args { listen: String, } +#[derive(RustEmbed)] +#[folder = "dist/"] +struct Assets; + #[tokio::main] async fn main() -> Result<()> { env_logger::init(); @@ -47,7 +55,10 @@ async fn main() -> Result<()> { }); // assemble routes - let routes = path!("base2020.ws").and(socket_handler); + let routes = path!("base2020.ws").and(socket_handler) + .or(path::end().and_then(serve_index)) + .or(path::tail().and_then(serve_asset)) + ; let addrs = args .listen @@ -64,6 +75,24 @@ async fn main() -> Result<()> { Ok(()) } +async fn serve_index() -> Result { + serve_file("index.html") +} + +async fn serve_asset(path: Tail) -> Result { + serve_file(path.as_str()) +} + +fn serve_file(path: &str) -> Result { + let asset = Assets::get(path).ok_or_else(reject::not_found)?; + let mime_type = mime_guess::from_path(path).first_or_octet_stream(); + + let mut response = Response::new(asset.into()); + let type_header = HeaderValue::from_str(mime_type.as_ref()).unwrap(); + response.headers_mut().insert("content-type", type_header); + Ok(response) +} + async fn handle_socket(game_server: Handle, websocket: WebSocket) -> Result<()> { let (sink, source) = websocket.split();