diff --git a/rust-backend/Cargo.lock b/rust-backend/Cargo.lock index 4493b96..c1cf722 100644 --- a/rust-backend/Cargo.lock +++ b/rust-backend/Cargo.lock @@ -1135,6 +1135,7 @@ dependencies = [ "hmac", "refinery", "rusqlite", + "serde", "serde_json", "sha2", ] diff --git a/rust-backend/Cargo.toml b/rust-backend/Cargo.toml index dc34cae..3199a8f 100644 --- a/rust-backend/Cargo.toml +++ b/rust-backend/Cargo.toml @@ -7,6 +7,7 @@ edition = "2021" base64 = "0.22.1" sha2 = "0.10.8" hmac = "0.12.1" +serde = "1.0.207" serde_json = "1.0.124" actix-web = "4" actix-utils = "3.0.1" diff --git a/rust-backend/src/main.rs b/rust-backend/src/main.rs index f5f5d38..ab4ae74 100644 --- a/rust-backend/src/main.rs +++ b/rust-backend/src/main.rs @@ -1,8 +1,10 @@ mod auth; +mod models; use actix_web::{get, Responder, HttpResponse, HttpServer, App, web}; -use std::sync::{Mutex, Arc}; -use crate::auth::AuthorizedUser; +use std::sync::{Mutex, MutexGuard, Arc}; +use auth::AuthorizedUser; +use models::Favorite; mod embedded { use refinery::embed_migrations; @@ -29,6 +31,26 @@ async fn authorized(auth: AuthorizedUser) -> impl Responder { HttpResponse::Ok().body(format!("Authorized as {} ({})", auth.username, auth.user_id)) } +#[get("/favorites")] +async fn favorites(auth: AuthorizedUser, data: web::Data) -> impl Responder { + let db = data.database.lock().unwrap(); + + match get_favorites(db, auth.user_id) { + Some(favorites) => HttpResponse::Ok().json(favorites), + None => HttpResponse::InternalServerError().finish(), + } +} + +fn get_favorites(db: MutexGuard<'_, rusqlite::Connection>, user_id: String) -> Option> { + Some( + db.prepare("SELECT * FROM favorites WHERE user_id = :user_id").ok()? + .query_map(&[(":user_id", &user_id)], |row| Favorite::from_row(row)) + .ok()? + .map(|fav| fav.unwrap()) + .collect() + ) +} + #[actix_web::main] async fn main() -> std::io::Result<()> { let _ = dotenvy::dotenv(); @@ -58,6 +80,7 @@ async fn main() -> std::io::Result<()> { })) .service(healthcheck) .service(authorized) + .service(favorites) }) .bind(("0.0.0.0", port))? .run() diff --git a/rust-backend/src/models.rs b/rust-backend/src/models.rs new file mode 100644 index 0000000..f266397 --- /dev/null +++ b/rust-backend/src/models.rs @@ -0,0 +1,23 @@ +use std::string::String; +use serde::Serialize; +use rusqlite::{Row, Error}; + +#[derive(Serialize)] +pub struct Favorite { + pub id: usize, + pub user_id: String, + pub lat: f64, + pub lng: f64, +} + +impl Favorite { + pub fn from_row(row: &Row) -> Result { + Ok(Favorite { + id: row.get("id")?, + user_id: row.get("user_id")?, + lat: row.get("lat")?, + lng: row.get("lng")?, + }) + } +} +