This commit is contained in:
Igor Katson 2025-01-14 10:44:38 +00:00
parent fd5feba501
commit 8abbf683c0
No known key found for this signature in database
GPG key ID: B4EC22B66D61A3F5

View file

@ -643,25 +643,8 @@ async fn h_api_root(parts: Parts) -> impl IntoResponse {
.into_response() .into_response()
} }
impl HttpApi { fn make_api_router(state: ApiState) -> Router {
pub fn new(api: Api, opts: Option<HttpApiOptions>) -> Self { let mut api_router = Router::new()
Self {
api,
opts: opts.unwrap_or_default(),
}
}
/// Run the HTTP server forever on the given address.
/// If read_only is passed, no state-modifying methods will be exposed.
#[inline(never)]
pub fn make_http_api_and_run(
self,
listener: TcpListener,
upnp_router: Option<Router>,
) -> BoxFuture<'static, anyhow::Result<()>> {
let state = Arc::new(self);
let mut app = Router::new()
.route("/", get(h_api_root)) .route("/", get(h_api_root))
.route("/stream_logs", get(h_stream_logs)) .route("/stream_logs", get(h_stream_logs))
.route("/rust_log", post(h_set_rust_log)) .route("/rust_log", post(h_set_rust_log))
@ -687,7 +670,7 @@ impl HttpApi {
); );
if !state.opts.read_only { if !state.opts.read_only {
app = app api_router = api_router
.route("/torrents", post(h_torrents_post)) .route("/torrents", post(h_torrents_post))
.route("/torrents/limits", post(h_update_session_ratelimits)) .route("/torrents/limits", post(h_update_session_ratelimits))
.route("/torrents/{id}/pause", post(h_torrent_action_pause)) .route("/torrents/{id}/pause", post(h_torrent_action_pause))
@ -700,11 +683,12 @@ impl HttpApi {
); );
} }
#[cfg(feature = "webui")] api_router.with_state(state)
{ }
use axum::response::Redirect;
let webui_router = Router::new() #[cfg(feature = "webui")]
fn make_webui_router() -> Router {
Router::new()
.route( .route(
"/", "/",
get(|| async { get(|| async {
@ -740,10 +724,37 @@ impl HttpApi {
include_str!("../webui/dist/assets/logo.svg"), include_str!("../webui/dist/assets/logo.svg"),
) )
}), }),
); )
}
app = app.nest("/web/", webui_router); impl HttpApi {
app = app.route("/web", get(|| async { Redirect::permanent("/web/") })) pub fn new(api: Api, opts: Option<HttpApiOptions>) -> Self {
Self {
api,
opts: opts.unwrap_or_default(),
}
}
/// Run the HTTP server forever on the given address.
/// If read_only is passed, no state-modifying methods will be exposed.
#[inline(never)]
pub fn make_http_api_and_run(
self,
listener: TcpListener,
upnp_router: Option<Router>,
) -> BoxFuture<'static, anyhow::Result<()>> {
let state = Arc::new(self);
let mut main_router = Router::new();
main_router = main_router.nest("/", make_api_router(state.clone()));
#[cfg(feature = "webui")]
{
use axum::response::Redirect;
let webui_router = make_webui_router();
main_router = main_router.nest("/web/", webui_router);
main_router = main_router.route("/web", get(|| async { Redirect::permanent("/web/") }))
} }
let cors_layer = { let cors_layer = {
@ -774,26 +785,25 @@ impl HttpApi {
.allow_headers(AllowHeaders::any()) .allow_headers(AllowHeaders::any())
}; };
let mut app = app.with_state(state.clone());
// Simple one-user basic auth // Simple one-user basic auth
if let Some((user, pass)) = state.opts.basic_auth.clone() { if let Some((user, pass)) = state.opts.basic_auth.clone() {
info!("Enabling simple basic authentication in HTTP API"); info!("Enabling simple basic authentication in HTTP API");
app = main_router = main_router.route_layer(axum::middleware::from_fn(
app.route_layer(axum::middleware::from_fn(move |headers, request, next| { move |headers, request, next| {
let user = user.clone(); let user = user.clone();
let pass = pass.clone(); let pass = pass.clone();
async move { async move {
simple_basic_auth(Some(&user), Some(&pass), headers, request, next).await simple_basic_auth(Some(&user), Some(&pass), headers, request, next).await
} }
})); },
));
} }
if let Some(upnp_router) = upnp_router { if let Some(upnp_router) = upnp_router {
app = app.nest("/upnp", upnp_router); main_router = main_router.nest("/upnp", upnp_router);
} }
let app = app let app = main_router
.layer(cors_layer) .layer(cors_layer)
.layer( .layer(
tower_http::trace::TraceLayer::new_for_http() tower_http::trace::TraceLayer::new_for_http()