Skip to content

Path prefixes

You can use Blueprint::prefix to group multiple routes under a common path prefix.

src/intro/blueprint.rs
use pavex::blueprint::router::GET;
use pavex::blueprint::Blueprint;
use pavex::f;

pub fn bp() -> Blueprint {
    let mut bp = Blueprint::new();
    bp.prefix("/homes").nest({
        
        let mut bp = Blueprint::new();
        bp.route(GET, "/", f!(super::list_homes));
        bp.route(GET, "/{id}", f!(super::get_home));
        bp
    });
    bp.route(GET, "/", f!(super::index));
    bp
}

The prefix is prepended to the path of all routes nested under it.
In the example above, we end up with three different route paths:

  • /homes/ and /homes/{id}, after applying the /homes prefix
  • /, not influenced by the prefix

Prefixes are concatenated

You aren't limited to a single level of nesting. You can break down your routes into as many levels as you need—path prefixes will be concatenated in the order they were declared.

src/deep/blueprint.rs
use pavex::blueprint::router::GET;
use pavex::blueprint::Blueprint;
use pavex::f;

pub fn bp() -> Blueprint {
    let mut bp = Blueprint::new();
    bp.prefix("/homes").nest(homes_bp());
    bp
}

pub fn homes_bp() -> Blueprint {
    let mut bp = Blueprint::new();
    bp.route(GET, "/", f!(super::list_homes));
    bp.prefix("/{home_id}").nest(home_bp());
    bp
}

pub fn home_bp() -> Blueprint {
    let mut bp = Blueprint::new();
    bp.route(GET, "/", f!(super::get_home));
    bp.prefix("/rooms").nest(rooms_bp());
    bp
}

pub fn rooms_bp() -> Blueprint {
    let mut bp = Blueprint::new();
    bp.route(GET, "/", f!(super::list_rooms));
    bp.route(GET, "/{room_id}", f!(super::get_room));
    bp
}

The get_room request handler will be available at /homes/{home_id}/rooms/{room_id}, after prepending all relevant prefixes.

Path parameters are allowed

As shown in the previous example, your path prefixes can contain path parameters.
There is no difference between a path parameter in a prefix and a path parameter in a route path.

Restrictions

There are a few restrictions to keep in mind when using path prefixes:

  • Prefixes can't be empty.
  • Prefixes must start with a / character.
  • Prefixes must not end with a / character.

These constraints are enforced by Pavex at compile time.

Trailing slashes

Pavex forbids trailing / in path prefixes as a safety measure.
It's easy to accidentally end up with consecutive / if a prefix ends with a /—e.g. /prefix//path, using /prefix/ as prefix and /path for your route.

Since consecutive slashes are rarely desirable, you must add them explicitly to your route path if that's what you want:

src/consecutive/blueprint.rs
use pavex::blueprint::router::GET;
use pavex::blueprint::Blueprint;
use pavex::f;

pub fn bp() -> Blueprint {
    let mut bp = Blueprint::new();
    bp.prefix("/prefix").nest({
        let mut bp = Blueprint::new();
        bp.route(GET, "//path", f!(super::handler));
        bp
    });
    bp
}