mirror of
https://github.com/LadybirdBrowser/ladybird.git
synced 2025-12-07 21:59:54 +00:00
Everywhere: Hoist the Libraries folder to the top-level
This commit is contained in:
parent
950e819ee7
commit
93712b24bf
Notes:
github-actions[bot]
2024-11-10 11:51:52 +00:00
Author: https://github.com/trflynn89
Commit: 93712b24bf
Pull-request: https://github.com/LadybirdBrowser/ladybird/pull/2256
Reviewed-by: https://github.com/sideshowbarker
4547 changed files with 104 additions and 113 deletions
28
Libraries/LibWeb/XHR/EventNames.cpp
Normal file
28
Libraries/LibWeb/XHR/EventNames.cpp
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
/*
|
||||
* Copyright (c) 2021, the SerenityOS developers.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#include <LibWeb/XHR/EventNames.h>
|
||||
|
||||
namespace Web::XHR::EventNames {
|
||||
|
||||
#define __ENUMERATE_XHR_EVENT(name) FlyString name;
|
||||
ENUMERATE_XHR_EVENTS
|
||||
#undef __ENUMERATE_XHR_EVENT
|
||||
|
||||
void initialize_strings()
|
||||
{
|
||||
static bool s_initialized = false;
|
||||
VERIFY(!s_initialized);
|
||||
|
||||
#define __ENUMERATE_XHR_EVENT(name) \
|
||||
name = #name##_fly_string;
|
||||
ENUMERATE_XHR_EVENTS
|
||||
#undef __ENUMERATE_XHR_EVENT
|
||||
|
||||
s_initialized = true;
|
||||
}
|
||||
|
||||
}
|
||||
30
Libraries/LibWeb/XHR/EventNames.h
Normal file
30
Libraries/LibWeb/XHR/EventNames.h
Normal file
|
|
@ -0,0 +1,30 @@
|
|||
/*
|
||||
* Copyright (c) 2021, the SerenityOS developers.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/Error.h>
|
||||
#include <AK/FlyString.h>
|
||||
|
||||
namespace Web::XHR::EventNames {
|
||||
|
||||
#define ENUMERATE_XHR_EVENTS \
|
||||
__ENUMERATE_XHR_EVENT(readystatechange) \
|
||||
__ENUMERATE_XHR_EVENT(loadstart) \
|
||||
__ENUMERATE_XHR_EVENT(progress) \
|
||||
__ENUMERATE_XHR_EVENT(abort) \
|
||||
__ENUMERATE_XHR_EVENT(error) \
|
||||
__ENUMERATE_XHR_EVENT(load) \
|
||||
__ENUMERATE_XHR_EVENT(timeout) \
|
||||
__ENUMERATE_XHR_EVENT(loadend)
|
||||
|
||||
#define __ENUMERATE_XHR_EVENT(name) extern FlyString name;
|
||||
ENUMERATE_XHR_EVENTS
|
||||
#undef __ENUMERATE_XHR_EVENT
|
||||
|
||||
void initialize_strings();
|
||||
|
||||
}
|
||||
194
Libraries/LibWeb/XHR/FormData.cpp
Normal file
194
Libraries/LibWeb/XHR/FormData.cpp
Normal file
|
|
@ -0,0 +1,194 @@
|
|||
/*
|
||||
* Copyright (c) 2023-2024, Kenneth Myhra <kennethmyhra@serenityos.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#include <AK/TypeCasts.h>
|
||||
#include <LibJS/Runtime/Completion.h>
|
||||
#include <LibWeb/Bindings/Intrinsics.h>
|
||||
#include <LibWeb/FileAPI/Blob.h>
|
||||
#include <LibWeb/FileAPI/File.h>
|
||||
#include <LibWeb/HTML/FormControlInfrastructure.h>
|
||||
#include <LibWeb/WebIDL/DOMException.h>
|
||||
#include <LibWeb/XHR/FormData.h>
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
JS_DEFINE_ALLOCATOR(FormData);
|
||||
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata
|
||||
WebIDL::ExceptionOr<JS::NonnullGCPtr<FormData>> FormData::construct_impl(JS::Realm& realm, JS::GCPtr<HTML::HTMLFormElement> form)
|
||||
{
|
||||
Vector<FormDataEntry> list;
|
||||
// 1. If form is given, then:
|
||||
if (form) {
|
||||
// 1. Let list be the result of constructing the entry list for form.
|
||||
auto entry_list = TRY(construct_entry_list(realm, *form));
|
||||
// 2. If list is null, then throw an "InvalidStateError" DOMException.
|
||||
if (!entry_list.has_value())
|
||||
return WebIDL::InvalidStateError::create(realm, "Form element does not contain any entries."_string);
|
||||
// 3. Set this’s entry list to list.
|
||||
list = entry_list.release_value();
|
||||
}
|
||||
|
||||
return construct_impl(realm, move(list));
|
||||
}
|
||||
|
||||
WebIDL::ExceptionOr<JS::NonnullGCPtr<FormData>> FormData::construct_impl(JS::Realm& realm, Vector<FormDataEntry> entry_list)
|
||||
{
|
||||
return realm.heap().allocate<FormData>(realm, realm, move(entry_list));
|
||||
}
|
||||
|
||||
WebIDL::ExceptionOr<JS::NonnullGCPtr<FormData>> FormData::create(JS::Realm& realm, Vector<DOMURL::QueryParam> entry_list)
|
||||
{
|
||||
Vector<FormDataEntry> list;
|
||||
list.ensure_capacity(entry_list.size());
|
||||
for (auto& entry : entry_list)
|
||||
list.unchecked_append({ .name = move(entry.name), .value = move(entry.value) });
|
||||
|
||||
return construct_impl(realm, move(list));
|
||||
}
|
||||
|
||||
FormData::FormData(JS::Realm& realm, Vector<FormDataEntry> entry_list)
|
||||
: PlatformObject(realm)
|
||||
, m_entry_list(move(entry_list))
|
||||
{
|
||||
}
|
||||
|
||||
FormData::~FormData() = default;
|
||||
|
||||
void FormData::initialize(JS::Realm& realm)
|
||||
{
|
||||
Base::initialize(realm);
|
||||
WEB_SET_PROTOTYPE_FOR_INTERFACE(FormData);
|
||||
}
|
||||
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-append
|
||||
WebIDL::ExceptionOr<void> FormData::append(String const& name, String const& value)
|
||||
{
|
||||
return append_impl(name, value);
|
||||
}
|
||||
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-append-blob
|
||||
WebIDL::ExceptionOr<void> FormData::append(String const& name, JS::NonnullGCPtr<FileAPI::Blob> const& blob_value, Optional<String> const& filename)
|
||||
{
|
||||
auto inner_filename = filename.has_value() ? filename.value() : Optional<String> {};
|
||||
return append_impl(name, blob_value, inner_filename);
|
||||
}
|
||||
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-append
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-append-blob
|
||||
WebIDL::ExceptionOr<void> FormData::append_impl(String const& name, Variant<JS::NonnullGCPtr<FileAPI::Blob>, String> const& value, Optional<String> const& filename)
|
||||
{
|
||||
auto& realm = this->realm();
|
||||
auto& vm = realm.vm();
|
||||
|
||||
// 1. Let value be value if given; otherwise blobValue.
|
||||
// 2. Let entry be the result of creating an entry with name, value, and filename if given.
|
||||
auto entry = TRY(HTML::create_entry(realm, name, value, filename));
|
||||
|
||||
// 3. Append entry to this’s entry list.
|
||||
TRY_OR_THROW_OOM(vm, m_entry_list.try_append(move(entry)));
|
||||
return {};
|
||||
}
|
||||
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-delete
|
||||
void FormData::delete_(String const& name)
|
||||
{
|
||||
// The delete(name) method steps are to remove all entries whose name is name from this’s entry list.
|
||||
m_entry_list.remove_all_matching([&name](FormDataEntry const& entry) {
|
||||
return entry.name == name;
|
||||
});
|
||||
}
|
||||
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-get
|
||||
Variant<JS::Handle<FileAPI::File>, String, Empty> FormData::get(String const& name)
|
||||
{
|
||||
// 1. If there is no entry whose name is name in this’s entry list, then return null.
|
||||
auto entry_iterator = m_entry_list.find_if([&name](FormDataEntry const& entry) {
|
||||
return entry.name == name;
|
||||
});
|
||||
if (entry_iterator.is_end())
|
||||
return Empty {};
|
||||
// 2. Return the value of the first entry whose name is name from this’s entry list.
|
||||
return entry_iterator->value;
|
||||
}
|
||||
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-getall
|
||||
WebIDL::ExceptionOr<Vector<FormDataEntryValue>> FormData::get_all(String const& name)
|
||||
{
|
||||
// 1. If there is no entry whose name is name in this’s entry list, then return the empty list.
|
||||
// 2. Return the values of all entries whose name is name, in order, from this’s entry list.
|
||||
Vector<FormDataEntryValue> values;
|
||||
for (auto const& entry : m_entry_list) {
|
||||
if (entry.name == name)
|
||||
TRY_OR_THROW_OOM(vm(), values.try_append(entry.value));
|
||||
}
|
||||
return values;
|
||||
}
|
||||
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-has
|
||||
bool FormData::has(String const& name)
|
||||
{
|
||||
// The has(name) method steps are to return true if there is an entry whose name is name in this’s entry list; otherwise false.
|
||||
return !m_entry_list.find_if([&name](auto& entry) {
|
||||
return entry.name == name;
|
||||
})
|
||||
.is_end();
|
||||
}
|
||||
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-set
|
||||
WebIDL::ExceptionOr<void> FormData::set(String const& name, String const& value)
|
||||
{
|
||||
return set_impl(name, value);
|
||||
}
|
||||
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-set-blob
|
||||
WebIDL::ExceptionOr<void> FormData::set(String const& name, JS::NonnullGCPtr<FileAPI::Blob> const& blob_value, Optional<String> const& filename)
|
||||
{
|
||||
auto inner_filename = filename.has_value() ? filename.value() : Optional<String> {};
|
||||
return set_impl(name, blob_value, inner_filename);
|
||||
}
|
||||
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-set
|
||||
// https://xhr.spec.whatwg.org/#dom-formdata-set-blob
|
||||
WebIDL::ExceptionOr<void> FormData::set_impl(String const& name, Variant<JS::NonnullGCPtr<FileAPI::Blob>, String> const& value, Optional<String> const& filename)
|
||||
{
|
||||
auto& realm = this->realm();
|
||||
auto& vm = realm.vm();
|
||||
|
||||
// 1. Let value be value if given; otherwise blobValue.
|
||||
// 2. Let entry be the result of creating an entry with name, value, and filename if given.
|
||||
auto entry = TRY(HTML::create_entry(realm, name, value, filename));
|
||||
|
||||
auto existing = m_entry_list.find_if([&name](auto& entry) {
|
||||
return entry.name == name;
|
||||
});
|
||||
|
||||
// 3. If there are entries in this’s entry list whose name is name, then replace the first such entry with entry and remove the others.
|
||||
if (!existing.is_end()) {
|
||||
existing->value = entry.value;
|
||||
m_entry_list.remove_all_matching([&name, &existing](auto& entry) {
|
||||
return &entry != &*existing && entry.name == name;
|
||||
});
|
||||
}
|
||||
// 4. Otherwise, append entry to this’s entry list.
|
||||
else {
|
||||
TRY_OR_THROW_OOM(vm, m_entry_list.try_append(move(entry)));
|
||||
}
|
||||
|
||||
return {};
|
||||
}
|
||||
|
||||
JS::ThrowCompletionOr<void> FormData::for_each(ForEachCallback callback)
|
||||
{
|
||||
for (auto i = 0u; i < m_entry_list.size(); ++i) {
|
||||
auto& entry = m_entry_list[i];
|
||||
TRY(callback(entry.name, entry.value));
|
||||
}
|
||||
|
||||
return {};
|
||||
}
|
||||
|
||||
}
|
||||
59
Libraries/LibWeb/XHR/FormData.h
Normal file
59
Libraries/LibWeb/XHR/FormData.h
Normal file
|
|
@ -0,0 +1,59 @@
|
|||
/*
|
||||
* Copyright (c) 2023-2024, Kenneth Myhra <kennethmyhra@serenityos.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LibWeb/Bindings/FormDataPrototype.h>
|
||||
#include <LibWeb/Bindings/PlatformObject.h>
|
||||
#include <LibWeb/DOMURL/URLSearchParams.h>
|
||||
#include <LibWeb/Forward.h>
|
||||
#include <LibWeb/HTML/HTMLFormElement.h>
|
||||
#include <LibWeb/WebIDL/ExceptionOr.h>
|
||||
#include <LibWeb/XHR/FormDataEntry.h>
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
// https://xhr.spec.whatwg.org/#interface-formdata
|
||||
class FormData : public Bindings::PlatformObject {
|
||||
WEB_PLATFORM_OBJECT(FormData, Bindings::PlatformObject);
|
||||
JS_DECLARE_ALLOCATOR(FormData);
|
||||
|
||||
public:
|
||||
virtual ~FormData() override;
|
||||
|
||||
static WebIDL::ExceptionOr<JS::NonnullGCPtr<FormData>> construct_impl(JS::Realm&, JS::GCPtr<HTML::HTMLFormElement> form = {});
|
||||
static WebIDL::ExceptionOr<JS::NonnullGCPtr<FormData>> construct_impl(JS::Realm&, Vector<FormDataEntry> entry_list);
|
||||
|
||||
static WebIDL::ExceptionOr<JS::NonnullGCPtr<FormData>> create(JS::Realm&, Vector<DOMURL::QueryParam> entry_list);
|
||||
|
||||
WebIDL::ExceptionOr<void> append(String const& name, String const& value);
|
||||
WebIDL::ExceptionOr<void> append(String const& name, JS::NonnullGCPtr<FileAPI::Blob> const& blob_value, Optional<String> const& filename = {});
|
||||
void delete_(String const& name);
|
||||
Variant<JS::Handle<FileAPI::File>, String, Empty> get(String const& name);
|
||||
WebIDL::ExceptionOr<Vector<FormDataEntryValue>> get_all(String const& name);
|
||||
bool has(String const& name);
|
||||
WebIDL::ExceptionOr<void> set(String const& name, String const& value);
|
||||
WebIDL::ExceptionOr<void> set(String const& name, JS::NonnullGCPtr<FileAPI::Blob> const& blob_value, Optional<String> const& filename = {});
|
||||
|
||||
Vector<FormDataEntry> const& entry_list() const { return m_entry_list; }
|
||||
|
||||
using ForEachCallback = Function<JS::ThrowCompletionOr<void>(String const&, FormDataEntryValue const&)>;
|
||||
JS::ThrowCompletionOr<void> for_each(ForEachCallback);
|
||||
|
||||
private:
|
||||
friend class FormDataIterator;
|
||||
|
||||
explicit FormData(JS::Realm&, Vector<FormDataEntry> entry_list = {});
|
||||
|
||||
virtual void initialize(JS::Realm&) override;
|
||||
|
||||
WebIDL::ExceptionOr<void> append_impl(String const& name, Variant<JS::NonnullGCPtr<FileAPI::Blob>, String> const& value, Optional<String> const& filename = {});
|
||||
WebIDL::ExceptionOr<void> set_impl(String const& name, Variant<JS::NonnullGCPtr<FileAPI::Blob>, String> const& value, Optional<String> const& filename = {});
|
||||
|
||||
Vector<FormDataEntry> m_entry_list;
|
||||
};
|
||||
|
||||
}
|
||||
27
Libraries/LibWeb/XHR/FormData.idl
Normal file
27
Libraries/LibWeb/XHR/FormData.idl
Normal file
|
|
@ -0,0 +1,27 @@
|
|||
#import <FileAPI/Blob.idl>
|
||||
#import <FileAPI/File.idl>
|
||||
// FIXME: This #import currently gives the following error after XHR/FormData.idl was #imported in Fetch/BodyInit.idl:
|
||||
// "LibWeb/HTML/Window.idl:114: error: Mixin 'WindowOrWorkerGlobalScope' was never defined."
|
||||
// XHR/FormData.idl needs to be #imported in Fetch/BodyInit.idl while removing #import HTML/HTMLFormElement.idl
|
||||
// currently makes no difference.
|
||||
// #import <HTML/HTMLFormElement.idl>
|
||||
|
||||
typedef (File or USVString) FormDataEntryValue;
|
||||
|
||||
// https://xhr.spec.whatwg.org/#interface-formdata
|
||||
[Exposed=(Window,Worker)]
|
||||
interface FormData {
|
||||
constructor(optional HTMLFormElement form);
|
||||
|
||||
undefined append(USVString name, USVString value);
|
||||
undefined append(USVString name, Blob blobValue, optional USVString filename);
|
||||
undefined delete(USVString name);
|
||||
// FIXME: The BindingsGenerator is not able to resolve the Variant's visit for FormDataEntryValue when
|
||||
// the return value for one function returns an optional FormDataEntryValue while the others does not.
|
||||
(File or USVString)? get(USVString name);
|
||||
sequence<FormDataEntryValue> getAll(USVString name);
|
||||
boolean has(USVString name);
|
||||
undefined set(USVString name, USVString value);
|
||||
undefined set(USVString name, Blob blobValue, optional USVString filename);
|
||||
iterable<USVString, FormDataEntryValue>;
|
||||
};
|
||||
24
Libraries/LibWeb/XHR/FormDataEntry.h
Normal file
24
Libraries/LibWeb/XHR/FormDataEntry.h
Normal file
|
|
@ -0,0 +1,24 @@
|
|||
/*
|
||||
* Copyright (c) 2023, Kenneth Myhra <kennethmyhra@serenityos.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/String.h>
|
||||
#include <AK/Variant.h>
|
||||
#include <LibJS/Heap/Handle.h>
|
||||
#include <LibWeb/Forward.h>
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
// https://xhr.spec.whatwg.org/#formdataentryvalue
|
||||
using FormDataEntryValue = Variant<JS::Handle<FileAPI::File>, String>;
|
||||
|
||||
struct FormDataEntry {
|
||||
String name;
|
||||
FormDataEntryValue value;
|
||||
};
|
||||
|
||||
}
|
||||
80
Libraries/LibWeb/XHR/FormDataIterator.cpp
Normal file
80
Libraries/LibWeb/XHR/FormDataIterator.cpp
Normal file
|
|
@ -0,0 +1,80 @@
|
|||
/*
|
||||
* Copyright (c) 2023, Kenneth Myhra <kennethmyhra@serenityos.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#include <LibJS/Runtime/Array.h>
|
||||
#include <LibJS/Runtime/Iterator.h>
|
||||
#include <LibWeb/Bindings/FormDataIteratorPrototype.h>
|
||||
#include <LibWeb/Bindings/Intrinsics.h>
|
||||
#include <LibWeb/FileAPI/File.h>
|
||||
#include <LibWeb/XHR/FormDataIterator.h>
|
||||
|
||||
namespace Web::Bindings {
|
||||
|
||||
template<>
|
||||
void Intrinsics::create_web_prototype_and_constructor<FormDataIteratorPrototype>(JS::Realm& realm)
|
||||
{
|
||||
auto prototype = heap().allocate<FormDataIteratorPrototype>(realm, realm);
|
||||
m_prototypes.set("FormDataIterator"_fly_string, prototype);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
JS_DEFINE_ALLOCATOR(FormDataIterator);
|
||||
|
||||
JS::NonnullGCPtr<FormDataIterator> FormDataIterator::create(FormData const& form_data, JS::Object::PropertyKind iterator_kind)
|
||||
{
|
||||
return form_data.heap().allocate<FormDataIterator>(form_data.realm(), form_data, iterator_kind);
|
||||
}
|
||||
|
||||
FormDataIterator::FormDataIterator(Web::XHR::FormData const& form_data, JS::Object::PropertyKind iterator_kind)
|
||||
: PlatformObject(form_data.realm())
|
||||
, m_form_data(form_data)
|
||||
, m_iterator_kind(iterator_kind)
|
||||
{
|
||||
}
|
||||
|
||||
FormDataIterator::~FormDataIterator() = default;
|
||||
|
||||
void FormDataIterator::initialize(JS::Realm& realm)
|
||||
{
|
||||
Base::initialize(realm);
|
||||
WEB_SET_PROTOTYPE_FOR_INTERFACE(FormDataIterator);
|
||||
}
|
||||
|
||||
void FormDataIterator::visit_edges(Cell::Visitor& visitor)
|
||||
{
|
||||
Base::visit_edges(visitor);
|
||||
visitor.visit(m_form_data);
|
||||
}
|
||||
|
||||
JS::Object* FormDataIterator::next()
|
||||
{
|
||||
auto& vm = this->vm();
|
||||
|
||||
if (m_index >= m_form_data->m_entry_list.size())
|
||||
return create_iterator_result_object(vm, JS::js_undefined(), true);
|
||||
|
||||
auto entry = m_form_data->m_entry_list[m_index++];
|
||||
if (m_iterator_kind == JS::Object::PropertyKind::Key)
|
||||
return create_iterator_result_object(vm, JS::PrimitiveString::create(vm, entry.name), false);
|
||||
|
||||
auto entry_value = entry.value.visit(
|
||||
[&](JS::Handle<FileAPI::File> const& file) -> JS::Value {
|
||||
return file.cell();
|
||||
},
|
||||
[&](String const& string) -> JS::Value {
|
||||
return JS::PrimitiveString::create(vm, string);
|
||||
});
|
||||
|
||||
if (m_iterator_kind == JS::Object::PropertyKind::Value)
|
||||
return create_iterator_result_object(vm, entry_value, false);
|
||||
|
||||
return create_iterator_result_object(vm, JS::Array::create_from(realm(), { JS::PrimitiveString::create(vm, entry.name), entry_value }), false).ptr();
|
||||
}
|
||||
|
||||
}
|
||||
36
Libraries/LibWeb/XHR/FormDataIterator.h
Normal file
36
Libraries/LibWeb/XHR/FormDataIterator.h
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
/*
|
||||
* Copyright (c) 2023, Kenneth Myhra <kennethmyhra@serenityos.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LibWeb/Bindings/PlatformObject.h>
|
||||
#include <LibWeb/XHR/FormData.h>
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
class FormDataIterator : public Bindings::PlatformObject {
|
||||
WEB_PLATFORM_OBJECT(FormDataIterator, Bindings::PlatformObject);
|
||||
JS_DECLARE_ALLOCATOR(FormDataIterator);
|
||||
|
||||
public:
|
||||
[[nodiscard]] static JS::NonnullGCPtr<FormDataIterator> create(FormData const&, JS::Object::PropertyKind iterator_kind);
|
||||
|
||||
virtual ~FormDataIterator() override;
|
||||
|
||||
JS::Object* next();
|
||||
|
||||
private:
|
||||
FormDataIterator(FormData const&, JS::Object::PropertyKind iterator_kind);
|
||||
|
||||
virtual void initialize(JS::Realm&) override;
|
||||
virtual void visit_edges(Cell::Visitor&) override;
|
||||
|
||||
JS::NonnullGCPtr<FormData const> m_form_data;
|
||||
JS::Object::PropertyKind m_iterator_kind;
|
||||
size_t m_index { 0 };
|
||||
};
|
||||
|
||||
}
|
||||
41
Libraries/LibWeb/XHR/ProgressEvent.cpp
Normal file
41
Libraries/LibWeb/XHR/ProgressEvent.cpp
Normal file
|
|
@ -0,0 +1,41 @@
|
|||
/*
|
||||
* Copyright (c) 2022, Andreas Kling <andreas@ladybird.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#include <LibWeb/Bindings/Intrinsics.h>
|
||||
#include <LibWeb/Bindings/ProgressEventPrototype.h>
|
||||
#include <LibWeb/XHR/ProgressEvent.h>
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
JS_DEFINE_ALLOCATOR(ProgressEvent);
|
||||
|
||||
JS::NonnullGCPtr<ProgressEvent> ProgressEvent::create(JS::Realm& realm, FlyString const& event_name, ProgressEventInit const& event_init)
|
||||
{
|
||||
return realm.heap().allocate<ProgressEvent>(realm, realm, event_name, event_init);
|
||||
}
|
||||
|
||||
WebIDL::ExceptionOr<JS::NonnullGCPtr<ProgressEvent>> ProgressEvent::construct_impl(JS::Realm& realm, FlyString const& event_name, ProgressEventInit const& event_init)
|
||||
{
|
||||
return create(realm, event_name, event_init);
|
||||
}
|
||||
|
||||
ProgressEvent::ProgressEvent(JS::Realm& realm, FlyString const& event_name, ProgressEventInit const& event_init)
|
||||
: Event(realm, event_name, event_init)
|
||||
, m_length_computable(event_init.length_computable)
|
||||
, m_loaded(event_init.loaded)
|
||||
, m_total(event_init.total)
|
||||
{
|
||||
}
|
||||
|
||||
ProgressEvent::~ProgressEvent() = default;
|
||||
|
||||
void ProgressEvent::initialize(JS::Realm& realm)
|
||||
{
|
||||
Base::initialize(realm);
|
||||
WEB_SET_PROTOTYPE_FOR_INTERFACE(ProgressEvent);
|
||||
}
|
||||
|
||||
}
|
||||
45
Libraries/LibWeb/XHR/ProgressEvent.h
Normal file
45
Libraries/LibWeb/XHR/ProgressEvent.h
Normal file
|
|
@ -0,0 +1,45 @@
|
|||
/*
|
||||
* Copyright (c) 2021, the SerenityOS developers.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/FlyString.h>
|
||||
#include <LibWeb/DOM/Event.h>
|
||||
#include <LibWeb/WebIDL/Types.h>
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
struct ProgressEventInit : public DOM::EventInit {
|
||||
bool length_computable { false };
|
||||
WebIDL::UnsignedLongLong loaded { 0 };
|
||||
WebIDL::UnsignedLongLong total { 0 };
|
||||
};
|
||||
|
||||
class ProgressEvent final : public DOM::Event {
|
||||
WEB_PLATFORM_OBJECT(ProgressEvent, DOM::Event);
|
||||
JS_DECLARE_ALLOCATOR(ProgressEvent);
|
||||
|
||||
public:
|
||||
[[nodiscard]] static JS::NonnullGCPtr<ProgressEvent> create(JS::Realm&, FlyString const& event_name, ProgressEventInit const& event_init);
|
||||
static WebIDL::ExceptionOr<JS::NonnullGCPtr<ProgressEvent>> construct_impl(JS::Realm&, FlyString const& event_name, ProgressEventInit const& event_init);
|
||||
|
||||
virtual ~ProgressEvent() override;
|
||||
|
||||
bool length_computable() const { return m_length_computable; }
|
||||
WebIDL::UnsignedLongLong loaded() const { return m_loaded; }
|
||||
WebIDL::UnsignedLongLong total() const { return m_total; }
|
||||
|
||||
private:
|
||||
ProgressEvent(JS::Realm&, FlyString const& event_name, ProgressEventInit const& event_init);
|
||||
|
||||
virtual void initialize(JS::Realm&) override;
|
||||
|
||||
bool m_length_computable { false };
|
||||
WebIDL::UnsignedLongLong m_loaded { 0 };
|
||||
WebIDL::UnsignedLongLong m_total { 0 };
|
||||
};
|
||||
|
||||
}
|
||||
17
Libraries/LibWeb/XHR/ProgressEvent.idl
Normal file
17
Libraries/LibWeb/XHR/ProgressEvent.idl
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
#import <DOM/Event.idl>
|
||||
|
||||
// https://xhr.spec.whatwg.org/#interface-progressevent
|
||||
[Exposed=(Window,Worker)]
|
||||
interface ProgressEvent : Event {
|
||||
constructor(DOMString type, optional ProgressEventInit eventInitDict = {});
|
||||
|
||||
readonly attribute boolean lengthComputable;
|
||||
readonly attribute unsigned long long loaded;
|
||||
readonly attribute unsigned long long total;
|
||||
};
|
||||
|
||||
dictionary ProgressEventInit : EventInit {
|
||||
boolean lengthComputable = false;
|
||||
unsigned long long loaded = 0;
|
||||
unsigned long long total = 0;
|
||||
};
|
||||
1296
Libraries/LibWeb/XHR/XMLHttpRequest.cpp
Normal file
1296
Libraries/LibWeb/XHR/XMLHttpRequest.cpp
Normal file
File diff suppressed because it is too large
Load diff
206
Libraries/LibWeb/XHR/XMLHttpRequest.h
Normal file
206
Libraries/LibWeb/XHR/XMLHttpRequest.h
Normal file
|
|
@ -0,0 +1,206 @@
|
|||
/*
|
||||
* Copyright (c) 2020-2021, Andreas Kling <andreas@ladybird.org>
|
||||
* Copyright (c) 2022, Kenneth Myhra <kennethmyhra@serenityos.org>
|
||||
* Copyright (c) 2023, Luke Wilde <lukew@serenityos.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/ByteBuffer.h>
|
||||
#include <AK/RefCounted.h>
|
||||
#include <AK/Weakable.h>
|
||||
#include <LibURL/URL.h>
|
||||
#include <LibWeb/DOM/EventTarget.h>
|
||||
#include <LibWeb/DOMURL/URLSearchParams.h>
|
||||
#include <LibWeb/Fetch/BodyInit.h>
|
||||
#include <LibWeb/Fetch/Infrastructure/HTTP/Bodies.h>
|
||||
#include <LibWeb/Fetch/Infrastructure/HTTP/Headers.h>
|
||||
#include <LibWeb/Fetch/Infrastructure/HTTP/Statuses.h>
|
||||
#include <LibWeb/HTML/Window.h>
|
||||
#include <LibWeb/MimeSniff/MimeType.h>
|
||||
#include <LibWeb/WebIDL/ExceptionOr.h>
|
||||
#include <LibWeb/XHR/XMLHttpRequestEventTarget.h>
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
// https://fetch.spec.whatwg.org/#typedefdef-xmlhttprequestbodyinit
|
||||
using DocumentOrXMLHttpRequestBodyInit = Variant<JS::Handle<Web::DOM::Document>, JS::Handle<Web::FileAPI::Blob>, JS::Handle<WebIDL::BufferSource>, JS::Handle<XHR::FormData>, JS::Handle<Web::DOMURL::URLSearchParams>, AK::String>;
|
||||
|
||||
class XMLHttpRequest final : public XMLHttpRequestEventTarget {
|
||||
WEB_PLATFORM_OBJECT(XMLHttpRequest, XMLHttpRequestEventTarget);
|
||||
JS_DECLARE_ALLOCATOR(XMLHttpRequest);
|
||||
|
||||
public:
|
||||
enum class State : u16 {
|
||||
Unsent = 0,
|
||||
Opened = 1,
|
||||
HeadersReceived = 2,
|
||||
Loading = 3,
|
||||
Done = 4,
|
||||
};
|
||||
|
||||
static WebIDL::ExceptionOr<JS::NonnullGCPtr<XMLHttpRequest>> construct_impl(JS::Realm&);
|
||||
|
||||
virtual ~XMLHttpRequest() override;
|
||||
|
||||
State ready_state() const { return m_state; }
|
||||
Fetch::Infrastructure::Status status() const;
|
||||
WebIDL::ExceptionOr<String> status_text() const;
|
||||
WebIDL::ExceptionOr<String> response_text() const;
|
||||
WebIDL::ExceptionOr<JS::GCPtr<DOM::Document>> response_xml();
|
||||
WebIDL::ExceptionOr<JS::Value> response();
|
||||
Bindings::XMLHttpRequestResponseType response_type() const { return m_response_type; }
|
||||
String response_url();
|
||||
|
||||
WebIDL::ExceptionOr<void> open(String const& method, String const& url);
|
||||
WebIDL::ExceptionOr<void> open(String const& method, String const& url, bool async, Optional<String> const& username = Optional<String> {}, Optional<String> const& password = Optional<String> {});
|
||||
WebIDL::ExceptionOr<void> send(Optional<DocumentOrXMLHttpRequestBodyInit> body);
|
||||
|
||||
WebIDL::ExceptionOr<void> set_request_header(String const& header, String const& value);
|
||||
WebIDL::ExceptionOr<void> set_response_type(Bindings::XMLHttpRequestResponseType);
|
||||
|
||||
WebIDL::ExceptionOr<Optional<String>> get_response_header(String const& name) const;
|
||||
WebIDL::ExceptionOr<String> get_all_response_headers() const;
|
||||
|
||||
WebIDL::CallbackType* onreadystatechange();
|
||||
void set_onreadystatechange(WebIDL::CallbackType*);
|
||||
|
||||
WebIDL::ExceptionOr<void> override_mime_type(String const& mime);
|
||||
|
||||
u32 timeout() const;
|
||||
WebIDL::ExceptionOr<void> set_timeout(u32 timeout);
|
||||
|
||||
bool with_credentials() const;
|
||||
WebIDL::ExceptionOr<void> set_with_credentials(bool);
|
||||
|
||||
void abort();
|
||||
|
||||
JS::NonnullGCPtr<XMLHttpRequestUpload> upload() const;
|
||||
|
||||
private:
|
||||
virtual void initialize(JS::Realm&) override;
|
||||
virtual void visit_edges(Cell::Visitor&) override;
|
||||
virtual bool must_survive_garbage_collection() const override;
|
||||
|
||||
[[nodiscard]] MimeSniff::MimeType get_response_mime_type() const;
|
||||
[[nodiscard]] Optional<StringView> get_final_encoding() const;
|
||||
[[nodiscard]] MimeSniff::MimeType get_final_mime_type() const;
|
||||
|
||||
String get_text_response() const;
|
||||
void set_document_response();
|
||||
|
||||
WebIDL::ExceptionOr<void> handle_response_end_of_body();
|
||||
WebIDL::ExceptionOr<void> handle_errors();
|
||||
JS::ThrowCompletionOr<void> request_error_steps(FlyString const& event_name, JS::GCPtr<WebIDL::DOMException> exception = nullptr);
|
||||
|
||||
XMLHttpRequest(JS::Realm&, XMLHttpRequestUpload&, Fetch::Infrastructure::HeaderList&, Fetch::Infrastructure::Response&, Fetch::Infrastructure::FetchController&);
|
||||
|
||||
// https://xhr.spec.whatwg.org/#upload-object
|
||||
// upload object
|
||||
// An XMLHttpRequestUpload object.
|
||||
JS::NonnullGCPtr<XMLHttpRequestUpload> m_upload_object;
|
||||
|
||||
// https://xhr.spec.whatwg.org/#concept-xmlhttprequest-state
|
||||
// state
|
||||
// One of unsent, opened, headers received, loading, and done; initially unsent.
|
||||
State m_state { State::Unsent };
|
||||
|
||||
// https://xhr.spec.whatwg.org/#send-flag
|
||||
// send() flag
|
||||
// A flag, initially unset.
|
||||
bool m_send { false };
|
||||
|
||||
// https://xhr.spec.whatwg.org/#timeout
|
||||
// timeout
|
||||
// An unsigned integer, initially 0.
|
||||
u32 m_timeout { 0 };
|
||||
|
||||
// https://xhr.spec.whatwg.org/#cross-origin-credentials
|
||||
// cross-origin credentials
|
||||
// A boolean, initially false.
|
||||
bool m_cross_origin_credentials { false };
|
||||
|
||||
// https://xhr.spec.whatwg.org/#request-method
|
||||
// request method
|
||||
// A method.
|
||||
ByteString m_request_method;
|
||||
|
||||
// https://xhr.spec.whatwg.org/#request-url
|
||||
// request URL
|
||||
// A URL.
|
||||
URL::URL m_request_url;
|
||||
|
||||
// https://xhr.spec.whatwg.org/#author-request-headers
|
||||
// author request headers
|
||||
// A header list, initially empty.
|
||||
JS::NonnullGCPtr<Fetch::Infrastructure::HeaderList> m_author_request_headers;
|
||||
|
||||
// https://xhr.spec.whatwg.org/#request-body
|
||||
// request body
|
||||
// Initially null.
|
||||
JS::GCPtr<Fetch::Infrastructure::Body> m_request_body;
|
||||
|
||||
// https://xhr.spec.whatwg.org/#synchronous-flag
|
||||
// synchronous flag
|
||||
// A flag, initially unset.
|
||||
bool m_synchronous { false };
|
||||
|
||||
// https://xhr.spec.whatwg.org/#upload-complete-flag
|
||||
// upload complete flag
|
||||
// A flag, initially unset.
|
||||
bool m_upload_complete { false };
|
||||
|
||||
// https://xhr.spec.whatwg.org/#upload-listener-flag
|
||||
// upload listener flag
|
||||
// A flag, initially unset.
|
||||
bool m_upload_listener { false };
|
||||
|
||||
// https://xhr.spec.whatwg.org/#timed-out-flag
|
||||
// timed out flag
|
||||
// A flag, initially unset.
|
||||
bool m_timed_out { false };
|
||||
|
||||
// https://xhr.spec.whatwg.org/#response
|
||||
// response
|
||||
// A response, initially a network error.
|
||||
JS::NonnullGCPtr<Fetch::Infrastructure::Response> m_response;
|
||||
|
||||
// https://xhr.spec.whatwg.org/#received-bytes
|
||||
// received bytes
|
||||
// A byte sequence, initially the empty byte sequence.
|
||||
ByteBuffer m_received_bytes;
|
||||
|
||||
// https://xhr.spec.whatwg.org/#response-type
|
||||
// response type
|
||||
// One of the empty string, "arraybuffer", "blob", "document", "json", and "text"; initially the empty string.
|
||||
Bindings::XMLHttpRequestResponseType m_response_type;
|
||||
|
||||
enum class Failure {
|
||||
/// ????
|
||||
};
|
||||
|
||||
// https://xhr.spec.whatwg.org/#response-object
|
||||
// response object
|
||||
// An object, failure, or null, initially null.
|
||||
// NOTE: This needs to be a JS::Value as the JSON response might not actually be an object.
|
||||
Variant<JS::NonnullGCPtr<JS::Object>, Failure, Empty> m_response_object;
|
||||
|
||||
// https://xhr.spec.whatwg.org/#xmlhttprequest-fetch-controller
|
||||
// fetch controller
|
||||
// A fetch controller, initially a new fetch controller.
|
||||
// NOTE: The send() method sets it to a useful fetch controller, but for simplicity it always holds a fetch controller.
|
||||
JS::NonnullGCPtr<Fetch::Infrastructure::FetchController> m_fetch_controller;
|
||||
|
||||
// https://xhr.spec.whatwg.org/#override-mime-type
|
||||
// override MIME type
|
||||
// A MIME type or null, initially null.
|
||||
// NOTE: Can get a value when overrideMimeType() is invoked.
|
||||
Optional<MimeSniff::MimeType> m_override_mime_type;
|
||||
|
||||
// Non-standard, see async path in `send()`
|
||||
u64 m_request_body_transmitted { 0 };
|
||||
};
|
||||
|
||||
}
|
||||
55
Libraries/LibWeb/XHR/XMLHttpRequest.idl
Normal file
55
Libraries/LibWeb/XHR/XMLHttpRequest.idl
Normal file
|
|
@ -0,0 +1,55 @@
|
|||
#import <DOM/Document.idl>
|
||||
#import <DOM/EventHandler.idl>
|
||||
#import <Fetch/BodyInit.idl>
|
||||
#import <XHR/XMLHttpRequestEventTarget.idl>
|
||||
#import <XHR/XMLHttpRequestUpload.idl>
|
||||
|
||||
enum XMLHttpRequestResponseType {
|
||||
"",
|
||||
"arraybuffer",
|
||||
"blob",
|
||||
"document",
|
||||
"json",
|
||||
"text"
|
||||
};
|
||||
|
||||
// https://xhr.spec.whatwg.org/#xmlhttprequest
|
||||
[Exposed=(Window,DedicatedWorker,SharedWorker)]
|
||||
interface XMLHttpRequest : XMLHttpRequestEventTarget {
|
||||
|
||||
constructor();
|
||||
|
||||
// event handler
|
||||
attribute EventHandler onreadystatechange;
|
||||
|
||||
// states
|
||||
const unsigned short UNSENT = 0;
|
||||
const unsigned short OPENED = 1;
|
||||
const unsigned short HEADERS_RECEIVED = 2;
|
||||
const unsigned short LOADING = 3;
|
||||
const unsigned short DONE = 4;
|
||||
readonly attribute unsigned short readyState;
|
||||
|
||||
// request
|
||||
undefined open(DOMString method, DOMString url);
|
||||
undefined open(ByteString method, USVString url, boolean async, optional USVString? username = null, optional USVString? password = null);
|
||||
undefined setRequestHeader(DOMString name, DOMString value);
|
||||
attribute unsigned long timeout;
|
||||
attribute boolean withCredentials;
|
||||
[SameObject] readonly attribute XMLHttpRequestUpload upload;
|
||||
undefined send(optional (Document or XMLHttpRequestBodyInit)? body = null);
|
||||
undefined abort();
|
||||
|
||||
// response
|
||||
readonly attribute USVString responseURL;
|
||||
readonly attribute unsigned short status;
|
||||
readonly attribute ByteString statusText;
|
||||
ByteString? getResponseHeader(ByteString name);
|
||||
ByteString getAllResponseHeaders();
|
||||
undefined overrideMimeType(DOMString mime);
|
||||
attribute XMLHttpRequestResponseType responseType;
|
||||
readonly attribute any response;
|
||||
readonly attribute DOMString responseText;
|
||||
readonly attribute Document? responseXML;
|
||||
|
||||
};
|
||||
27
Libraries/LibWeb/XHR/XMLHttpRequestEventTarget.cpp
Normal file
27
Libraries/LibWeb/XHR/XMLHttpRequestEventTarget.cpp
Normal file
|
|
@ -0,0 +1,27 @@
|
|||
/*
|
||||
* Copyright (c) 2021, Andreas Kling <andreas@ladybird.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#include <LibWeb/Bindings/XMLHttpRequestEventTargetPrototype.h>
|
||||
#include <LibWeb/HTML/EventHandler.h>
|
||||
#include <LibWeb/XHR/EventNames.h>
|
||||
#include <LibWeb/XHR/XMLHttpRequestEventTarget.h>
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
#undef __ENUMERATE
|
||||
#define __ENUMERATE(attribute_name, event_name) \
|
||||
void XMLHttpRequestEventTarget::set_##attribute_name(WebIDL::CallbackType* value) \
|
||||
{ \
|
||||
set_event_handler_attribute(event_name, value); \
|
||||
} \
|
||||
WebIDL::CallbackType* XMLHttpRequestEventTarget::attribute_name() \
|
||||
{ \
|
||||
return event_handler_attribute(event_name); \
|
||||
}
|
||||
ENUMERATE_XML_HTTP_REQUEST_EVENT_TARGET_EVENT_HANDLERS(__ENUMERATE)
|
||||
#undef __ENUMERATE
|
||||
|
||||
}
|
||||
43
Libraries/LibWeb/XHR/XMLHttpRequestEventTarget.h
Normal file
43
Libraries/LibWeb/XHR/XMLHttpRequestEventTarget.h
Normal file
|
|
@ -0,0 +1,43 @@
|
|||
/*
|
||||
* Copyright (c) 2021, the SerenityOS developers.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LibWeb/DOM/EventDispatcher.h>
|
||||
#include <LibWeb/DOM/EventTarget.h>
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
#define ENUMERATE_XML_HTTP_REQUEST_EVENT_TARGET_EVENT_HANDLERS(E) \
|
||||
E(onloadstart, XHR::EventNames::loadstart) \
|
||||
E(onprogress, XHR::EventNames::progress) \
|
||||
E(onabort, XHR::EventNames::abort) \
|
||||
E(onerror, XHR::EventNames::error) \
|
||||
E(onload, XHR::EventNames::load) \
|
||||
E(ontimeout, XHR::EventNames::timeout) \
|
||||
E(onloadend, XHR::EventNames::loadend)
|
||||
|
||||
class XMLHttpRequestEventTarget : public DOM::EventTarget {
|
||||
WEB_PLATFORM_OBJECT(XMLHttpRequestEventTarget, DOM::EventTarget);
|
||||
|
||||
public:
|
||||
virtual ~XMLHttpRequestEventTarget() override {};
|
||||
|
||||
#undef __ENUMERATE
|
||||
#define __ENUMERATE(attribute_name, event_name) \
|
||||
void set_##attribute_name(WebIDL::CallbackType*); \
|
||||
WebIDL::CallbackType* attribute_name();
|
||||
ENUMERATE_XML_HTTP_REQUEST_EVENT_TARGET_EVENT_HANDLERS(__ENUMERATE)
|
||||
#undef __ENUMERATE
|
||||
|
||||
protected:
|
||||
XMLHttpRequestEventTarget(JS::Realm& realm)
|
||||
: DOM::EventTarget(realm)
|
||||
{
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
17
Libraries/LibWeb/XHR/XMLHttpRequestEventTarget.idl
Normal file
17
Libraries/LibWeb/XHR/XMLHttpRequestEventTarget.idl
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
#import <DOM/EventTarget.idl>
|
||||
#import <DOM/EventHandler.idl>
|
||||
|
||||
// https://xhr.spec.whatwg.org/#xmlhttprequesteventtarget
|
||||
[Exposed=(Window,DedicatedWorker,SharedWorker)]
|
||||
interface XMLHttpRequestEventTarget : EventTarget {
|
||||
|
||||
// event handlers
|
||||
attribute EventHandler onloadstart;
|
||||
attribute EventHandler onprogress;
|
||||
attribute EventHandler onabort;
|
||||
attribute EventHandler onerror;
|
||||
attribute EventHandler onload;
|
||||
attribute EventHandler ontimeout;
|
||||
attribute EventHandler onloadend;
|
||||
|
||||
};
|
||||
28
Libraries/LibWeb/XHR/XMLHttpRequestUpload.cpp
Normal file
28
Libraries/LibWeb/XHR/XMLHttpRequestUpload.cpp
Normal file
|
|
@ -0,0 +1,28 @@
|
|||
/*
|
||||
* Copyright (c) 2023, Luke Wilde <lukew@serenityos.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#include <LibWeb/Bindings/Intrinsics.h>
|
||||
#include <LibWeb/Bindings/XMLHttpRequestUploadPrototype.h>
|
||||
#include <LibWeb/XHR/XMLHttpRequestUpload.h>
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
JS_DEFINE_ALLOCATOR(XMLHttpRequestUpload);
|
||||
|
||||
XMLHttpRequestUpload::XMLHttpRequestUpload(JS::Realm& realm)
|
||||
: XMLHttpRequestEventTarget(realm)
|
||||
{
|
||||
}
|
||||
|
||||
XMLHttpRequestUpload::~XMLHttpRequestUpload() = default;
|
||||
|
||||
void XMLHttpRequestUpload::initialize(JS::Realm& realm)
|
||||
{
|
||||
Base::initialize(realm);
|
||||
WEB_SET_PROTOTYPE_FOR_INTERFACE(XMLHttpRequestUpload);
|
||||
}
|
||||
|
||||
}
|
||||
26
Libraries/LibWeb/XHR/XMLHttpRequestUpload.h
Normal file
26
Libraries/LibWeb/XHR/XMLHttpRequestUpload.h
Normal file
|
|
@ -0,0 +1,26 @@
|
|||
/*
|
||||
* Copyright (c) 2023, Luke Wilde <lukew@serenityos.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <LibWeb/XHR/XMLHttpRequestEventTarget.h>
|
||||
|
||||
namespace Web::XHR {
|
||||
|
||||
class XMLHttpRequestUpload : public XMLHttpRequestEventTarget {
|
||||
WEB_PLATFORM_OBJECT(XMLHttpRequestUpload, XMLHttpRequestEventTarget);
|
||||
JS_DECLARE_ALLOCATOR(XMLHttpRequestUpload);
|
||||
|
||||
public:
|
||||
virtual ~XMLHttpRequestUpload() override;
|
||||
|
||||
private:
|
||||
XMLHttpRequestUpload(JS::Realm&);
|
||||
|
||||
virtual void initialize(JS::Realm&) override;
|
||||
};
|
||||
|
||||
}
|
||||
6
Libraries/LibWeb/XHR/XMLHttpRequestUpload.idl
Normal file
6
Libraries/LibWeb/XHR/XMLHttpRequestUpload.idl
Normal file
|
|
@ -0,0 +1,6 @@
|
|||
#import <XHR/XMLHttpRequestEventTarget.idl>
|
||||
|
||||
// https://xhr.spec.whatwg.org/#xmlhttprequestupload
|
||||
[Exposed=(Window,DedicatedWorker,SharedWorker)]
|
||||
interface XMLHttpRequestUpload : XMLHttpRequestEventTarget {
|
||||
};
|
||||
Loading…
Add table
Add a link
Reference in a new issue