You cannot select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
111 lines
3.7 KiB
Rust
111 lines
3.7 KiB
Rust
//! UI binary entrypoint for quotesdb.
|
|
//!
|
|
//! Compiled to WebAssembly via Trunk targeting `wasm32-unknown-unknown`.
|
|
//! Runs the Yew single-page application with client-side routing.
|
|
//!
|
|
//! All functional code is gated on `wasm32` — yew, web-sys, and wasm-bindgen
|
|
//! are wasm32-only crates unavailable on native targets.
|
|
|
|
#[cfg(target_arch = "wasm32")]
|
|
mod api;
|
|
#[cfg(target_arch = "wasm32")]
|
|
mod components;
|
|
#[cfg(target_arch = "wasm32")]
|
|
mod pages;
|
|
#[cfg(target_arch = "wasm32")]
|
|
mod storage;
|
|
|
|
#[cfg(target_arch = "wasm32")]
|
|
use yew::prelude::*;
|
|
#[cfg(target_arch = "wasm32")]
|
|
use yew_router::prelude::*;
|
|
|
|
/// Application routes matching the frontend route definitions in the design spec.
|
|
///
|
|
/// Routes map to page components. The `NotFound` variant catches all unmatched paths.
|
|
#[cfg(target_arch = "wasm32")]
|
|
#[derive(Clone, Routable, PartialEq)]
|
|
pub enum Route {
|
|
/// Home page — displays a random quote.
|
|
#[at("/")]
|
|
Home,
|
|
/// Browse page — paginated list of quotes with filters.
|
|
#[at("/browse")]
|
|
Browse,
|
|
/// Single quote view/edit/delete page.
|
|
#[at("/quotes/:id")]
|
|
QuoteDetail { id: String },
|
|
/// All quotes by a specific author.
|
|
#[at("/author/:name")]
|
|
Author { name: String },
|
|
/// New quote submission form.
|
|
#[at("/submit")]
|
|
Submit,
|
|
/// Admin panel for managing submissions lock and auth codes.
|
|
#[at("/admin")]
|
|
Admin,
|
|
/// Catch-all 404 page.
|
|
#[not_found]
|
|
#[at("/404")]
|
|
NotFound,
|
|
}
|
|
|
|
/// Route switch function — maps each `Route` variant to its page component.
|
|
#[cfg(target_arch = "wasm32")]
|
|
fn switch(routes: Route) -> Html {
|
|
match routes {
|
|
Route::Home => html! { <pages::home::HomePage /> },
|
|
Route::Browse => html! { <pages::browse::BrowsePage /> },
|
|
Route::QuoteDetail { id } => html! { <pages::quote::QuotePage id={id} /> },
|
|
Route::Author { name } => html! { <pages::author::AuthorPage name={name} /> },
|
|
Route::Submit => html! { <pages::submit::SubmitPage /> },
|
|
Route::Admin => html! { <pages::admin::AdminPage /> },
|
|
Route::NotFound => html! {
|
|
<div class="page-not-found">
|
|
<h1>{ "404 — Page Not Found" }</h1>
|
|
<p>{ "The page you are looking for does not exist." }</p>
|
|
<a href="/">{ "Go home" }</a>
|
|
</div>
|
|
},
|
|
}
|
|
}
|
|
|
|
/// Root application component.
|
|
///
|
|
/// Wraps the entire application in a `BrowserRouter` and renders the
|
|
/// route-switched page components via `Switch`.
|
|
#[cfg(target_arch = "wasm32")]
|
|
#[function_component(App)]
|
|
fn app() -> Html {
|
|
html! {
|
|
<BrowserRouter>
|
|
<nav class="nav">
|
|
<Link<Route> to={Route::Home} classes="nav__brand">{ "QuotesDB" }</Link<Route>>
|
|
<div class="nav__links">
|
|
<Link<Route> to={Route::Browse} classes="nav__link">{ "Browse" }</Link<Route>>
|
|
<Link<Route> to={Route::Submit} classes="nav__link">{ "Submit" }</Link<Route>>
|
|
</div>
|
|
</nav>
|
|
<main class="main-content">
|
|
<Switch<Route> render={switch} />
|
|
</main>
|
|
<footer class="site-footer">
|
|
<p>{ "Contact: " }<a href="mailto:quotes@elijah.run">{ "quotes@elijah.run" }</a></p>
|
|
</footer>
|
|
</BrowserRouter>
|
|
}
|
|
}
|
|
|
|
/// WASM entry point — called by the Trunk-generated JS bootstrap.
|
|
#[cfg(target_arch = "wasm32")]
|
|
fn main() {
|
|
yew::Renderer::<App>::new().render();
|
|
}
|
|
|
|
/// Stub entry point for native targets.
|
|
///
|
|
/// The UI binary is only meaningful when compiled for wasm32 via Trunk.
|
|
/// This stub satisfies the Rust binary requirement on other targets.
|
|
#[cfg(not(target_arch = "wasm32"))]
|
|
fn main() {}
|