use cratestack_core::Procedure;
use quote::quote;
use crate::shared::{ident, to_snake_case};
pub(super) fn procedure_axum_route_tokens(procedure: &Procedure) -> proc_macro2::TokenStream {
let route_path = procedure_route_path(procedure);
let handler_ident = ident(&format!("handle_{}", to_snake_case(&procedure.name)));
quote! { .route(#route_path, axum::routing::post(#handler_ident)) }
}
pub(super) fn procedure_route_path(procedure: &Procedure) -> String {
if let Some(version) = procedure_api_version(procedure) {
format!("/{}/$procs/{}", version, procedure.name)
} else {
format!("/$procs/{}", procedure.name)
}
}
fn procedure_api_version(procedure: &Procedure) -> Option<String> {
procedure.attributes.iter().find_map(|attribute| {
attribute
.raw
.strip_prefix("@api_version(\"")
.and_then(|rest| rest.strip_suffix("\")"))
.map(|s| s.to_owned())
})
}
pub(super) fn procedure_deprecation_header_tokens(
procedure: &Procedure,
) -> proc_macro2::TokenStream {
let deprecated = procedure
.attributes
.iter()
.find(|a| a.raw == "@deprecated" || a.raw.starts_with("@deprecated("));
let Some(attribute) = deprecated else {
return quote! {};
};
let message: Option<String> = attribute
.raw
.strip_prefix("@deprecated(\"")
.and_then(|s| s.strip_suffix("\")"))
.map(|s| s.to_owned());
let message_block = match message {
Some(m) => quote! {
if let Ok(value) = ::cratestack::axum::http::HeaderValue::from_str(#m) {
response.headers_mut().insert("X-Deprecation", value);
}
},
None => quote! {},
};
quote! {
response
.headers_mut()
.insert("Deprecation", ::cratestack::axum::http::HeaderValue::from_static("true"));
#message_block
}
}