use actix_web::{post, web::Data, HttpRequest, HttpResponse}; use serde::Deserialize; use super::ActionTemplate; use crate::{ ctx::Ctx, db::models::Ban, error::NekrochanError, qsform::QsForm, web::{ tcx::{ip_from_req, TemplateCtx}, template_response, }, }; #[derive(Deserialize)] pub struct AppealBanForm { pub id: i32, pub appeal: String, } #[post("/actions/appeal-ban")] pub async fn appeal_ban( ctx: Data, req: HttpRequest, QsForm(form): QsForm, ) -> Result { let tcx = TemplateCtx::new(&ctx, &req).await?; let (ip, _, _) = ip_from_req(&req)?; let ban = Ban::read_by_id(&ctx, form.id) .await? .ok_or(NekrochanError::BanNotFound)?; if !ban.ip_range.contains(ip) { return Err(NekrochanError::BanNotFound); } if ban.appeal.is_some() { return Err(NekrochanError::AlreadyAppealedError); } if !ban.appealable { return Err(NekrochanError::UnappealableError); } let appeal: String = form.appeal.trim().into(); if appeal.is_empty() || appeal.len() > 1000 { return Err(NekrochanError::BanAppealFormatError); } ban.update_appeal(&ctx, appeal).await?; template_response(&ActionTemplate { tcx, response: "Ban byl úspěšně odvolán.".into(), }) }