From 339d6f43021e7d671cd1f50cc1016955aa39c88b Mon Sep 17 00:00:00 2001 From: Cory Buecker Date: Mon, 7 Oct 2024 06:51:50 -0500 Subject: [PATCH] chore(main): reorganize background jobs --- src/jobs.rs | 1 + src/jobs/clear_sessions.rs | 26 +++++++++++ src/jobs/convert_goals.rs | 18 +++++--- src/main.rs | 93 +++----------------------------------- src/utilities.rs | 1 + src/utilities/tera.rs | 46 +++++++++++++++++++ 6 files changed, 93 insertions(+), 92 deletions(-) create mode 100644 src/jobs/clear_sessions.rs create mode 100644 src/utilities/tera.rs diff --git a/src/jobs.rs b/src/jobs.rs index 75c1680..e9976f6 100644 --- a/src/jobs.rs +++ b/src/jobs.rs @@ -1 +1,2 @@ +pub mod clear_sessions; pub mod convert_goals; diff --git a/src/jobs/clear_sessions.rs b/src/jobs/clear_sessions.rs new file mode 100644 index 0000000..bf2d8ad --- /dev/null +++ b/src/jobs/clear_sessions.rs @@ -0,0 +1,26 @@ +use crate::{models::user::User, mongo_client}; +use bson::doc; +use chrono::Utc; +use tracing::{error, info}; + +pub async fn clear_sessions() { + info!("clearing old sessions at {}", Utc::now()); + let mongo = mongo_client().await.unwrap(); + + let update_result = mongo + .default_database() + .unwrap() + .collection::("users") + .update_many( + doc! {}, + doc! {"$pull": doc! {"sessions": doc! {"expiration": doc! { "$lte": Utc::now()}}}}, + ) + .await; + + match update_result { + Ok(_) => {} + Err(err) => { + error!("{}", err); + } + } +} diff --git a/src/jobs/convert_goals.rs b/src/jobs/convert_goals.rs index f3eec94..7fc6635 100644 --- a/src/jobs/convert_goals.rs +++ b/src/jobs/convert_goals.rs @@ -1,10 +1,18 @@ -use crate::models::{envelope::Envelope, goal::Goal}; +use crate::{ + models::{envelope::Envelope, goal::Goal}, + mongo_client, +}; use bson::{doc, oid::ObjectId}; use chrono::Utc; -use mongodb::ClientSession; use std::str::FromStr; +use tracing::info; + +pub async fn convert_goals() -> Result { + info!("converting goals to envelopes at {}", Utc::now()); + + let mongo = mongo_client().await?; + let mut session = mongo.start_session().await?; -pub async fn convert_goals(mut session: ClientSession) -> Result { session.start_transaction().await?; let envelopes = session @@ -101,9 +109,7 @@ mod tests { .await .unwrap(); - let session = client.start_session().await.unwrap(); - - match convert_goals(session).await { + match convert_goals().await { Ok(result) => println!("{}", result), Err(error) => println!("conversion error: {}", error), }; diff --git a/src/main.rs b/src/main.rs index dd2db70..ef980f1 100644 --- a/src/main.rs +++ b/src/main.rs @@ -10,15 +10,13 @@ use axum::{ }; use axum_extra::extract::cookie::Key; use bson::doc; -use chrono::{Local, Utc}; -use models::user::User; +use jobs::{ + clear_sessions::{clear_sessions}, + convert_goals::convert_goals, +}; use mongodb::Client; use serde::Serialize; -use std::{ - collections::HashMap, - env, - time::{Duration, SystemTime}, -}; +use std::{env, time::Duration}; use tera::{Context, Tera}; use tokio::{ select, @@ -27,6 +25,7 @@ use tokio::{ sync::mpsc, time::interval, }; +use utilities::tera::{digest_asset, extract_id}; mod authenticated; use tower_http::{ services::ServeDir, @@ -68,92 +67,14 @@ impl FromRef for Key { } } -pub fn extract_id() -> impl tera::Filter { - return |value: &tera::Value, - args: &HashMap| - -> tera::Result { - debug!("{}", value); - debug!("{:#?}", args); - - let id = value.get("_id"); - - match id { - None => Err(tera::Error::msg("could not find id field".to_string())), - Some(id) => Ok(tera::Value::String( - id["$oid"].to_string().replace("\"", ""), - )), - } - }; -} - -pub fn digest_asset() -> impl tera::Function { - let key = SystemTime::now(); - let key = key - .duration_since(SystemTime::UNIX_EPOCH) - .expect("could not generate asset timestamp"); - let key = key.as_secs().to_string(); - - return move |args: &HashMap| -> tera::Result { - match args.get("file") { - Some(file) => { - let mut path = "/assets/".to_string(); - - let Some(file) = file.as_str() else { - return Err("".to_string().into()); - }; - - path.push_str(file); - path.push_str("?v="); - path.push_str(&key); - - Ok(path.into()) - } - None => Err("".to_string().into()), - } - }; -} - -async fn current_time() { - println!("{}", Local::now()) -} - -async fn clear_sessions() { - let mongo = mongo_client().await.unwrap(); - - let update_result = mongo - .default_database() - .unwrap() - .collection::("users") - .update_many( - doc! {}, - doc! {"$pull": doc! {"sessions": doc! {"expiration": doc! { "$lte": Utc::now()}}}}, - ) - .await; - - match update_result { - Ok(_) => {} - Err(err) => { - println!("{}", err); - } - } -} - -async fn convert_goals_wrapper() { - let mongo = mongo_client().await.unwrap(); - let _ = jobs::convert_goals::convert_goals(mongo.start_session().await.unwrap()).await; -} - fn start_background_jobs() -> tokio::task::JoinHandle<()> { spawn(async { let mut interval = interval(Duration::from_millis(60000)); loop { - let h1 = async { current_time().await }; - let h2 = async { current_time().await }; - interval.tick().await; - tokio::join!(h1, h2, clear_sessions(), convert_goals_wrapper()); + let _result = tokio::join!(clear_sessions(), convert_goals()); } }) } diff --git a/src/utilities.rs b/src/utilities.rs index bf4e93c..90174a1 100644 --- a/src/utilities.rs +++ b/src/utilities.rs @@ -1 +1,2 @@ pub mod dates; +pub mod tera; diff --git a/src/utilities/tera.rs b/src/utilities/tera.rs new file mode 100644 index 0000000..432199f --- /dev/null +++ b/src/utilities/tera.rs @@ -0,0 +1,46 @@ +use std::{collections::HashMap, time::SystemTime}; +use tera::{Filter, Value}; +use tracing::debug; + +pub fn extract_id() -> impl Filter { + return |value: &Value, args: &HashMap| -> tera::Result { + debug!("{}", value); + debug!("{:#?}", args); + + let id = value.get("_id"); + + match id { + None => Err(tera::Error::msg("could not find id field".to_string())), + Some(id) => Ok(tera::Value::String( + id["$oid"].to_string().replace("\"", ""), + )), + } + }; +} + +pub fn digest_asset() -> impl tera::Function { + let key = SystemTime::now(); + let key = key + .duration_since(SystemTime::UNIX_EPOCH) + .expect("could not generate asset timestamp"); + let key = key.as_secs().to_string(); + + return move |args: &HashMap| -> tera::Result { + match args.get("file") { + Some(file) => { + let mut path = "/assets/".to_string(); + + let Some(file) = file.as_str() else { + return Err("".to_string().into()); + }; + + path.push_str(file); + path.push_str("?v="); + path.push_str(&key); + + Ok(path.into()) + } + None => Err("".to_string().into()), + } + }; +}