Cannot isolate middleware when using wildcard patterns at the same path prefix #3685
Replies: 1 comment
-
|
Yeah, actix-web matches services in the order they are defined, but a wildcard scope often "swallows" everything if you aren't careful. The best way to isolate middleware while keeping the same prefix is to use a You can use use actix_web::{web, guard, App, middleware::Logger};
App::new()
// Scope 1: REST API with Middleware
.service(
web::scope("/api")
.guard(guard::fn_guard(|ctx| {
// Only match if NOT a docs request
!ctx.path().starts_with("/api/docs")
}))
.wrap(Logger::default())
.route("/items", web::get().to(api_handler))
)
// Scope 2: Swagger/Wildcard without Middleware
.service(
web::scope("/api")
.route("/docs/{tail:.*}", web::get().to(swagger_handler))
)Alternatively, you can wrap individual resources instead of the entire scope. If you only have a few REST endpoints, this is often simpler: web::scope("/api")
.service(
web::resource("/items")
.wrap(Logger::default())
.route(web::get().to(api_handler))
)
.route("/docs/{tail:.*}", web::get().to(swagger_handler))Using the |
Beta Was this translation helpful? Give feedback.
Uh oh!
There was an error while loading. Please reload this page.
-
Environment
Problem description
I'm trying to serve both REST API endpoints and Swagger UI documentation at the same path prefix (
/api) but with different middleware requirements. However, actix-web's routing behavior with wildcard patterns makes it impossible to properly isolate middleware between these different types of content.Current limitation
There appears to be no way to achieve this configuration:
GET /api/items- REST endpoint WITH middleware.GET /api/*- Swagger UI WITHOUT middleware.My current solution
With the following code, the middleware is applied only to the REST endpoint as expected, but Swagger UI is served at a different path prefix, which is not what I want:
cargo run.http://127.0.0.1:8080/docs/: Nothing logged as expected.http://127.0.0.1:8080/api/items: Logged as expected.Cargo.toml:
Attempted approaches
Approach 1: Different Path Prefixes (Works, but not desired)
Result: ✅ Middleware isolation works, but API is at
/api/itemsand docs at/docs/(different prefixes)Approach 2: Same Scope, SwaggerUI Last
Result: ❌ Cannot selectively apply middleware - it affects both REST endpoints AND Swagger UI
Approach 3: Separate Scopes, Same Prefix (Doesn't work)
Result: ❌ One of the scopes is ignored entirely.
Questions
Use Case
I want to serve a REST API with authentication middleware alongside Swagger UI documentation, both at
/api/*. This is a common pattern for API servers where documentation is co-located with the API itself.Impact
This limitation forces developers to either:
Existing issues
Beta Was this translation helpful? Give feedback.
All reactions