136 lines
4.2 KiB
Rust
136 lines
4.2 KiB
Rust
use chrono::NaiveDateTime;
|
|
use serde::{Deserialize, Serialize};
|
|
|
|
use crate::database::DatabaseHandler;
|
|
|
|
#[derive(Debug, Clone, sqlx::FromRow, Serialize, Deserialize)]
|
|
pub struct Map {
|
|
pub map: String,
|
|
pub mappers: Vec<String>,
|
|
pub category: String,
|
|
pub points: i16,
|
|
pub stars: i16,
|
|
pub release: Option<NaiveDateTime>,
|
|
pub width: Option<i16>,
|
|
pub height: Option<i16>,
|
|
pub tiles: Option<Vec<String>>,
|
|
}
|
|
|
|
impl Map {
|
|
/// This gets all maps in the map database.
|
|
pub async fn get_all_maps(db: &DatabaseHandler) -> Result<Vec<Map>, sqlx::Error> {
|
|
sqlx::query_file_as!(Map, "sql/maps/get_all_maps.sql")
|
|
.fetch_all(&db.pool)
|
|
.await
|
|
}
|
|
|
|
/// This gets a map from the database via its name.
|
|
/// Returns an Err<sqlx::Error> if no map exists with the given name.
|
|
pub async fn get_map_by_name(db: &DatabaseHandler, map: &str) -> Result<Map, sqlx::Error> {
|
|
sqlx::query_file_as!(Map, "sql/maps/get_map_by_name.sql", map)
|
|
.fetch_one(&db.pool)
|
|
.await
|
|
}
|
|
|
|
/// This gets all maps from the database via their category.
|
|
/// Valid values are: Novice, Moderate, Brutal, Insane, Dummy, DDmaX.Easy, DDmaX.Next, DDmaX.Pro, DDmaX.Nut, Oldschool, Solo, Race, Fun
|
|
/// FIXME: Returns an empty array on invalid category!
|
|
pub async fn get_maps_by_category(
|
|
db: &DatabaseHandler,
|
|
category: &str,
|
|
) -> Result<Vec<Map>, sqlx::Error> {
|
|
sqlx::query_file_as!(Map, "sql/maps/get_maps_by_category.sql", category)
|
|
.fetch_all(&db.pool)
|
|
.await
|
|
}
|
|
|
|
/// This gets all the maps in the database made by a specific mapper.
|
|
/// Mappers are stored as an array, so if that array contains the given mapper, the entry is returned.
|
|
/// FIXME: Returns an empty array on non-existant mapper!
|
|
pub async fn get_maps_by_mapper(
|
|
db: &DatabaseHandler,
|
|
mapper: &str,
|
|
) -> Result<Vec<Map>, sqlx::Error> {
|
|
sqlx::query_file_as!(Map, "sql/maps/get_maps_by_mapper.sql", mapper)
|
|
.fetch_all(&db.pool)
|
|
.await
|
|
}
|
|
|
|
/// Experimental function to search for maps.
|
|
pub async fn search_maps(
|
|
db: &DatabaseHandler,
|
|
map: Option<&str>,
|
|
mappers: Option<Vec<String>>,
|
|
category: Option<&str>,
|
|
stars: Option<Vec<i16>>,
|
|
release_after: Option<NaiveDateTime>,
|
|
release_before: Option<NaiveDateTime>,
|
|
tiles: Option<Vec<String>>,
|
|
orderby: Option<&str>,
|
|
sort: Option<&str>,
|
|
) -> Result<Vec<Map>, sqlx::Error> {
|
|
let stars = stars.unwrap_or((0..=5).collect());
|
|
let mappers = mappers.unwrap_or(vec![]);
|
|
let tiles = tiles.unwrap_or(vec![]);
|
|
|
|
sqlx::query_file_as!(
|
|
Map,
|
|
"sql/maps/search_maps.sql",
|
|
map.map(|map| format!("%{}%", map)),
|
|
mappers.as_slice(),
|
|
category,
|
|
stars.as_slice(),
|
|
release_after,
|
|
release_before,
|
|
tiles.as_slice(),
|
|
orderby,
|
|
sort,
|
|
)
|
|
.fetch_all(&db.pool)
|
|
.await
|
|
}
|
|
}
|
|
|
|
#[cfg(test)]
|
|
mod tests {
|
|
use super::*;
|
|
|
|
#[test]
|
|
fn test_get_all_maps() {
|
|
async fn test() {
|
|
let db = match DatabaseHandler::create().await {
|
|
Ok(db) => db,
|
|
Err(err) => panic!("Error while connecting to database! {:?}", err),
|
|
};
|
|
let maps = match Map::get_all_maps(&db).await {
|
|
Ok(maps) => maps,
|
|
Err(err) => panic!("Error while getting all maps! {:?}", err),
|
|
};
|
|
|
|
for map in maps {
|
|
println!("{:?}", map);
|
|
}
|
|
}
|
|
|
|
tokio_test::block_on(test());
|
|
}
|
|
|
|
#[test]
|
|
fn test_get_map_by_name() {
|
|
async fn test() {
|
|
let db = match DatabaseHandler::create().await {
|
|
Ok(db) => db,
|
|
Err(err) => panic!("Error while connecting to database! {:?}", err),
|
|
};
|
|
let map = match Map::get_map_by_name(&db, "Kobra").await {
|
|
Ok(map) => map,
|
|
Err(err) => panic!("Error while getting all maps! {:?}", err),
|
|
};
|
|
|
|
println!("{:?}", map);
|
|
}
|
|
|
|
tokio_test::block_on(test());
|
|
}
|
|
}
|