From 139a5b51b64dc6447d0a77bdf92cfcd68ebb8d4e Mon Sep 17 00:00:00 2001 From: Johannes Hoff Date: Sun, 20 Aug 2017 21:59:16 +0200 Subject: [PATCH] Propage database connections; dispatch requests --- src/main.rs | 7 +++---- src/site.rs | 57 +++++++++++++++++++++++++++++++++++++++++++++------- src/state.rs | 17 ++++++++++++++++ 3 files changed, 70 insertions(+), 11 deletions(-) create mode 100644 src/state.rs diff --git a/src/main.rs b/src/main.rs index bafacb7..059131e 100644 --- a/src/main.rs +++ b/src/main.rs @@ -11,6 +11,7 @@ use std::net::SocketAddr; mod db; mod schema; mod site; +mod state; fn args<'a>() -> clap::ArgMatches<'a> { use clap::{App, Arg}; @@ -35,19 +36,17 @@ fn args<'a>() -> clap::ArgMatches<'a> { fn core_main() -> Result<(), Box> { let args = args(); - let db_file = args.value_of("DATABASE").expect("Guaranteed by clap"); + let db_file = args.value_of("DATABASE").expect("Guaranteed by clap").to_owned(); let bind_host = "127.0.0.1".parse().unwrap(); let bind_port = args.value_of("port") .map(|p| p.parse().expect("Guaranteed by validator")) .unwrap_or(8080); - let _db_connection = db::connect_database(db_file, true); - let server = hyper::server::Http::new() .bind( &SocketAddr::new(bind_host, bind_port), - || Ok(site::Site {}) + move || Ok(site::Site::new(state::State::new(db::connect_database(&db_file, true)))) )?; server.run()?; diff --git a/src/site.rs b/src/site.rs index 7ed06fd..97182ed 100644 --- a/src/site.rs +++ b/src/site.rs @@ -3,12 +3,20 @@ use hyper; use hyper::header::ContentType; use hyper::mime; use hyper::server::*; +use state::State; lazy_static! { static ref TEXT_HTML: mime::Mime = "text/html;charset=utf-8".parse().unwrap(); } pub struct Site { + state: State +} + +impl Site { + pub fn new(state: State) -> Site { + Site { state } + } } impl Service for Site { @@ -17,12 +25,47 @@ impl Service for Site { type Error = hyper::Error; type Future = futures::BoxFuture; - fn call(&self, _req: Request) -> Self::Future { - futures::finished( - Response::new() - .with_header(ContentType(TEXT_HTML.clone())) - .with_body(format!("WOOOOOOOOOOT!")) - .with_status(hyper::StatusCode::Ok) - ).boxed() + fn call(&self, req: Request) -> Self::Future { + println!("{} {}", req.method(), req.path()); + + let path = req.path(); + + if path.starts_with("/_") { + futures::finished( + Response::new() + .with_header(ContentType(TEXT_HTML.clone())) + .with_body(format!("Page not found")) + .with_status(hyper::StatusCode::NotFound) + ).boxed() + } else { + assert!(path.starts_with("/")); + match self.state.find_article_by_slug(&path[1..]) { + Ok(Some(article)) => { + futures::finished( + Response::new() + .with_header(ContentType(TEXT_HTML.clone())) + .with_body(format!("Article found.")) + .with_status(hyper::StatusCode::Ok) + ).boxed() + }, + Ok(None) => { + futures::finished( + Response::new() + .with_header(ContentType(TEXT_HTML.clone())) + .with_body(format!("Article not found.")) + .with_status(hyper::StatusCode::NotFound) + ).boxed() + }, + Err(err) => { + eprintln!("Error while servicing request {} {}:\n{:#?}", req.method(), req.path(), err); + futures::finished( + Response::new() + .with_header(ContentType(TEXT_HTML.clone())) + .with_body(format!("Internal server error")) + .with_status(hyper::StatusCode::InternalServerError) + ).boxed() + } + } + } } } diff --git a/src/state.rs b/src/state.rs new file mode 100644 index 0000000..1f87fd2 --- /dev/null +++ b/src/state.rs @@ -0,0 +1,17 @@ +use std; + +use diesel::sqlite::SqliteConnection; + +pub struct State { + db_connection: SqliteConnection +} + +impl State { + pub fn new(db_connection: SqliteConnection) -> State { + State { db_connection } + } + + pub fn find_article_by_slug(&self, slug: &str) -> Result, Box> { + Ok(None) + } +}