wayver's git archive


a simple self-hosted git server
git clone https://git.wayver.dev/bile

src/utils/mod.rs@f3f2b40f0ffae5de2e6d3f661e32b582274bae49

raw
Date Commit Message Author Files + -
2026-02-17 21:07 initial mvp wayverd 74 10800 0
...

1pub mod git;
2
3pub mod error;
4pub mod extractor;
5pub mod filters;
6pub mod markdown;
7pub mod response;
8
9use axum::{
10    http::StatusCode,
11    response::{IntoResponse, Response},
12};
13
14use crate::utils::response::Html;
15
16pub type Result<T = Response, E = Error> = std::result::Result<T, E>;
17
18// TODO: https://github.com/rust-lang/rust/issues/110011
19// #[track_caller]
20pub async fn spawn_blocking<F, R>(f: F) -> R
21where
22    F: FnOnce() -> R + Send + 'static,
23    R: Send + 'static,
24{
25    tokio::task::spawn_blocking(f)
26        .await
27        .expect("failed to join spawn_blocking call, this should only happen due to a panic")
28}
29
30#[derive(askama::Template)]
31#[template(path = "error.html")]
32pub enum Error {
33    Failure {
34        status: StatusCode,
35        err: error::Error,
36    },
37    Custom {
38        status: StatusCode,
39        message: String,
40    },
41}
42
43impl Error {
44    pub fn new<M: ToString + ?Sized>(status: StatusCode, message: &M) -> Self {
45        Self::Custom {
46            status,
47            message: message.to_string(),
48        }
49    }
50}
51
52impl IntoResponse for Error {
53    fn into_response(self) -> Response {
54        let status = match &self {
55            Self::Failure { status, err } => {
56                tracing::error!(err=?err, "failed to respond to request");
57
58                status
59            }
60            Self::Custom { status, .. } => status,
61        };
62
63        (*status, Html(self)).into_response()
64    }
65}
66
67impl<E> From<E> for Error
68where
69    E: Into<error::Error>,
70{
71    fn from(err: E) -> Self {
72        Self::Failure {
73            status: StatusCode::INTERNAL_SERVER_ERROR,
74            err: err.into(),
75        }
76    }
77}
78
79#[must_use]
80pub fn blob_mime(blob: &git2::Blob<'_>, extension: &str) -> mime::Mime {
81    extension.parse().unwrap_or_else(|_| {
82        if blob.is_binary() {
83            mime::APPLICATION_OCTET_STREAM
84        } else {
85            mime::TEXT_PLAIN_UTF_8
86        }
87    })
88}
89