setup.rs
⎇
Raw
1use crate::i18n;
2use leptos::prelude::*;
3use wasm_bindgen_futures::spawn_local;
4
5use crate::api::{self, Me, input_value};
6use crate::app::AuthPhase;
7use crate::components::logo::Logo;
8use crate::router::{Location, navigate};
9
10#[component]
11pub fn SetupView(
12 set_me: WriteSignal<Option<Me>>,
13 set_phase: WriteSignal<AuthPhase>,
14) -> impl IntoView {
15 let (error, set_error) = signal(String::new());
16 let (busy, set_busy) = signal(false);
17
18 let on_submit = move |ev: web_sys::SubmitEvent| {
19 ev.prevent_default();
20 let name = input_value("setup-name");
21 let pass = input_value("setup-pass");
22 let confirm = input_value("setup-confirm");
23 let name = name.trim();
24
25 if name.is_empty() || name.len() > 64 {
26 set_error.set(i18n::t(i18n::k::SETUP_NAME_ERR).into());
27 return;
28 }
29 if pass.len() < 8 {
30 set_error.set(i18n::t(i18n::k::PW_SHORT).into());
31 return;
32 }
33 if pass != confirm {
34 set_error.set(i18n::t(i18n::k::SETUP_PW_MISMATCH).into());
35 return;
36 }
37
38 set_error.set(String::new());
39 set_busy.set(true);
40 let (name, pass) = (name.to_string(), pass);
41 spawn_local(async move {
42 match api::setup(name, pass).await {
43 Ok(_) => match api::me().await {
44 Ok(m) => {
45 navigate(&Location::root());
46 set_me.set(Some(m));
47 set_phase.set(AuthPhase::Authed);
48 }
49 Err(e) => {
50 set_error.set(e.to_string());
51 set_busy.set(false);
52 }
53 },
54 Err(e) => {
55 set_error.set(e.to_string());
56 set_busy.set(false);
57 }
58 }
59 });
60 };
61
62 view! {
63 <div class="center-screen">
64 <div class="card auth-card">
65 <Logo class="auth-logo".to_string()/>
66 <h1>"filebrowser-ng"</h1>
67 <p class="muted">{i18n::tr(i18n::k::SETUP_INTRO)}</p>
68 <form on:submit=on_submit>
69 <label class="field">
70 <span>{i18n::tr(i18n::k::NAME)}</span>
71 <input
72 id="setup-name"
73 type="text"
74 autofocus=true
75 autocomplete="username"
76 />
77 </label>
78 <label class="field">
79 <span>{i18n::tr(i18n::k::PASSWORD)}</span>
80 <input
81 id="setup-pass"
82 type="password"
83 autocomplete="new-password"
84 />
85 </label>
86 <label class="field">
87 <span>{i18n::tr(i18n::k::REPEAT_PASSWORD)}</span>
88 <input
89 id="setup-confirm"
90 type="password"
91 autocomplete="new-password"
92 />
93 </label>
94 <p class="error">{move || error.get()}</p>
95 <button class="btn-primary" type="submit" disabled=move || busy.get()>
96 {i18n::tr(i18n::k::CREATE_ADMIN)}
97 </button>
98 </form>
99 </div>
100 </div>
101 }
102}
103