mirror of
https://github.com/RGBCube/serenity
synced 2025-07-26 19:37:36 +00:00
LibWeb: Port URL and URLSearchParams to new String
This commit is contained in:
parent
843c9d6cd7
commit
9da09e4fd3
12 changed files with 229 additions and 157 deletions
|
@ -32,7 +32,7 @@ HTMLButtonElement::HTMLButtonElement(DOM::Document& document, DOM::QualifiedName
|
|||
case TypeAttributeState::Submit:
|
||||
// Submit Button
|
||||
// Submit element's form owner from element.
|
||||
form()->submit_form(this);
|
||||
form()->submit_form(this).release_value_but_fixme_should_propagate_errors();
|
||||
break;
|
||||
case TypeAttributeState::Reset:
|
||||
// Reset Button
|
||||
|
|
|
@ -47,21 +47,21 @@ void HTMLFormElement::visit_edges(Cell::Visitor& visitor)
|
|||
visitor.visit(element.ptr());
|
||||
}
|
||||
|
||||
void HTMLFormElement::submit_form(JS::GCPtr<HTMLElement> submitter, bool from_submit_binding)
|
||||
ErrorOr<void> HTMLFormElement::submit_form(JS::GCPtr<HTMLElement> submitter, bool from_submit_binding)
|
||||
{
|
||||
if (cannot_navigate())
|
||||
return;
|
||||
return {};
|
||||
|
||||
if (action().is_null()) {
|
||||
dbgln("Unsupported form action ''");
|
||||
return;
|
||||
return {};
|
||||
}
|
||||
|
||||
auto effective_method = method().to_lowercase();
|
||||
|
||||
if (effective_method == "dialog") {
|
||||
dbgln("Failed to submit form: Unsupported form method '{}'", method());
|
||||
return;
|
||||
return {};
|
||||
}
|
||||
|
||||
if (effective_method != "get" && effective_method != "post") {
|
||||
|
@ -70,7 +70,7 @@ void HTMLFormElement::submit_form(JS::GCPtr<HTMLElement> submitter, bool from_su
|
|||
|
||||
if (!from_submit_binding) {
|
||||
if (m_firing_submission_events)
|
||||
return;
|
||||
return {};
|
||||
|
||||
m_firing_submission_events = true;
|
||||
|
||||
|
@ -91,51 +91,56 @@ void HTMLFormElement::submit_form(JS::GCPtr<HTMLElement> submitter, bool from_su
|
|||
m_firing_submission_events = false;
|
||||
|
||||
if (!continue_)
|
||||
return;
|
||||
return {};
|
||||
|
||||
// This is checked again because arbitrary JS may have run when handling submit,
|
||||
// which may have changed the result.
|
||||
if (cannot_navigate())
|
||||
return;
|
||||
return {};
|
||||
}
|
||||
|
||||
AK::URL url(document().parse_url(action()));
|
||||
|
||||
if (!url.is_valid()) {
|
||||
dbgln("Failed to submit form: Invalid URL: {}", action());
|
||||
return;
|
||||
return {};
|
||||
}
|
||||
|
||||
if (url.scheme() == "file") {
|
||||
if (document().url().scheme() != "file") {
|
||||
dbgln("Failed to submit form: Security violation: {} may not submit to {}", document().url(), url);
|
||||
return;
|
||||
return {};
|
||||
}
|
||||
if (effective_method != "get") {
|
||||
dbgln("Failed to submit form: Unsupported form method '{}' for URL: {}", method(), url);
|
||||
return;
|
||||
return {};
|
||||
}
|
||||
} else if (url.scheme() != "http" && url.scheme() != "https") {
|
||||
dbgln("Failed to submit form: Unsupported protocol for URL: {}", url);
|
||||
return;
|
||||
return {};
|
||||
}
|
||||
|
||||
Vector<URL::QueryParam> parameters;
|
||||
|
||||
for_each_in_inclusive_subtree_of_type<HTMLInputElement>([&](auto& input) {
|
||||
if (!input.name().is_null() && (input.type() != "submit" || &input == submitter))
|
||||
parameters.append({ input.name(), input.value() });
|
||||
if (!input.name().is_null() && (input.type() != "submit" || &input == submitter)) {
|
||||
auto name = String::from_deprecated_string(input.name()).release_value_but_fixme_should_propagate_errors();
|
||||
auto value = String::from_deprecated_string(input.value()).release_value_but_fixme_should_propagate_errors();
|
||||
parameters.append({ move(name), move(value) });
|
||||
}
|
||||
return IterationDecision::Continue;
|
||||
});
|
||||
|
||||
if (effective_method == "get") {
|
||||
url.set_query(url_encode(parameters, AK::URL::PercentEncodeSet::ApplicationXWWWFormUrlencoded));
|
||||
auto url_encoded_parameters = TRY(url_encode(parameters, AK::URL::PercentEncodeSet::ApplicationXWWWFormUrlencoded)).to_deprecated_string();
|
||||
url.set_query(move(url_encoded_parameters));
|
||||
}
|
||||
|
||||
LoadRequest request = LoadRequest::create_for_url_on_page(url, document().page());
|
||||
|
||||
if (effective_method == "post") {
|
||||
auto body = url_encode(parameters, AK::URL::PercentEncodeSet::ApplicationXWWWFormUrlencoded).to_byte_buffer();
|
||||
auto url_encoded_parameters_as_bytes = TRY(url_encode(parameters, AK::URL::PercentEncodeSet::ApplicationXWWWFormUrlencoded)).bytes();
|
||||
auto body = TRY(ByteBuffer::copy(url_encoded_parameters_as_bytes));
|
||||
request.set_method("POST");
|
||||
request.set_header("Content-Type", "application/x-www-form-urlencoded");
|
||||
request.set_body(move(body));
|
||||
|
@ -143,6 +148,8 @@ void HTMLFormElement::submit_form(JS::GCPtr<HTMLElement> submitter, bool from_su
|
|||
|
||||
if (auto* page = document().page())
|
||||
page->load(request);
|
||||
|
||||
return {};
|
||||
}
|
||||
|
||||
// https://html.spec.whatwg.org/multipage/form-control-infrastructure.html#resetting-a-form
|
||||
|
@ -166,9 +173,12 @@ void HTMLFormElement::reset_form()
|
|||
}
|
||||
}
|
||||
|
||||
void HTMLFormElement::submit()
|
||||
WebIDL::ExceptionOr<void> HTMLFormElement::submit()
|
||||
{
|
||||
submit_form(this, true);
|
||||
auto& vm = realm().vm();
|
||||
|
||||
TRY_OR_THROW_OOM(vm, submit_form(this, true));
|
||||
return {};
|
||||
}
|
||||
|
||||
// https://html.spec.whatwg.org/multipage/forms.html#dom-form-reset
|
||||
|
|
|
@ -22,12 +22,12 @@ public:
|
|||
DeprecatedString action() const;
|
||||
DeprecatedString method() const { return attribute(HTML::AttributeNames::method); }
|
||||
|
||||
void submit_form(JS::GCPtr<HTMLElement> submitter, bool from_submit_binding = false);
|
||||
ErrorOr<void> submit_form(JS::GCPtr<HTMLElement> submitter, bool from_submit_binding = false);
|
||||
|
||||
void reset_form();
|
||||
|
||||
// NOTE: This is for the JS bindings. Use submit_form instead.
|
||||
void submit();
|
||||
WebIDL::ExceptionOr<void> submit();
|
||||
|
||||
// NOTE: This is for the JS bindings. Use submit_form instead.
|
||||
void reset();
|
||||
|
|
|
@ -35,7 +35,7 @@ HTMLInputElement::HTMLInputElement(DOM::Document& document, DOM::QualifiedName q
|
|||
// FIXME: 1. If this element is not mutable and is not in the Checkbox state and is not in the Radio state, then return.
|
||||
|
||||
// 2. Run this element's input activation behavior, if any, and do nothing otherwise.
|
||||
run_input_activation_behavior();
|
||||
run_input_activation_behavior().release_value_but_fixme_should_propagate_errors();
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -217,12 +217,12 @@ WebIDL::ExceptionOr<void> HTMLInputElement::show_picker()
|
|||
}
|
||||
|
||||
// https://html.spec.whatwg.org/multipage/input.html#input-activation-behavior
|
||||
void HTMLInputElement::run_input_activation_behavior()
|
||||
ErrorOr<void> HTMLInputElement::run_input_activation_behavior()
|
||||
{
|
||||
if (type_state() == TypeAttributeState::Checkbox || type_state() == TypeAttributeState::RadioButton) {
|
||||
// 1. If the element is not connected, then return.
|
||||
if (!is_connected())
|
||||
return;
|
||||
return {};
|
||||
|
||||
// 2. Fire an event named input at the element with the bubbles and composed attributes initialized to true.
|
||||
auto input_event = DOM::Event::create(realm(), HTML::EventNames::input).release_value_but_fixme_should_propagate_errors();
|
||||
|
@ -238,19 +238,21 @@ void HTMLInputElement::run_input_activation_behavior()
|
|||
JS::GCPtr<HTMLFormElement> form;
|
||||
// 1. If the element does not have a form owner, then return.
|
||||
if (!(form = this->form()))
|
||||
return;
|
||||
return {};
|
||||
|
||||
// 2. If the element's node document is not fully active, then return.
|
||||
if (!document().is_fully_active())
|
||||
return;
|
||||
return {};
|
||||
|
||||
// 3. Submit the form owner from the element.
|
||||
form->submit_form(this);
|
||||
TRY(form->submit_form(this));
|
||||
} else if (type_state() == TypeAttributeState::FileUpload) {
|
||||
show_the_picker_if_applicable(*this);
|
||||
} else {
|
||||
dispatch_event(DOM::Event::create(realm(), EventNames::change).release_value_but_fixme_should_propagate_errors());
|
||||
}
|
||||
|
||||
return {};
|
||||
}
|
||||
|
||||
void HTMLInputElement::did_edit_text_node(Badge<BrowsingContext>)
|
||||
|
|
|
@ -139,7 +139,7 @@ private:
|
|||
|
||||
static TypeAttributeState parse_type_attribute(StringView);
|
||||
void create_shadow_tree_if_needed();
|
||||
void run_input_activation_behavior();
|
||||
ErrorOr<void> run_input_activation_behavior();
|
||||
void set_checked_within_group();
|
||||
|
||||
// https://html.spec.whatwg.org/multipage/input.html#value-sanitization-algorithm
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue