diff options
author | bors-servo <lbergstrom+bors@mozilla.com> | 2019-12-10 07:50:27 -0500 |
---|---|---|
committer | GitHub <noreply@github.com> | 2019-12-10 07:50:27 -0500 |
commit | 4d5bf653f72a4ebf02c627eda7c5fa7f3744cbe8 (patch) | |
tree | 05b0d5187d3665ab7d001f2a62f548255c5d8134 | |
parent | 8a7de32d5b8b735caf21d45d3b007ebc2644e7dd (diff) | |
parent | 7f41b1b2941824451de81febb5bee135fb863f62 (diff) | |
download | servo-4d5bf653f72a4ebf02c627eda7c5fa7f3744cbe8.tar.gz servo-4d5bf653f72a4ebf02c627eda7c5fa7f3744cbe8.zip |
Auto merge of #25217 - pshaughn:fix25150, r=jdm
hidden field named _charset_ now appears in FormData as UTF-8
<!-- Please describe your changes on the following line: -->
HTMLInputElement now has special case logic for putting a hidden field named `_charset_` in an entry set. To support this, the encoding used when constructing a form dataset is now being passed further down the callchain than it was before.
---
<!-- Thank you for contributing to Servo! Please replace each `[ ]` by `[X]` when the step is complete, and replace `___` with appropriate data: -->
- [X] `./mach build -d` does not report any errors
- [X] `./mach test-tidy` does not report any errors
- [X] These changes fix #25150
<!-- Either: -->
- [X] There are tests for these changes
<!-- Also, please make sure that "Allow edits from maintainers" checkbox is checked, so that we can help you if you get stuck somewhere along the way.-->
<!-- Pull requests that do not address these steps are welcome, but they will require additional verification as part of the review process. -->
4 files changed, 44 insertions, 18 deletions
diff --git a/components/script/dom/formdata.rs b/components/script/dom/formdata.rs index 7a084ca0162..d0572e9b0e1 100644 --- a/components/script/dom/formdata.rs +++ b/components/script/dom/formdata.rs @@ -55,7 +55,7 @@ impl FormData { form: Option<&HTMLFormElement>, ) -> Fallible<DomRoot<FormData>> { if let Some(opt_form) = form { - return match opt_form.get_form_dataset(None) { + return match opt_form.get_form_dataset(None, None) { Some(form_datums) => Ok(FormData::new(Some(form_datums), global)), None => Err(Error::InvalidState), }; diff --git a/components/script/dom/htmlformelement.rs b/components/script/dom/htmlformelement.rs index 913f5f8530a..f4135ac3e0a 100755 --- a/components/script/dom/htmlformelement.rs +++ b/components/script/dom/htmlformelement.rs @@ -357,7 +357,7 @@ impl HTMLFormElement { let encoding = self.pick_encoding(); // Step 9 - let mut form_data = match self.get_form_dataset(Some(submitter)) { + let mut form_data = match self.get_form_dataset(Some(submitter), Some(encoding)) { Some(form_data) => form_data, None => return, }; @@ -645,8 +645,14 @@ impl HTMLFormElement { } /// <https://html.spec.whatwg.org/multipage/#constructing-the-form-data-set> + /// terminology note: "form data set" = "entry list" /// Steps range from 3 to 5 - fn get_unclean_dataset(&self, submitter: Option<FormSubmitter>) -> Vec<FormDatum> { + /// 5.x substeps are mostly handled inside element-specific methods + fn get_unclean_dataset( + &self, + submitter: Option<FormSubmitter>, + encoding: Option<&'static Encoding>, + ) -> Vec<FormDatum> { let controls = self.controls.borrow(); let mut data_set = Vec::new(); for child in controls.iter() { @@ -668,7 +674,7 @@ impl HTMLFormElement { HTMLElementTypeId::HTMLInputElement => { let input = child.downcast::<HTMLInputElement>().unwrap(); - data_set.append(&mut input.form_datums(submitter)); + data_set.append(&mut input.form_datums(submitter, encoding)); }, HTMLElementTypeId::HTMLButtonElement => { let button = child.downcast::<HTMLButtonElement>().unwrap(); @@ -705,7 +711,11 @@ impl HTMLFormElement { } /// <https://html.spec.whatwg.org/multipage/#constructing-the-form-data-set> - pub fn get_form_dataset(&self, submitter: Option<FormSubmitter>) -> Option<Vec<FormDatum>> { + pub fn get_form_dataset( + &self, + submitter: Option<FormSubmitter>, + encoding: Option<&'static Encoding>, + ) -> Option<Vec<FormDatum>> { fn clean_crlf(s: &str) -> DOMString { // Step 4 let mut buf = "".to_owned(); @@ -746,7 +756,7 @@ impl HTMLFormElement { self.constructing_entry_list.set(true); // Step 3-6 - let mut ret = self.get_unclean_dataset(submitter); + let mut ret = self.get_unclean_dataset(submitter, encoding); for datum in &mut ret { match &*datum.ty { "file" | "textarea" => (), // TODO diff --git a/components/script/dom/htmlinputelement.rs b/components/script/dom/htmlinputelement.rs index b48dfbc42db..9018f05813a 100755 --- a/components/script/dom/htmlinputelement.rs +++ b/components/script/dom/htmlinputelement.rs @@ -49,6 +49,7 @@ use crate::textinput::{Direction, SelectionDirection, TextInput, UTF16CodeUnits, use caseless::compatibility_caseless_match_str; use dom_struct::dom_struct; use embedder_traits::FilterPattern; +use encoding_rs::Encoding; use html5ever::{LocalName, Prefix}; use msg::constellation_msg::InputMethodType; use net_traits::blob_url_store::get_blob_origin; @@ -929,14 +930,18 @@ impl HTMLInputElement { } /// <https://html.spec.whatwg.org/multipage/#constructing-the-form-data-set> - /// Steps range from 3.1 to 3.7 (specific to HTMLInputElement) - pub fn form_datums(&self, submitter: Option<FormSubmitter>) -> Vec<FormDatum> { + /// Steps range from 5.1 to 5.10 (specific to HTMLInputElement) + pub fn form_datums( + &self, + submitter: Option<FormSubmitter>, + encoding: Option<&'static Encoding>, + ) -> Vec<FormDatum> { // 3.1: disabled state check is in get_unclean_dataset - // Step 3.2 + // Step 5.2 let ty = self.Type(); - // Step 3.4 + // Step 5.4 let name = self.Name(); let is_submitter = match submitter { Some(FormSubmitter::InputElement(s)) => self == s, @@ -944,12 +949,12 @@ impl HTMLInputElement { }; match self.input_type() { - // Step 3.1: it's a button but it is not submitter. + // Step 5.1: it's a button but it is not submitter. InputType::Submit | InputType::Button | InputType::Reset if !is_submitter => { return vec![]; }, - // Step 3.1: it's the "Checkbox" or "Radio Button" and whose checkedness is false. + // Step 5.1: it's the "Checkbox" or "Radio Button" and whose checkedness is false. InputType::Radio | InputType::Checkbox => { if !self.Checked() || name.is_empty() { return vec![]; @@ -959,7 +964,7 @@ impl HTMLInputElement { InputType::File => { let mut datums = vec![]; - // Step 3.2-3.7 + // Step 5.2-5.7 let name = self.Name(); match self.GetFiles() { @@ -988,7 +993,21 @@ impl HTMLInputElement { InputType::Image => return vec![], // Unimplemented - // Step 3.1: it's not the "Image Button" and doesn't have a name attribute. + // Step 5.10: it's a hidden field named _charset_ + InputType::Hidden => { + if name == "_charset_" { + return vec![FormDatum { + ty: ty.clone(), + name: name, + value: FormDatumValue::String(match encoding { + None => DOMString::from("UTF-8"), + Some(enc) => DOMString::from(enc.name()), + }), + }]; + } + }, + + // Step 5.1: it's not the "Image Button" and doesn't have a name attribute. _ => { if name.is_empty() { return vec![]; @@ -996,7 +1015,7 @@ impl HTMLInputElement { }, } - // Step 3.9 + // Step 5.12 vec![FormDatum { ty: ty.clone(), name: name, diff --git a/tests/wpt/metadata/html/semantics/forms/form-submission-0/constructing-form-data-set.html.ini b/tests/wpt/metadata/html/semantics/forms/form-submission-0/constructing-form-data-set.html.ini index ee52a142650..4a1159022d0 100644 --- a/tests/wpt/metadata/html/semantics/forms/form-submission-0/constructing-form-data-set.html.ini +++ b/tests/wpt/metadata/html/semantics/forms/form-submission-0/constructing-form-data-set.html.ini @@ -1,7 +1,4 @@ [constructing-form-data-set.html] - [FormData constructor always produces UTF-8 _charset_ value.] - expected: FAIL - [_charset_ control sets the expected encoding name.] expected: FAIL |