pub trait HistoryProvider<R: Routable> {
    // Required methods
    fn current_route(&self) -> R;
    fn go_back(&mut self);
    fn go_forward(&mut self);
    fn push(&mut self, route: R);
    fn replace(&mut self, path: R);

    // Provided methods
    fn current_prefix(&self) -> Option<String> { ... }
    fn can_go_back(&self) -> bool { ... }
    fn can_go_forward(&self) -> bool { ... }
    fn external(&mut self, url: String) -> bool { ... }
    fn updater(&mut self, callback: Arc<dyn Fn() + Send + Sync>) { ... }
}
Expand description

An integration with some kind of navigation history.

Depending on your use case, your implementation may deviate from the described procedure. This is fine, as long as both current_route and current_query match the described format.

However, you should document all deviations. Also, make sure the navigation is user-friendly. The described behaviors are designed to mimic a web browser, which most users should already know. Deviations might confuse them.

Required Methods§

source

fn current_route(&self) -> R

Get the path of the current URL.

Must start with /. Must not contain the prefix.

#[derive(Clone, Routable, Debug, PartialEq)]
enum Route {
    #[route("/")]
    Index {},
    #[route("/some-other-page")]
    OtherPage {},
}
let mut history = MemoryHistory::<Route>::default();
assert_eq!(history.current_route().to_string(), "/");

history.push(Route::OtherPage {});
assert_eq!(history.current_route().to_string(), "/some-other-page");
source

fn go_back(&mut self)

Go back to a previous page.

If a HistoryProvider cannot go to a previous page, it should do nothing. This method might be called, even if can_go_back returns false.

#[derive(Clone, Routable, Debug, PartialEq)]
enum Route {
    #[route("/")]
    Index {},
    #[route("/some-other-page")]
    OtherPage {},
}
let mut history = MemoryHistory::<Route>::default();
assert_eq!(history.current_route().to_string(), "/");

history.go_back();
assert_eq!(history.current_route().to_string(), "/");

history.push(Route::OtherPage {});
assert_eq!(history.current_route().to_string(), "/some-other-page");

history.go_back();
assert_eq!(history.current_route().to_string(), "/");
source

fn go_forward(&mut self)

Go forward to a future page.

If a HistoryProvider cannot go to a previous page, it should do nothing. This method might be called, even if can_go_forward returns false.

#[derive(Clone, Routable, Debug, PartialEq)]
enum Route {
    #[route("/")]
    Index {},
    #[route("/some-other-page")]
    OtherPage {},
}
let mut history = MemoryHistory::<Route>::default();
history.push(Route::OtherPage {});
assert_eq!(history.current_route(), Route::OtherPage {});

history.go_back();
assert_eq!(history.current_route(), Route::Index {});

history.go_forward();
assert_eq!(history.current_route(), Route::OtherPage {});
source

fn push(&mut self, route: R)

Go to another page.

This should do three things:

  1. Merge the current URL with the path parameter (which may also include a query part).
  2. Remove the previous URL to the navigation history.
  3. Clear the navigation future.
#[derive(Clone, Routable, Debug, PartialEq)]
enum Route {
    #[route("/")]
    Index {},
    #[route("/some-other-page")]
    OtherPage {},
}
let mut history = MemoryHistory::<Route>::default();
assert_eq!(history.current_route(), Route::Index {});

history.push(Route::OtherPage {});
assert_eq!(history.current_route(), Route::OtherPage {});
assert!(history.can_go_back());
source

fn replace(&mut self, path: R)

Replace the current page with another one.

This should merge the current URL with the path parameter (which may also include a query part). In contrast to the push function, the navigation history and future should stay untouched.

#[derive(Clone, Routable, Debug, PartialEq)]
enum Route {
    #[route("/")]
    Index {},
    #[route("/some-other-page")]
    OtherPage {},
}
let mut history = MemoryHistory::<Route>::default();
assert_eq!(history.current_route(), Route::Index {});

history.replace(Route::OtherPage {});
assert_eq!(history.current_route(), Route::OtherPage {});
assert!(!history.can_go_back());

Provided Methods§

source

fn current_prefix(&self) -> Option<String>

Get the current path prefix of the URL.

Not all HistoryProviders need a prefix feature. It is meant for environments where a dioxus-router-core-routed application is not running on /. The HistoryProvider is responsible for removing the prefix from the dioxus-router-core-internal path, and also for adding it back in during navigation. This functions value is only used for creating hrefs (e.g. for SSR or display (but not navigation) in a web app).

source

fn can_go_back(&self) -> bool

Check whether there is a previous page to navigate back to.

If a HistoryProvider cannot know this, it should return true.

#[derive(Clone, Routable, Debug, PartialEq)]
enum Route {
    #[route("/")]
    Index {},
    #[route("/other")]
    Other {},
}
let mut history = MemoryHistory::<Route>::default();
assert_eq!(history.can_go_back(), false);

history.push(Route::Other {});
assert_eq!(history.can_go_back(), true);
source

fn can_go_forward(&self) -> bool

Check whether there is a future page to navigate forward to.

If a HistoryProvider cannot know this, it should return true.

#[derive(Clone, Routable, Debug, PartialEq)]
enum Route {
    #[route("/")]
    Index {},
    #[route("/some-other-page")]
    OtherPage {},
}
let mut history = MemoryHistory::<Route>::default();
assert_eq!(history.can_go_forward(), false);

history.push(Route::OtherPage {});
assert_eq!(history.can_go_forward(), false);

history.go_back();
assert_eq!(history.can_go_forward(), true);
source

fn external(&mut self, url: String) -> bool

Navigate to an external URL.

This should navigate to an external URL, which isn’t controlled by the router. If a HistoryProvider cannot do that, it should return false, otherwise true.

Returning false will cause the router to handle the external navigation failure.

source

fn updater(&mut self, callback: Arc<dyn Fn() + Send + Sync>)

Provide the HistoryProvider with an update callback.

Some HistoryProviders may receive URL updates from outside the router. When such updates are received, they should call callback, which will cause the router to update.

Implementors§