54 lines
1.6 KiB
Rust
54 lines
1.6 KiB
Rust
use crate::commands::{Command, RequestType};
|
|
use crate::context::Context;
|
|
use crate::Result;
|
|
use geoffrey_db::helper::load_location;
|
|
use geoffrey_db::query::QueryBuilder;
|
|
use geoffrey_models::models::locations::{Location, LocationDb};
|
|
use geoffrey_models::models::parameters::info_params::InfoParams;
|
|
use geoffrey_models::models::player::Player;
|
|
use geoffrey_models::models::response::api_error::GeoffreyAPIError;
|
|
use geoffrey_models::models::CommandLevel;
|
|
use std::sync::Arc;
|
|
use strsim::normalized_damerau_levenshtein;
|
|
|
|
pub struct InfoCommand {}
|
|
|
|
impl Command for InfoCommand {
|
|
type Req = InfoParams;
|
|
type Resp = Location;
|
|
|
|
fn command_name() -> String {
|
|
"info".to_string()
|
|
}
|
|
|
|
fn request_type() -> RequestType {
|
|
RequestType::GET
|
|
}
|
|
|
|
fn command_level() -> CommandLevel {
|
|
CommandLevel::ALL
|
|
}
|
|
|
|
fn run_command(ctx: Arc<Context>, req: &Self::Req, _: Option<Player>) -> Result<Self::Resp> {
|
|
let query = QueryBuilder::<LocationDb>::default()
|
|
.with_name_regex_case_insensitive(&req.location_name)?;
|
|
|
|
let mut locations = ctx.db.run_query(query)?;
|
|
|
|
if locations.is_empty() {
|
|
Err(GeoffreyAPIError::EntryNotFound)
|
|
} else {
|
|
locations.sort_by(|a, b| {
|
|
let a =
|
|
(normalized_damerau_levenshtein(&a.name, &req.location_name) * 1000.0) as u32;
|
|
let b =
|
|
(normalized_damerau_levenshtein(&b.name, &req.location_name) * 1000.0) as u32;
|
|
|
|
a.cmp(&b)
|
|
});
|
|
|
|
Ok(load_location(&ctx.db, &locations.pop().unwrap())?)
|
|
}
|
|
}
|
|
}
|