diff --git a/Cargo.lock b/Cargo.lock index 0ffee99..adcffea 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -1185,6 +1185,15 @@ dependencies = [ "wasm-bindgen", ] +[[package]] +name = "keccak" +version = "0.1.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "3afef3b6eff9ce9d8ff9b3601125eec7f0c8cbac7abd14f355d053fa56c98768" +dependencies = [ + "cpufeatures", +] + [[package]] name = "kernel32-sys" version = "0.2.2" @@ -2071,11 +2080,13 @@ name = "rot" version = "0.1.0" dependencies = [ "chrono", + "hex", "rocket", "rocket_dyn_templates", "sea-orm", "sea-orm-migration", "serde", + "sha3", ] [[package]] @@ -2377,6 +2388,16 @@ dependencies = [ "digest", ] +[[package]] +name = "sha3" +version = "0.10.6" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "bdf0c33fae925bdc080598b84bc15c55e7b9a4a43b3c704da051f977469691c9" +dependencies = [ + "digest", + "keccak", +] + [[package]] name = "sharded-slab" version = "0.1.4" diff --git a/Cargo.toml b/Cargo.toml index 92faafe..1207e8c 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -9,7 +9,8 @@ edition = "2021" sea-orm = { version = "^0", features = [ "sqlx-sqlite", "runtime-tokio-rustls", "macros" ] } sea-orm-migration = { version = "0.11", features = [ "runtime-tokio-rustls", "sqlx-sqlite" ] } serde = { version = "1.0", features = [ "derive" ]} -rocket = "0.5.0-rc.2" +rocket = { version = "0.5.0-rc.2", features = ["secrets"]} rocket_dyn_templates = { version = "0.1.0-rc.2", features= ["tera"] } chrono = { version = "0.4", features = ["serde"]} - +sha3 = "0.10" +hex = "0.4" diff --git a/db.sqlite b/db.sqlite index 69e8f0e..04ccdc8 100644 Binary files a/db.sqlite and b/db.sqlite differ diff --git a/migration/src/m20230209_063357_create_user.rs b/migration/src/m20230209_063357_create_user.rs index cd6018a..21de6f7 100644 --- a/migration/src/m20230209_063357_create_user.rs +++ b/migration/src/m20230209_063357_create_user.rs @@ -19,6 +19,7 @@ impl MigrationTrait for Migration { .primary_key(), ) .col(ColumnDef::new(User::Name).string().not_null().unique_key()) + .col(ColumnDef::new(User::Pw).string()) .col( ColumnDef::new(User::IsCox) .boolean() @@ -49,6 +50,7 @@ pub enum User { Table, Id, Name, + Pw, IsCox, IsAdmin, } diff --git a/src/models/all.rs b/src/models/all.rs index 89500f1..95a73d1 100644 --- a/src/models/all.rs +++ b/src/models/all.rs @@ -1,4 +1,4 @@ -use sea_orm::{DatabaseConnection, ModelTrait}; +use sea_orm::{ColumnTrait, DatabaseConnection, EntityTrait, QueryFilter}; use serde::Serialize; use super::{day, trip, user}; @@ -10,16 +10,8 @@ pub struct TripWithUser { } impl TripWithUser { - async fn new(trip: trip::Model, db: &DatabaseConnection) -> Self { - Self { - trip: trip.clone(), - user: trip - .find_related(user::Entity) - .one(db) - .await - .unwrap() - .unwrap(), - } + fn new(trip: trip::Model, user: user::Model) -> Self { + Self { trip, user } } } @@ -32,8 +24,17 @@ pub struct DayWithTrips { impl DayWithTrips { pub async fn new(day: day::Model, db: &DatabaseConnection) -> Self { let mut trips = Vec::new(); - for trip in day.find_related(trip::Entity).all(db).await.unwrap() { - trips.push(TripWithUser::new(trip, db).await); + + let trips_with_users: Vec<(trip::Model, Option)> = trip::Entity::find() + .filter(trip::Column::Day.eq(day.day)) + .find_also_related(user::Entity) + .all(db) + .await + .unwrap(); + println!("{:#?}", trips_with_users); + + for (trip, users) in trips_with_users { + trips.push(TripWithUser::new(trip, users.unwrap())); } Self { day, trips } diff --git a/src/models/user.rs b/src/models/user.rs index 5139e92..dc763cb 100644 --- a/src/models/user.rs +++ b/src/models/user.rs @@ -14,6 +14,7 @@ pub struct Model { #[sea_orm(primary_key)] pub id: i32, pub name: String, + pub pw: Option, pub is_cox: bool, pub is_admin: bool, } @@ -53,7 +54,7 @@ impl<'r> FromRequest<'r> for Model { type Error = UserError; async fn from_request(req: &'r Request<'_>) -> request::Outcome { - match req.cookies().get("name") { + match req.cookies().get_private("name") { Some(name) => { let db = req.guard::<&'r State>(); let name = name.value(); @@ -70,7 +71,7 @@ impl<'r> FromRequest<'r> for AdminUser { type Error = UserError; async fn from_request(req: &'r Request<'_>) -> request::Outcome { - match req.cookies().get("name") { + match req.cookies().get_private("name") { Some(name) => { let db = req.guard::<&'r State>(); let name = name.value(); diff --git a/src/rest/mod.rs b/src/rest/mod.rs index 8c78041..671be62 100644 --- a/src/rest/mod.rs +++ b/src/rest/mod.rs @@ -14,6 +14,7 @@ use rocket::{ }; use rocket_dyn_templates::{context, Template}; use sea_orm::{Database, DatabaseConnection}; +use sha3::{Digest, Sha3_256}; use super::models::{all::DayWithTrips, day, user}; @@ -35,17 +36,18 @@ impl Deref for NaiveDateForm { } } -#[get("/")] -async fn index(db: &State, user: user::Model) -> Template { +#[get("/?")] +async fn index(db: &State, user: user::Model, all: Option) -> Template { let mut data = Vec::new(); let mut show_next_n_days = 6; - if user.is_cox { - let end_of_year = NaiveDate::from_ymd_opt(Local::now().year(), 5, 31).unwrap(); - show_next_n_days = end_of_year - .signed_duration_since(Local::now().date_naive()) - .num_days() - + 1; + if let Some(_) = all { + if user.is_cox { + let end_of_year = NaiveDate::from_ymd_opt(Local::now().year(), 12, 31).unwrap(); + show_next_n_days = end_of_year + .signed_duration_since(Local::now().date_naive()) + .num_days(); + } } for i in 0..show_next_n_days { @@ -65,17 +67,45 @@ fn name() -> Template { #[derive(FromForm)] struct NameForm { name: String, + pw: Option, } #[put("/name", data = "")] -fn savename(name: Form, cookies: &CookieJar) -> Redirect { - cookies.add(Cookie::new("name", name.name.clone())); +async fn savename( + name: Form, + cookies: &CookieJar<'_>, + db: &State, +) -> Redirect { + let user = user::Model::find_or_create_user(&name.name, db.inner()).await; + match user.pw { + Some(pw) => { + match &name.pw { + Some(entered_pw) => { + let mut hasher = Sha3_256::new(); + hasher.update(entered_pw); + let entered_pw = hasher.finalize(); + + if hex::encode(entered_pw) == pw { + cookies.add_private(Cookie::new("name", name.name.clone())); + } else { + Redirect::to("/"); // Wrong PW + } + } + None => { + Redirect::to("/"); // No PW supplied + } + } + } + None => { + cookies.add_private(Cookie::new("name", name.name.clone())); + } + } Redirect::to("/") } #[get("/logout")] fn logout(cookies: &CookieJar) -> Redirect { - cookies.remove(Cookie::new("name", "")); + cookies.remove_private(Cookie::new("name", "")); Redirect::to("/") } diff --git a/src/rest/restuser.rs b/src/rest/restuser.rs index d2f5244..704d238 100644 --- a/src/rest/restuser.rs +++ b/src/rest/restuser.rs @@ -1,10 +1,9 @@ use rocket::{form::Form, response::Redirect, Route, State}; use rocket_dyn_templates::{context, Template}; use sea_orm::{ActiveModelTrait, DatabaseConnection, EntityTrait, Set}; +use sha3::{Digest, Sha3_256}; -use crate::models::{day, user}; - -use super::NaiveDateForm; +use crate::models::user; #[get("/")] async fn index(db: &State, user: user::AdminUser) -> Template { @@ -15,6 +14,7 @@ async fn index(db: &State, user: user::AdminUser) -> Templat #[derive(FromForm)] struct UserEditForm { + pw: Option, is_cox: bool, is_admin: bool, } @@ -26,12 +26,22 @@ async fn update( data: Form, _user: user::AdminUser, ) -> Redirect { - let new_user = user::ActiveModel { + let mut new_user = user::ActiveModel { id: Set(id), is_cox: Set(data.is_cox), is_admin: Set(data.is_admin), ..Default::default() }; + if let Some(pw) = &data.pw { + if pw != "" { + let mut hasher = Sha3_256::new(); + hasher.update(pw); + let entered_pw = hasher.finalize(); + + let pw = hex::encode(entered_pw); + new_user.pw = Set(Some(pw)); + } + } new_user.update(db.inner()).await.unwrap(); Redirect::to("/user") diff --git a/templates/index.html.tera b/templates/index.html.tera index d2ac294..779e533 100644 --- a/templates/index.html.tera +++ b/templates/index.html.tera @@ -83,5 +83,9 @@ {% endfor %} +{% if user.is_cox %} + Alle heurigen Ausfahrten anzeigen +{% endif %} + {% endblock content %} diff --git a/templates/name.html.tera b/templates/name.html.tera index 57e0bc8..c3d09b6 100644 --- a/templates/name.html.tera +++ b/templates/name.html.tera @@ -3,8 +3,13 @@
+ + + + +
{% endblock content %} diff --git a/templates/user/index.html.tera b/templates/user/index.html.tera index 858e734..740621d 100644 --- a/templates/user/index.html.tera +++ b/templates/user/index.html.tera @@ -5,6 +5,7 @@ Name + Pw Cox Admin Action @@ -16,6 +17,12 @@
{{user.name}} + + {% if user.pw %} + + {% endif %} + +