Added better error handling for API+Database

+ GeoffreyDatabaseError implements Into<GeoffreyApiError>
+ The database Option and Result were combined into just Result to reduce complexity
main
Joey Hines 2021-10-17 12:21:01 -06:00
parent 692cbfebd8
commit c2bc16f3d8
No known key found for this signature in database
GPG Key ID: 80F567B5C968F91B
5 changed files with 30 additions and 17 deletions

View File

@ -42,7 +42,7 @@ impl Command for AddLocation {
.insert(location)
.map_err(|err| GeoffreyAPIError::DatabaseError(err.to_string()))
} else {
Err(GeoffreyAPIError::PlayerNotFound)
Err(GeoffreyAPIError::PlayerNotRegistered)
}
}
}

View File

@ -2,13 +2,11 @@ use crate::Result;
use geoffrey_db::database::Database;
use geoffrey_models::models::parameters::CommandRequest;
use geoffrey_models::models::player::Player;
use geoffrey_models::models::response::api_error::GeoffreyAPIError;
pub fn get_player_from_req<T>(db: &Database, req: &CommandRequest<T>) -> Result<Option<Player>> {
if let Some(user_id) = &req.user {
Ok(db
.filter(|_, player: &Player| player.has_user_id(user_id))
.map_err(|err| GeoffreyAPIError::DatabaseError(err.to_string()))?
.filter(|_, player: &Player| player.has_user_id(user_id)).map_err(|e| e.into())?
.next())
} else {
Ok(None)

View File

@ -48,7 +48,7 @@ impl Database {
Ok(model)
}
pub fn get<T>(&self, id: u64) -> Result<Option<T>>
pub fn get<T>(&self, id: u64) -> Result<T>
where
T: GeoffreyDatabaseModel,
{
@ -56,9 +56,9 @@ impl Database {
let id_bytes = id.to_be_bytes();
if let Some(bytes) = tree.get(id_bytes)? {
Ok(Some(T::try_from_bytes(&bytes)?))
Ok(T::try_from_bytes(&bytes)?)
} else {
Ok(None)
Err(GeoffreyDBError::NotFound)
}
}
@ -125,7 +125,7 @@ mod tests {
#[test]
fn test_insert() {
let player = Player::new("CoolZero123", UserID::DiscordUUID(0u64));
let player = Player::new("CoolZero123", UserID::DiscordUUID {discord_uuid: 0u64});
let p2 = DB.insert::<Player>(player.clone()).unwrap();
@ -137,8 +137,8 @@ mod tests {
#[test]
fn test_unique_insert() {
let player1 = Player::new("CoolZero123", UserID::DiscordUUID(0u64));
let player2 = Player::new("CoolZero123", UserID::DiscordUUID(0u64));
let player1 = Player::new("CoolZero123", UserID::DiscordUUID {discord_uuid: 0u64});
let player2 = Player::new("CoolZero123", UserID::DiscordUUID {discord_uuid: 0u64});
DB.insert::<Player>(player1.clone()).unwrap();
assert_eq!(DB.insert::<Player>(player2.clone()).is_err(), true);
@ -148,20 +148,19 @@ mod tests {
#[test]
fn test_get() {
let player = Player::new("CoolZero123", UserID::DiscordUUID(0u64));
let player = Player::new("CoolZero123", UserID::DiscordUUID {discord_uuid: 0u64});
let p2 = DB.insert::<Player>(player.clone()).unwrap();
let p3 = DB.get::<Player>(p2.id().unwrap()).unwrap();
assert!(p3.is_some());
assert_eq!(p3.unwrap().name, player.name);
assert_eq!(p3.name, player.name);
cleanup();
}
#[test]
fn test_filter() {
let player = Player::new("CoolZero123", UserID::DiscordUUID(0u64));
let player = Player::new("CoolZero123", UserID::DiscordUUID {discord_uuid: 0u64});
let player = DB.insert::<Player>(player.clone()).unwrap();
let loc = Location::new(
"Test Shop",
@ -191,7 +190,7 @@ mod tests {
let insert_count = 1000;
let timer = Instant::now();
for i in 0..insert_count {
let player = Player::new("test", UserID::DiscordUUID(i));
let player = Player::new("test", UserID::DiscordUUID {discord_uuid: i});
DB.insert::<Player>(player).unwrap();
}

View File

@ -1,3 +1,5 @@
use geoffrey_models::models::response::api_error::GeoffreyAPIError;
pub type Result<T> = std::result::Result<T, GeoffreyDBError>;
#[derive(Debug)]
@ -5,6 +7,7 @@ pub enum GeoffreyDBError {
SledError(sled::Error),
SerdeJsonError(serde_json::Error),
NotUnique,
NotFound,
}
impl std::error::Error for GeoffreyDBError {}
@ -15,6 +18,7 @@ impl std::fmt::Display for GeoffreyDBError {
GeoffreyDBError::SledError(e) => write!(f, "Sled Error: {}", e),
GeoffreyDBError::SerdeJsonError(e) => write!(f, "Serde JSON Error: {}", e),
GeoffreyDBError::NotUnique => write!(f, "Entry is not unique."),
GeoffreyDBError::NotFound => write!(f, "Entry was not found."),
}
}
}
@ -30,3 +34,14 @@ impl From<serde_json::Error> for GeoffreyDBError {
GeoffreyDBError::SerdeJsonError(e)
}
}
impl Into<GeoffreyAPIError> for GeoffreyDBError {
fn into(self) -> GeoffreyAPIError {
match self {
GeoffreyDBError::SledError(_) => GeoffreyAPIError::DatabaseError(self.to_string()),
GeoffreyDBError::SerdeJsonError(_) => GeoffreyAPIError::DatabaseError(self.to_string()),
GeoffreyDBError::NotUnique => GeoffreyAPIError::EntryNotUnique,
GeoffreyDBError::NotFound => GeoffreyAPIError::EntryNotFound
}
}
}

View File

@ -2,8 +2,9 @@ use serde::{Deserialize, Serialize};
#[derive(Debug, Serialize, Deserialize)]
pub enum GeoffreyAPIError {
PlayerNotFound,
LocationNotFound,
PlayerNotRegistered,
EntryNotFound,
PermissionInsufficient,
EntryNotUnique,
DatabaseError(String),
}