diff options
| author | Benedikt Peetz <benedikt.peetz@b-peetz.de> | 2026-03-19 07:45:14 +0100 |
|---|---|---|
| committer | Benedikt Peetz <benedikt.peetz@b-peetz.de> | 2026-03-19 07:45:14 +0100 |
| commit | f6a3fb9c4d8dd86f78c9f75a23c1ac35bf35d4eb (patch) | |
| tree | 5f28fbca03d83921b568f7cb1708374456d9ec42 /src/pages/login.rs | |
| parent | feat(treewide): Add further buttons (diff) | |
| download | web-client-f6a3fb9c4d8dd86f78c9f75a23c1ac35bf35d4eb.zip | |
feat(treewide): Commit MVP
Diffstat (limited to 'src/pages/login.rs')
| -rw-r--r-- | src/pages/login.rs | 81 |
1 files changed, 81 insertions, 0 deletions
diff --git a/src/pages/login.rs b/src/pages/login.rs new file mode 100644 index 0000000..af3f660 --- /dev/null +++ b/src/pages/login.rs @@ -0,0 +1,81 @@ +use leptos::{ + IntoView, component, + prelude::{Get, Show, signal}, + task::spawn_local, + view, +}; +use leptos_router::{ + NavigateOptions, + hooks::{use_navigate, use_query_map}, +}; +use rocie_client::models::LoginInfo; +use rocie_macros::Form; + +use crate::{ + api::{get_config, login_external_wrapped}, + components::{banner::Banner, catch_errors::CatchErrors, site_header::SiteHeader}, +}; + +#[component] +pub fn Login() -> impl IntoView { + let back = || { + let back = use_query_map() + .get() + .get("back") + .expect("Should always have a back, because the router would otherwise not match"); + + if back.starts_with('/') { + back + } else { + // Prevent a redirect like `/login?back=https://gnu.org` to work + "/".to_owned() + } + }; + + let (error_message, error_message_set) = signal(None); + + view! { + <CatchErrors> + <SiteHeader logo=icondata_io::IoArrowBack back_location="/" name="Login" /> + + <Show when=move || error_message.get().is_some()> + <Banner text=move || error_message.get().expect("Is some") /> + </Show> + + { + Form! { + on_submit = |user_name, password| { + let config = get_config!(); + let navigate = use_navigate(); + let back = back(); + + spawn_local(async move { + match login_external_wrapped( + &config, + LoginInfo { user_name, password } + ).await { + Ok(()) => { + navigate(back.as_str(), NavigateOptions::default()); + } + Err(err) => error_message_set.set(Some(format!("Failed to login: {err}"))), + } + }); + }; + + <Input + name=user_name, + rust_type=String, + html_type="text", + label="Username" + /> + <Input + name=password, + rust_type=String, + html_type="password", + label="Password" + /> + } + } + </CatchErrors> + } +} |
