From c1fbf31a274c89a47c4681f56fff6aacb7789fae Mon Sep 17 00:00:00 2001 From: serzhiio Date: Mon, 15 Jan 2024 17:21:05 +0400 Subject: [PATCH] Form fields with same name can aggregate in array of values. --- packages/web/src/event.rs | 53 +++++++++++++++++++++------------------ 1 file changed, 28 insertions(+), 25 deletions(-) diff --git a/packages/web/src/event.rs b/packages/web/src/event.rs index 2e9632eae..da242f569 100644 --- a/packages/web/src/event.rs +++ b/packages/web/src/event.rs @@ -389,7 +389,27 @@ impl HasFormData for WebFormData { } fn values(&self) -> HashMap { - let mut values = std::collections::HashMap::new(); + let mut values = HashMap::new(); + + fn insert_value(map: &mut HashMap, key: String, new_value: String) { + match map.entry(key) { + std::collections::hash_map::Entry::Occupied(mut o) => { + let first_value = match o.get_mut() { + FormValue::Text(data) => { + std::mem::take(data) + } + FormValue::VecText(vec) => { + vec.push(new_value); + return + } + }; + let _ = o.insert(FormValue::VecText(vec![first_value, new_value])); + } + std::collections::hash_map::Entry::Vacant(v) => { + let _ = v.insert(FormValue::Text(new_value)); + } + } + }; // try to fill in form values if let Some(form) = self.element.dyn_ref::() { @@ -398,24 +418,19 @@ impl HasFormData for WebFormData { if let Ok(array) = value.dyn_into::() { if let Some(name) = array.get(0).as_string() { if let Ok(item_values) = array.get(1).dyn_into::() { - let item_values: Vec = - item_values.iter().filter_map(|v| v.as_string()).collect(); - - values.insert(name, FormValue::VecText(item_values)); + item_values.iter() + .filter_map(|v| v.as_string()) + .for_each(|v| { + insert_value(&mut values, name.clone(), v) + }); } else if let Ok(item_value) = array.get(1).dyn_into::() { - values.insert(name, FormValue::Text(item_value.as_string().unwrap())); + insert_value(&mut values, name, item_value.as_string().unwrap()); } } } } } - // try to fill in select element values - if let Some(select) = self.element.dyn_ref::() { - let options = get_select_data(select); - values.insert("options".to_string(), FormValue::VecText(options)); - } - values } @@ -536,19 +551,7 @@ export function get_form_data(form) { const formData = new FormData(form); for (let name of formData.keys()) { - const fieldType = form.elements[name].type; - console.log(fieldType); - - switch (fieldType) { - case "select-multiple": - values.set(name, formData.getAll(name)); - break; - - // add cases for fieldTypes that can hold multiple values here - default: - values.set(name, formData.get(name)); - break; - } + values.set(name, formData.getAll(name)); } return values;