credence_lib/server/
routers.rs1use super::super::{configuration::*, middleware::*};
2
3use {
4 ::axum::{
5 extract::{Request, *},
6 http::{header::*, *},
7 middleware::*,
8 response::*,
9 routing::*,
10 },
11 kutil::{
12 http::{
13 axum::*,
14 cache::{axum::*, *},
15 },
16 std::immutable::*,
17 },
18 tower_http::{limit::*, services::*, timeout::*, trace::*},
19};
20
21pub fn new_site_router<CacheT>(shutdown: &Shutdown, cache: &CacheT, configuration: &CredenceConfiguration) -> Router
23where
24 CacheT: Cache<CommonCacheKey>,
25{
26 let admin_router = Router::default()
27 .route("/about", get(about_handler))
28 .route("/shutdown", post(shutdown_handler))
29 .with_state(shutdown.clone())
30 .route("/reset-cache", post(reset_cache_handler::<CacheT, _>))
31 .with_state(cache.clone())
32 .route("/status/{status_code}", get(status_code_handler));
33
34 let router = Router::default()
35 .fallback_service(ServeDir::new(&configuration.files.assets).append_index_html_on_directories(false))
36 .nest("/admin", admin_router)
37 .layer(from_fn_with_state(RenderMiddleware::new(configuration.clone()), RenderMiddleware::function))
38 .layer(configuration.caching_layer(cache.clone()))
39 .layer(from_fn_with_state(CatchMiddleware::new(configuration.files.status.clone()), CatchMiddleware::function));
40
41 let router = Router::default()
45 .merge(router)
46 .layer(map_request_with_state(FacadeMiddleware::new(configuration.clone()), FacadeMiddleware::function))
47 .layer(RequestBodyLimitLayer::new(configuration.requests.max_body_size.inner.into()))
48 .layer(TimeoutLayer::new(configuration.requests.max_duration.inner.into()))
49 .layer(TraceLayer::new_for_http());
50
51 router
52}
53
54pub fn new_redirecting_router(tls: bool, host: ByteString, tcp_port: u16) -> Router {
56 let scheme = if tls { "https://" } else { "http://" };
57
58 let tcp_port = match tcp_port {
59 80 | 443 => Default::default(),
60 _ => format!(":{}", tcp_port),
61 };
62
63 Router::default().fallback(async move |request: Request| {
64 let path_and_query = request
65 .uri()
66 .path_and_query()
67 .map(|path_and_query| path_and_query.to_string())
68 .unwrap_or_else(|| "/".into());
69
70 let uri = format!("{}{}{}{}", scheme, host, tcp_port, path_and_query);
71
72 (StatusCode::MOVED_PERMANENTLY, [(LOCATION, uri)]).into_response()
73 })
74}
75
76async fn status_code_handler(Path(status_code): Path<u16>) -> StatusCode {
77 tracing::debug!("status code: {}", status_code);
78 StatusCode::from_u16(status_code).unwrap_or(StatusCode::INTERNAL_SERVER_ERROR)
79}
80
81build_info::build_info!(fn build_info);
82
83async fn about_handler() -> impl IntoResponse {
84 let build_info = build_info();
85 let mut about = String::default();
86
87 about += &format!("credence-lib: {}\n", env!("CARGO_PKG_VERSION"));
88
89 if let Some(version_control) = &build_info.version_control
90 && let Some(git) = version_control.git()
91 {
92 about += "\n";
93 about += &format!("git-commit-id: {}\n", git.commit_id);
94 about += &format!("git-commit-timestamp: {}\n", git.commit_timestamp);
95 if let Some(branch) = &git.branch {
96 about += &format!("git-commit-branch: {}\n", branch);
97 }
98 if !git.tags.is_empty() {
99 about += &format!("git-commit-tags: {}\n", git.tags.join(","));
100 }
101 about += &format!("git-dirty: {}]\n", git.dirty);
102 }
103
104 about += "\n";
105 about += &format!("binary-cpu: {}\n", build_info.target.cpu.arch);
106 about += &format!("binary-cpu-bits: {}]\n", build_info.target.cpu.pointer_width);
107 about += &format!("binary-cpu-endianness: {}\n", build_info.target.cpu.endianness.to_string().to_lowercase());
108 if !build_info.target.cpu.features.is_empty() {
109 about += &format!("binary-cpu-features: {}\n", build_info.target.cpu.features.join(","));
110 }
111 about += &format!("binary-os: {}\n", build_info.target.os);
112 about += &format!("binary-architecture: {}\n", build_info.target.triple);
113
114 about += "\n";
115 about += &format!("compilation-timestamp: {}\n", build_info.timestamp);
116 about += &format!("compilation-profile: {}\n", build_info.profile);
117 about += &format!("compilation-optimization-level: {}\n", build_info.optimization_level);
118
119 about += "\n";
120 about += "compiler: rustc\n";
121 about += &format!("compiler-version: {}\n", build_info.compiler.version);
122 about += &format!("compiler-channel: {}\n", build_info.compiler.channel.to_string().to_lowercase());
123 if let Some(commit_id) = &build_info.compiler.commit_id {
124 about += &format!("compiler-git-commit-id: {}\n", commit_id);
125 }
126 if let Some(commit_date) = &build_info.compiler.commit_date {
127 about += &format!("compiler-git-commit-date: {}\n", commit_date);
128 }
129
130 ([("content-type", "text/plain")], about)
131}