3 changed files with 136 additions and 0 deletions
@ -0,0 +1,119 @@ |
|||||||
|
use axum::{ |
||||||
|
Json, Router, |
||||||
|
extract::{Path, Query, State}, |
||||||
|
http::StatusCode, |
||||||
|
response::IntoResponse, |
||||||
|
routing::get, |
||||||
|
}; |
||||||
|
use serde::{Deserialize, Serialize}; |
||||||
|
use std::sync::Arc; |
||||||
|
|
||||||
|
use crate::state::AppState; |
||||||
|
|
||||||
|
#[derive(Debug, Deserialize)] |
||||||
|
pub struct EncodeQuery { |
||||||
|
pub dict: Option<String>, |
||||||
|
} |
||||||
|
|
||||||
|
#[derive(Debug, Deserialize)] |
||||||
|
pub struct DecodeQuery { |
||||||
|
pub dict: Option<String>, |
||||||
|
} |
||||||
|
|
||||||
|
#[derive(Debug, Serialize)] |
||||||
|
pub struct EncodeResponse { |
||||||
|
pub input: String, |
||||||
|
pub dict: String, |
||||||
|
pub result: Vec<Vec<EncodePart>>, |
||||||
|
} |
||||||
|
|
||||||
|
#[derive(Debug, Serialize)] |
||||||
|
pub struct EncodePart { |
||||||
|
pub value: u64, |
||||||
|
pub words: Vec<String>, |
||||||
|
} |
||||||
|
|
||||||
|
#[derive(Debug, Serialize)] |
||||||
|
pub struct DecodeResponse { |
||||||
|
pub input: String, |
||||||
|
pub result: String, |
||||||
|
} |
||||||
|
|
||||||
|
#[derive(Debug, Serialize)] |
||||||
|
pub struct ErrorResponse { |
||||||
|
pub error: String, |
||||||
|
} |
||||||
|
|
||||||
|
impl IntoResponse for ErrorResponse { |
||||||
|
fn into_response(self) -> axum::response::Response { |
||||||
|
(StatusCode::INTERNAL_SERVER_ERROR, Json(self)).into_response() |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
impl From<anyhow::Error> for ErrorResponse { |
||||||
|
fn from(err: anyhow::Error) -> Self { |
||||||
|
Self { |
||||||
|
error: err.to_string(), |
||||||
|
} |
||||||
|
} |
||||||
|
} |
||||||
|
|
||||||
|
pub async fn encode_handler( |
||||||
|
State(state): State<Arc<AppState>>, |
||||||
|
Path(input): Path<String>, |
||||||
|
Query(params): Query<EncodeQuery>, |
||||||
|
) -> Result<Json<EncodeResponse>, ErrorResponse> { |
||||||
|
let dict_name = params.dict.unwrap_or_else(|| "demo_pl".to_string()); |
||||||
|
let encoder = state |
||||||
|
.container |
||||||
|
.create_encoder(&dict_name) |
||||||
|
.await |
||||||
|
.map_err(|e| anyhow::anyhow!("Failed to create encoder: {}", e))?; |
||||||
|
let result = encoder |
||||||
|
.encode(&input) |
||||||
|
.map_err(|e| anyhow::anyhow!("Failed to encode: {}", e))?; |
||||||
|
|
||||||
|
let encoded_parts: Vec<Vec<EncodePart>> = result |
||||||
|
.iter() |
||||||
|
.map(|split| { |
||||||
|
split |
||||||
|
.iter() |
||||||
|
.map(|part| EncodePart { |
||||||
|
value: part.value, |
||||||
|
words: part.words.clone(), |
||||||
|
}) |
||||||
|
.collect() |
||||||
|
}) |
||||||
|
.collect(); |
||||||
|
|
||||||
|
Ok(Json(EncodeResponse { |
||||||
|
input, |
||||||
|
dict: dict_name, |
||||||
|
result: encoded_parts, |
||||||
|
})) |
||||||
|
} |
||||||
|
|
||||||
|
pub async fn decode_handler( |
||||||
|
State(state): State<Arc<AppState>>, |
||||||
|
Path(input): Path<String>, |
||||||
|
Query(_params): Query<DecodeQuery>, |
||||||
|
) -> Result<Json<DecodeResponse>, ErrorResponse> { |
||||||
|
let decoder = state |
||||||
|
.container |
||||||
|
.create_decoder() |
||||||
|
.map_err(|e| anyhow::anyhow!("Failed to create decoder: {}", e))?; |
||||||
|
let result = decoder |
||||||
|
.decode(&input) |
||||||
|
.map_err(|e| anyhow::anyhow!("Failed to decode: {}", e))?; |
||||||
|
|
||||||
|
Ok(Json(DecodeResponse { |
||||||
|
input, |
||||||
|
result: result.as_str().to_string(), |
||||||
|
})) |
||||||
|
} |
||||||
|
|
||||||
|
pub fn routes() -> Router<Arc<AppState>> { |
||||||
|
Router::new() |
||||||
|
.route("/encode/major_pl/{input}", get(encode_handler)) |
||||||
|
.route("/decode/major_pl/{input}", get(decode_handler)) |
||||||
|
} |
||||||
Loading…
Reference in new issue