actix / actix/actix-web

Scope only serve the first sub-scope

Aperta
#2,295 1 commento 0 reazioni 0 assegnatari Vedi su GitHub
A-web C-improvement duplicate
Lingua principale
Rust
Stelle
24.8k
Fork
1.9k
Merge medio
23h 10m
PR unite (30g)
26

Descrizione

Let's consider the following setup:

```rust
// module base

#[get("/ping")]
pub async fn ping() -> impl Responder {
HttpResponse::Ok().body("ping - ok")
}

pub fn base_router() -> Scope {
web::scope("/")
.service(ping)
.service(b::router())
.service(c::router())
}

[snip]
// create the application using
let app = App::new().service(base_router())

```

```rust
// module b
#[get("/testb")]
async fn test() -> HttpResponse {
HttpResponse::Ok().body("b - test")
}

pub fn router() -> Scope {
web::scope("/")
.service(test)
}
```

```rust
// module c
#[get("/testc")]
async fn test() -> HttpResponse {
HttpResponse::Ok().body("c - test")
}

pub fn router() -> Scope {
web::scope("/")
.service(test)
}
```
```rust
// module d
#[get("/testd")]
async fn test() -> HttpResponse {
HttpResponse::Ok().body("d - test")
}

pub fn router() -> Scope {
web::scope("/smth/")
.service(test)
}
```

## Expected Behavior
The routes `/ping`, `/testb`, and `testc` are all valid and served by the application.

## Current Behavior
The `/ping` route is served (all the services defined directly in the top-level scope in general).
The `/testb` route is served, but not the `/testc` one; only the first sub-scope is served: if we inverse the order of definition (see bellow), then the `/testc` route is served but not the `/testb`

This behaviour is only present if the two sub-scope have the same path or if one of the subscope is set to the "root path" (`/`) and is defined first :
```rust
web::scope("/")
.service(ping) // served
.service(b::router()) // served (root)
.service(c::router()) // not served (root)

web::scope("/")
.service(ping) // served
.service(c::router()) // served (root)
.service(b::router()) // not served (root)

web::scope("/")
.service(ping) // served
.service(d::router()) // served (/smth/)
.service(c::router()) // served (root)

web::scope("/")
.service(ping) // served
.service(c::router()) // served
.service(d::router()) // not served (/smth/)
```

## Context
The only solution I found was not to use any "root" sub-scope. Though I haven't found anything in the documentation preventing me from using the root path in a sub-scope (and the application compiles & run fine).

## Your Environment
Rust 1.53 `rustc 1.53.0 (53cb7b09b 2021-06-17)`
Actix-Web 3 & 4.0.0-beta.8

Guida per i contributori

Apri la guida per i contributori

Direzione di ricerca

Start by reproducing the nested web::scope setup from the issue with App::new().service(), checking the /ping, /testb, /testc, and /testd routes in different registration orders. Trace the scope and service routing entry points to find why only the first same-path sub-scope is served. Done means all expected routes work regardless of sub-scope order, with regression coverage for the shown root and /smth/ combinations.

Scritto dal modello di indicizzazione a partire dal testo della issue.

Valutazione

Stack tecnologico
rust
Ambito
api, backend
Tipo di issue
Bug
Difficoltà
4/5
Tempo stimato
3-5 giorni
Stato di attività
Ferma
Chiarezza
Abbastanza chiara
Idoneità per principianti
35/100

Ricevi le nuove issue nella tua casella

Un breve riepilogo di issue GitHub adatte ai principianti.