Constellation, Spacedust, Slingshot, UFOs: atproto crates and services for microcosm
at main 1.1 kB view raw
1use askama::Template; 2use axum::http::StatusCode; 3use axum::response::{Html, IntoResponse, Json, Response}; 4use axum_extra::TypedHeader; 5use headers_accept::Accept; 6use mediatype::names::{APPLICATION, HTML, JSON, TEXT}; 7use mediatype::MediaType; 8use serde::Serialize; 9 10const TEXT_HTML: MediaType = MediaType::new(TEXT, HTML); 11const APPLICATION_JSON: MediaType = MediaType::new(APPLICATION, JSON); 12const AVAILABLE: &[MediaType] = &[APPLICATION_JSON, TEXT_HTML]; 13 14pub type ExtractAccept = Option<TypedHeader<Accept>>; 15 16pub fn acceptable<T: Serialize + Template>(accept: ExtractAccept, thing: T) -> Response { 17 if let Some(accepting) = accept { 18 if accepting.negotiate(AVAILABLE) == Some(&TEXT_HTML) { 19 match thing.render() { 20 Ok(content) => return Html(content).into_response(), 21 Err(e) => { 22 eprintln!("template rendering failed: {e:?}"); 23 return StatusCode::INTERNAL_SERVER_ERROR.into_response(); 24 } 25 } 26 } 27 } 28 Json(thing).into_response() 29}