fix web history

This commit is contained in:
Evan Almloff committed 2023-05-23 11:58:12 -05:00
1 parent b91fb39142
commit dd48c5a163
5 files changed
+45 -15

No files matched your search

+1 -4
View File
@@ -3,7 +3,6 @@ use log::error;
use std::{cell::RefCell, str::FromStr}; use std::{cell::RefCell, str::FromStr};
use crate::{ use crate::{
history::HistoryProvider,
prelude::{outlet::OutletContext, RouterContext}, prelude::{outlet::OutletContext, RouterContext},
routable::Routable, routable::Routable,
router_cfg::RouterConfiguration, router_cfg::RouterConfiguration,
@@ -26,9 +25,7 @@ impl<R: Routable> PartialEq for RouterProps<R> {
} }
/// A component that renders the current route. /// A component that renders the current route.
pub fn Router<R: Routable + Clone, H: HistoryProvider<R> + Default + 'static>( pub fn Router<R: Routable + Clone>(cx: Scope<RouterProps<R>>) -> Element
cx: Scope<RouterProps<R>>,
) -> Element
where where
<R as FromStr>::Err: std::fmt::Display, <R as FromStr>::Err: std::fmt::Display,
{ {
+23 -5
View File
@@ -76,7 +76,10 @@ impl<R> RouterContext<R>
where where
R: Routable, R: Routable,
{ {
pub(crate) fn new(cfg: RouterConfiguration<R>, mark_dirty: Arc<dyn Fn(ScopeId)>) -> Self pub(crate) fn new(
cfg: RouterConfiguration<R>,
mark_dirty: Arc<dyn Fn(ScopeId) + Sync + Send>,
) -> Self
where where
R: Clone, R: Clone,
{ {
@@ -87,17 +90,32 @@ where
history: cfg.history, history: cfg.history,
})); }));
Self { let subscriber_update = mark_dirty.clone();
let subscribers = Arc::new(RwLock::new(HashSet::new()));
let myself = Self {
state, state,
subscribers: Arc::new(RwLock::new(HashSet::new())), subscribers: subscribers.clone(),
subscriber_update: mark_dirty, subscriber_update,
routing_callback: cfg.on_update, routing_callback: cfg.on_update,
failure_external_navigation: cfg.failure_external_navigation, failure_external_navigation: cfg.failure_external_navigation,
failure_named_navigation: cfg.failure_named_navigation, failure_named_navigation: cfg.failure_named_navigation,
failure_redirection_limit: cfg.failure_redirection_limit, failure_redirection_limit: cfg.failure_redirection_limit,
};
// set the updater
{
let mut state = myself.state.write().unwrap();
state.history.updater(Arc::new(move || {
for &id in subscribers.read().unwrap().iter() {
(mark_dirty)(id);
}
}));
} }
myself
} }
/// Check whether there is a previous page to navigate back to. /// Check whether there is a previous page to navigate back to.
@@ -161,7 +179,7 @@ where
where where
R: Clone, R: Clone,
{ {
self.state.read().unwrap().history.current_route().clone() self.state.read().unwrap().history.current_route()
} }
/// The prefix that is currently active. /// The prefix that is currently active.
+8 -2
View File
@@ -45,6 +45,12 @@ pub struct WebHistory<R: Serialize + DeserializeOwned> {
phantom: std::marker::PhantomData<R>, phantom: std::marker::PhantomData<R>,
} }
impl<R: Serialize + DeserializeOwned> Default for WebHistory<R> {
fn default() -> Self {
Self::new(None, true)
}
}
impl<R: Serialize + DeserializeOwned> WebHistory<R> { impl<R: Serialize + DeserializeOwned> WebHistory<R> {
/// Create a new [`WebHistory`]. /// Create a new [`WebHistory`].
/// ///
@@ -97,9 +103,9 @@ where
<R as std::str::FromStr>::Err: std::fmt::Display, <R as std::str::FromStr>::Err: std::fmt::Display,
{ {
fn current_route(&self) -> R { fn current_route(&self) -> R {
match get_current(&self.history) { match get_current::<WebHistoryState<_>>(&self.history) {
// Try to get the route from the history state // Try to get the route from the history state
Some(route) => route, Some(route) => route.state,
// If that fails, get the route from the current URL // If that fails, get the route from the current URL
None => R::from_str( None => R::from_str(
&self &self
+12 -4
View File
@@ -1,3 +1,4 @@
use gloo::console::error;
use gloo_utils::format::JsValueSerdeExt; use gloo_utils::format::JsValueSerdeExt;
use serde::{de::DeserializeOwned, Serialize}; use serde::{de::DeserializeOwned, Serialize};
use wasm_bindgen::JsValue; use wasm_bindgen::JsValue;
@@ -24,8 +25,15 @@ pub(crate) fn push_state_and_url<V: Serialize>(
} }
pub(crate) fn get_current<V: DeserializeOwned>(history: &History) -> Option<V> { pub(crate) fn get_current<V: DeserializeOwned>(history: &History) -> Option<V> {
history let state = history.state();
.state() if let Err(err) = &state {
.ok() error!(err);
.and_then(|state| state.into_serde().ok()) }
state.ok().and_then(|state| {
let deserialized = state.into_serde();
if let Err(err) = &deserialized {
error!(format!("{}", err));
}
deserialized.ok()
})
} }
+1
View File
@@ -47,6 +47,7 @@ pub mod prelude {
pub use crate::components::*; pub use crate::components::*;
pub use crate::contexts::*; pub use crate::contexts::*;
pub use crate::hooks::*; pub use crate::hooks::*;
pub use crate::router_cfg::RouterConfiguration;
pub use dioxus_router_macro::routable; pub use dioxus_router_macro::routable;
} }