().await {
let has_admin = data["has_admin"].as_bool().unwrap_or(false);
admin_exists.set(Some(has_admin));
}
}
_ => {
admin_exists.set(Some(false));
}
}
});
|| ()
});
}
match *admin_exists {
None => html! { { "Lade..." }
},
Some(false) => {
navigator.push(&Route::Setup);
html! { { "Leite weiter zur Einrichtung..." }
}
}
Some(true) => props.children.clone().into(),
}
}
/// The main routing logic for the application.
///
/// This function takes a [`Route`] enum variant and returns the corresponding HTML
/// content to be rendered. It acts as a central dispatcher for the application's
/// navigation and authentication flow.
///
/// Most routes are wrapped in [`ProtectedRoute`] to enforce authentication
/// and authorization based on the `admin_page` flag, and in [`SidebarShell`] to maintain consistent layout.
/// Login and Setup routes use [`AdminCheckWrapper`] instead to handle pre-authentication states.
///
/// # Arguments
/// - `route`: The [`Route`] enum variant representing the current URL path.
///
/// # Returns
/// An `Html` component that should be rendered for the given route.
///
/// # Route Protection
/// - **Admin-required routes** (`admin_page={true}`): Require both authentication and admin privileges
/// - **Public routes** (`admin_page={false}`): Require only authentication
/// - **Pre-auth routes** (`AdminCheckWrapper`): Used before admin creation or login
fn switch(route: Route) -> Html {
match route {
Route::Home => html! {
},
Route::NotFound => html! { },
Route::Ticket => html! {
},
Route::TicketById { id } => html! {
},
Route::AllTickets => html! {
},
Route::ArchivedTickets => html! {
},
Route::Register => html! {
},
Route::Login => html! {
},
Route::Setup => html! {
},
Route::AllUsers => html! {
},
Route::UserByID { id } => html! {
},
Route::PermissionDenied => html! { },
Route::Diagnostics => html! {
},
}
}
/// The root component of the Yew application.
///
/// This component sets up the application's routing using `yew-router`'s
/// `BrowserRouter` and `Switch` components. All other application content
/// is rendered based on the current [`Route`] matched by the `switch` function.
///
/// Uses [`switch`] as the routing dispatcher to handle all route-specific rendering,
/// which applies appropriate middleware like [`ProtectedRoute`] and [`AdminCheckWrapper`].
///
/// # Structure
/// - `BrowserRouter`: Enables client-side routing.
/// - `Switch`: Renders components based on the matched [`Route`].
/// - `switch` function: Determines which component to render for each route.
#[component(App)]
pub fn app() -> Html {
html! {
render={switch} />
}
}