use crate::db::{Dao, TenebrousDbConn}; use crate::errors::Error; use crate::models::characters::{Character, CharacterDataType, DynCharacterData, Visibility}; use crate::models::proto::{cofd::*, Proto}; use crate::models::users::User; use rocket_contrib::templates::Template; use serde::Serialize; use std::borrow::Cow; use std::collections::HashMap; pub(crate) fn routes() -> Vec { routes![ cofd::update_basic_info, cofd::update_attributes, cofd::update_attribute, cofd::update_skills, cofd::add_condition, cofd::remove_condition ] } /// Load the character belonging to the given user, as long as they're /// the owner of that character. Returns an error if user is not /// logged in, the owner of the character is not found, or the logged /// in user does not have the permission to access this character. async fn load_character( conn: &TenebrousDbConn<'_>, logged_in_user: Option<&User>, owner: String, character_id: i32, ) -> Result { let logged_in_user = logged_in_user.ok_or(Error::NotLoggedIn)?; let owner = conn.load_user(&owner).await?.ok_or(Error::NotFound)?; let character: Character = conn .load_character(character_id) .await? .ok_or(Error::NotFound)?; if logged_in_user != &owner { return Err(Error::NoPermission); } Ok(character) } /// Protobuf-based REST endpoints for editing a character. mod cofd { use super::*; use crate::models::proto::{cofd::api::*, cofd::*, Proto}; #[post("/cofd///basic-info", data = "")] pub(super) fn update_basic_info<'a>( owner: String, character_id: i32, info: Proto, ) -> &'a str { "lol" } #[post("/cofd///attributes", data = "")] pub(super) fn update_attributes<'a>( owner: String, character_id: i32, info: Proto, ) -> &'a str { "lol" } #[patch("/cofd///attributes", data = "")] pub(super) async fn update_attribute<'a>( owner: String, character_id: i32, attr_update: Proto, conn: TenebrousDbConn<'_>, logged_in_user: Option<&User>, ) -> Result<&'a str, Error> { let mut character = load_character(&conn, logged_in_user, owner, character_id).await?; let mut sheet: CofdSheet = character.try_deserialize()?; match attr_update.name.to_lowercase().as_ref() { "strength" => Ok(sheet.strength = attr_update.value), "dexterity" => Ok(sheet.dexterity = attr_update.value), "stamina" => Ok(sheet.stamina = attr_update.value), "intelligence" => Ok(sheet.intelligence = attr_update.value), "wits" => Ok(sheet.wits = attr_update.value), "resolve" => Ok(sheet.resolve = attr_update.value), "presence" => Ok(sheet.presence = attr_update.value), "manipulation" => Ok(sheet.manipulation = attr_update.value), "composure" => Ok(sheet.composure = attr_update.value), _ => Err(Error::InvalidInput), }?; println!( "updated {} attribute {} to {}", character.character_name, attr_update.name, attr_update.value ); character.update_data(sheet)?; conn.update_character_sheet(&character).await?; Ok("lol") } #[post("/cofd///skills", data = "")] pub(super) fn update_skills<'a>( owner: String, character_id: i32, info: Proto, conn: TenebrousDbConn<'_>, ) -> &'a str { "lol" } #[put("/cofd///conditions", data = "")] pub(super) fn add_condition<'a>( owner: String, character_id: i32, info: Proto, ) -> &'a str { "lol" } #[delete("/cofd///conditions", data = "")] pub(super) fn remove_condition<'a>( owner: String, character_id: i32, info: Proto, ) -> &'a str { "lol" } }