Make use of pool.acquire to prevent out-of-order db-actions

This commit is contained in:
Tobias Reisinger 2023-11-21 03:42:33 +01:00
parent f3d08aab80
commit 271b24b70d
8 changed files with 248 additions and 131 deletions

View file

@ -1,11 +1,11 @@
use log::{info, trace};
use sqlx::migrate::Migrator;
use sqlx::{Pool, Sqlite};
use sqlx::sqlite::SqlitePoolOptions;
use sqlx::{Pool, Sqlite};
use crate::db::errors::DatabaseError;
use crate::db::model_utils::Period;
use crate::db::models::{Schedule, Periods};
use crate::db::models::{Periods, Schedule};
use crate::types::EmgauwaUid;
pub mod errors;
@ -19,35 +19,38 @@ static MIGRATOR: Migrator = sqlx::migrate!(); // defaults to "./migrations"
pub async fn run_migrations(pool: &Pool<Sqlite>) {
info!("Running migrations");
MIGRATOR
.run(pool)
.await
.expect("Failed to run migrations.");
MIGRATOR.run(pool).await.expect("Failed to run migrations.");
}
async fn init_schedule(pool: &Pool<Sqlite>, uid: &EmgauwaUid, name: &str, periods: Periods) -> Result<(), DatabaseError> {
async fn init_schedule(
pool: &Pool<Sqlite>,
uid: &EmgauwaUid,
name: &str,
periods: Periods,
) -> Result<(), DatabaseError> {
trace!("Initializing schedule {:?}", name);
match schedules::get_schedule_by_uid(pool, uid).await {
match schedules::get_schedule_by_uid(&mut pool.acquire().await.unwrap(), uid).await {
Ok(_) => Ok(()),
Err(err) => match err {
DatabaseError::NotFound => {
trace!("Schedule {:?} not found, inserting", name);
sqlx::query_as!(Schedule, "INSERT INTO schedules (uid, name, periods) VALUES (?, ?, ?) RETURNING *",
sqlx::query_as!(
Schedule,
"INSERT INTO schedules (uid, name, periods) VALUES (?, ?, ?) RETURNING *",
uid,
name,
periods,
)
.fetch_optional(pool)
.await?
.ok_or(DatabaseError::InsertGetError)
.map(|_| ())
.fetch_optional(pool)
.await?
.ok_or(DatabaseError::InsertGetError)
.map(|_| ())
}
_ => Err(err),
},
}
}
pub async fn init(db: &str) -> Pool<Sqlite> {
let pool: Pool<Sqlite> = SqlitePoolOptions::new()
.acquire_timeout(std::time::Duration::from_secs(1))
@ -58,12 +61,7 @@ pub async fn init(db: &str) -> Pool<Sqlite> {
run_migrations(&pool).await;
init_schedule(
&pool,
&EmgauwaUid::Off,
"Off",
Periods(vec![])
)
init_schedule(&pool, &EmgauwaUid::Off, "Off", Periods(vec![]))
.await
.expect("Error initializing schedule Off");
@ -71,10 +69,10 @@ pub async fn init(db: &str) -> Pool<Sqlite> {
&pool,
&EmgauwaUid::On,
"On",
Periods(vec![Period::new_on()])
Periods(vec![Period::new_on()]),
)
.await
.expect("Error initializing schedule On");
.await
.expect("Error initializing schedule On");
pool
}