1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-05-31 09:38:11 +00:00

LibWeb: Do not use HTMLFormElement::elements to get submittable elements

HTMLFormElement::elements is not the correct filter for submittable
elements. It includes non-submittable elements (HTMLObjectElement) and
also excludes submittable elements (HTMLInputElements in the "image"
type state, "for historical reasons").
This commit is contained in:
Timothy Flynn 2024-02-18 21:52:27 -05:00 committed by Andreas Kling
parent debb5690ce
commit 986811d2aa
3 changed files with 14 additions and 27 deletions

View file

@ -51,8 +51,6 @@ WebIDL::ExceptionOr<XHR::FormDataEntry> create_entry(JS::Realm& realm, String co
// https://html.spec.whatwg.org/multipage/form-control-infrastructure.html#constructing-the-form-data-set // https://html.spec.whatwg.org/multipage/form-control-infrastructure.html#constructing-the-form-data-set
WebIDL::ExceptionOr<Optional<Vector<XHR::FormDataEntry>>> construct_entry_list(JS::Realm& realm, HTMLFormElement& form, JS::GCPtr<HTMLElement> submitter, Optional<String> encoding) WebIDL::ExceptionOr<Optional<Vector<XHR::FormDataEntry>>> construct_entry_list(JS::Realm& realm, HTMLFormElement& form, JS::GCPtr<HTMLElement> submitter, Optional<String> encoding)
{ {
auto& vm = realm.vm();
// 1. If form's constructing entry list is true, then return null. // 1. If form's constructing entry list is true, then return null.
if (form.constructing_entry_list()) if (form.constructing_entry_list())
return Optional<Vector<XHR::FormDataEntry>> {}; return Optional<Vector<XHR::FormDataEntry>> {};
@ -61,7 +59,7 @@ WebIDL::ExceptionOr<Optional<Vector<XHR::FormDataEntry>>> construct_entry_list(J
form.set_constructing_entry_list(true); form.set_constructing_entry_list(true);
// 3. Let controls be a list of all the submittable elements whose form owner is form, in tree order. // 3. Let controls be a list of all the submittable elements whose form owner is form, in tree order.
auto controls = TRY_OR_THROW_OOM(vm, form.get_submittable_elements()); auto controls = form.get_submittable_elements();
// 4. Let entry list be a new empty entry list. // 4. Let entry list be a new empty entry list.
Vector<XHR::FormDataEntry> entry_list; Vector<XHR::FormDataEntry> entry_list;

View file

@ -538,31 +538,22 @@ WebIDL::ExceptionOr<bool> HTMLFormElement::report_validity()
} }
// https://html.spec.whatwg.org/multipage/forms.html#category-submit // https://html.spec.whatwg.org/multipage/forms.html#category-submit
ErrorOr<Vector<JS::NonnullGCPtr<DOM::Element>>> HTMLFormElement::get_submittable_elements() Vector<JS::NonnullGCPtr<DOM::Element>> HTMLFormElement::get_submittable_elements()
{ {
Vector<JS::NonnullGCPtr<DOM::Element>> submittable_elements = {}; Vector<JS::NonnullGCPtr<DOM::Element>> submittable_elements;
for (size_t i = 0; i < elements()->length(); i++) {
auto* element = elements()->item(i); root().for_each_in_subtree([&](auto& node) {
TRY(populate_vector_with_submittable_elements_in_tree_order(*element, submittable_elements)); if (auto* form_associated_element = dynamic_cast<FormAssociatedElement*>(&node)) {
} if (form_associated_element->is_submittable() && form_associated_element->form() == this)
submittable_elements.append(form_associated_element->form_associated_element_to_html_element());
}
return IterationDecision::Continue;
});
return submittable_elements; return submittable_elements;
} }
ErrorOr<void> HTMLFormElement::populate_vector_with_submittable_elements_in_tree_order(JS::NonnullGCPtr<DOM::Element> element, Vector<JS::NonnullGCPtr<DOM::Element>>& elements)
{
if (auto* form_associated_element = dynamic_cast<HTML::FormAssociatedElement*>(element.ptr())) {
if (form_associated_element->is_submittable())
TRY(elements.try_append(element));
}
for (size_t i = 0; i < element->children()->length(); i++) {
auto* child = element->children()->item(i);
TRY(populate_vector_with_submittable_elements_in_tree_order(*child, elements));
}
return {};
}
// https://html.spec.whatwg.org/multipage/form-control-infrastructure.html#dom-fs-method // https://html.spec.whatwg.org/multipage/form-control-infrastructure.html#dom-fs-method
StringView HTMLFormElement::method() const StringView HTMLFormElement::method() const
{ {

View file

@ -74,7 +74,7 @@ public:
void add_associated_element(Badge<FormAssociatedElement>, HTMLElement&); void add_associated_element(Badge<FormAssociatedElement>, HTMLElement&);
void remove_associated_element(Badge<FormAssociatedElement>, HTMLElement&); void remove_associated_element(Badge<FormAssociatedElement>, HTMLElement&);
ErrorOr<Vector<JS::NonnullGCPtr<DOM::Element>>> get_submittable_elements(); Vector<JS::NonnullGCPtr<DOM::Element>> get_submittable_elements();
JS::NonnullGCPtr<DOM::HTMLFormControlsCollection> elements() const; JS::NonnullGCPtr<DOM::HTMLFormControlsCollection> elements() const;
unsigned length() const; unsigned length() const;
@ -109,8 +109,6 @@ private:
virtual Vector<FlyString> supported_property_names() const override; virtual Vector<FlyString> supported_property_names() const override;
virtual bool is_supported_property_index(u32) const override; virtual bool is_supported_property_index(u32) const override;
ErrorOr<void> populate_vector_with_submittable_elements_in_tree_order(JS::NonnullGCPtr<DOM::Element> element, Vector<JS::NonnullGCPtr<DOM::Element>>& elements);
ErrorOr<String> pick_an_encoding() const; ErrorOr<String> pick_an_encoding() const;
ErrorOr<void> mutate_action_url(AK::URL parsed_action, Vector<XHR::FormDataEntry> entry_list, String encoding, JS::NonnullGCPtr<Navigable> target_navigable, Bindings::NavigationHistoryBehavior history_handling, UserNavigationInvolvement user_involvement); ErrorOr<void> mutate_action_url(AK::URL parsed_action, Vector<XHR::FormDataEntry> entry_list, String encoding, JS::NonnullGCPtr<Navigable> target_navigable, Bindings::NavigationHistoryBehavior history_handling, UserNavigationInvolvement user_involvement);