Last active
July 23, 2020 11:24
-
-
Save rebo/009079899e3b5521b6d196b95342de7e to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// | |
// ... | |
// Regular Seed app/init/model/msg stuff here.. | |
// ... | |
// | |
#[wasm_bindgen(start)] | |
pub fn start() { | |
let app = App::start("app", init, update, view); | |
my_app().set(Some(app)); | |
} | |
#[atom] | |
fn my_app() -> Atom<Option<App<Msg,Model,Node<Msg>>>>{ | |
None | |
} | |
#[derive(Debug, Default, Validate, Deserialize,Clone)] | |
struct SignupData { | |
#[validate(email)] | |
mail: String, | |
#[validate(url)] | |
site: String, | |
#[validate(length(min = 1), custom = "validate_unique_username")] | |
#[serde(rename = "firstName")] | |
first_name: String, | |
#[validate(range(min = 18, max = 45))] | |
age: u32, | |
} | |
// User struct for querying server | |
#[derive(Deserialize, Debug,Clone)] | |
pub struct User { | |
id: u32, | |
email: String, | |
username:String, | |
phone:String, | |
} | |
fn validate_unique_username(username: &str) -> Result<(), ValidationError> { | |
if username == "xXxShad0wxXx" { | |
// the value of the username will automatically be added later | |
return Err(ValidationError::new("terrible_username")); | |
} | |
Ok(()) | |
} | |
#[atom] | |
fn signup_data() -> Atom<SignupData> { | |
SignupData::default() | |
} | |
#[reaction] | |
fn client_validation() -> Reaction<Result<(), ValidationErrors>> { | |
signup_data().observe().validate() | |
} | |
#[atom] | |
fn server_validation_response() -> Atom<Result<Result<(), ValidationErrors>, String >>{ | |
Err("Not Checked Yet".to_string()) | |
} | |
#[reaction] | |
fn server_validation() -> Reaction<()> { // we dont care about the return value here | |
if let Ok(_) = client_validation().observe() { | |
let signup_data = signup_data().get(); | |
// The below does a fetch request for the username from Json Placeholder mock site | |
// it needs to match the first_name field from the struct for it to pas validation | |
spawn_local({ | |
async move { | |
let fetch_url = "https://jsonplaceholder.typicode.com/users/1"; | |
let response = fetch(fetch_url).await.expect("HTTP request failed"); | |
match response.check_status(){ | |
Ok(response) => { | |
let user = response | |
.json::<User>() | |
.await | |
.expect("deserialization failed"); | |
log!(user.username); | |
if user.username == signup_data.first_name { | |
server_validation_response().update(|r| | |
*r = Ok(Ok(())) | |
) | |
} else { | |
server_validation_response().update(|r| | |
*r = Err(format!("Usernames dont match!! it should be {}", user.username )) | |
) | |
} | |
}, | |
Err(_error) => { | |
server_validation_response().update(|r| *r = Err("server connection error".to_string() )) | |
} | |
} | |
my_app().get().unwrap().update_with_option(None); | |
} | |
}); | |
} | |
} | |
#[reaction] | |
fn form_widget() -> Reaction<Node<Msg>> { | |
let form_data = signup_data().observe(); | |
let client_errors = client_validation().observe(); | |
let server_errors = server_validation_response().observe(); | |
server_validation().observe(); | |
div![ | |
form![ | |
s().style_child("input").b_width(px(1)).b_color("gray").b_style_solid().display_block(), | |
label!["Mail"], | |
input![attrs![At::Value => form_data.mail ], signup_data().on_input(|data,inp| data.mail = inp)], | |
label!["Site"], | |
input![attrs![At::Value => form_data.site ], signup_data().on_input(|data,inp| data.site = inp)], | |
label!["First Name"], | |
input![attrs![At::Value => form_data.first_name ], signup_data().on_input(|data,inp| data.first_name = inp)], | |
label!["Age"], | |
input![attrs![At::Value => form_data.age ], signup_data().on_input(|data,inp| data.age = inp.parse::<u32>().unwrap())], | |
], | |
h1!["Client Errors: "], | |
match client_errors { | |
Ok(_) => span!["None"], | |
Err(err) => pre![format!("{:#?}",err)], | |
}, | |
h1!["Server Errors: "], | |
match server_errors { | |
Ok(Ok(_)) => span!["None"], | |
Ok(Err(err)) => pre![format!("{:#?}",err)], | |
Err(err) => pre![err], | |
} | |
] | |
} | |
#[topo::nested] // Needed for Seed Hooks | |
pub fn view(_model: &Model) -> Node<Msg> { | |
form_widget().get() | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment