diff --git a/Userland/Libraries/LibWeb/FileAPI/Blob.h b/Userland/Libraries/LibWeb/FileAPI/Blob.h index 42984e7676..642ad2fa02 100644 --- a/Userland/Libraries/LibWeb/FileAPI/Blob.h +++ b/Userland/Libraries/LibWeb/FileAPI/Blob.h @@ -66,11 +66,11 @@ protected: virtual void initialize(JS::Realm&) override; -private: - explicit Blob(JS::Realm&); - ByteBuffer m_byte_buffer {}; String m_type {}; + +private: + explicit Blob(JS::Realm&); }; } diff --git a/Userland/Libraries/LibWeb/FileAPI/File.cpp b/Userland/Libraries/LibWeb/FileAPI/File.cpp index 47c99cc628..c468dbb44d 100644 --- a/Userland/Libraries/LibWeb/FileAPI/File.cpp +++ b/Userland/Libraries/LibWeb/FileAPI/File.cpp @@ -1,5 +1,5 @@ /* - * Copyright (c) 2022-2023, Kenneth Myhra + * Copyright (c) 2022-2024, Kenneth Myhra * * SPDX-License-Identifier: BSD-2-Clause */ @@ -21,6 +21,11 @@ File::File(JS::Realm& realm, ByteBuffer byte_buffer, String file_name, String ty { } +File::File(JS::Realm& realm) + : Blob(realm, {}) +{ +} + void File::initialize(JS::Realm& realm) { Base::initialize(realm); @@ -29,6 +34,11 @@ void File::initialize(JS::Realm& realm) File::~File() = default; +JS::NonnullGCPtr File::create(JS::Realm& realm) +{ + return realm.heap().allocate(realm, realm); +} + // https://w3c.github.io/FileAPI/#ref-for-dom-file-file WebIDL::ExceptionOr> File::create(JS::Realm& realm, Vector const& file_bits, String const& file_name, Optional const& options) { @@ -77,4 +87,53 @@ WebIDL::ExceptionOr> File::construct_impl(JS::Realm& real return create(realm, file_bits, file_name, options); } +WebIDL::ExceptionOr File::serialization_steps(HTML::SerializationRecord& record, bool) +{ + auto& vm = this->vm(); + + TRY(HTML::serialize_string(vm, record, interface_name())); + + // FIXME: 1. Set serialized.[[SnapshotState]] to value’s snapshot state. + + // NON-STANDARD: FileAPI spec doesn't specify that type should be serialized, although + // to be conformant with other browsers this needs to be serialized. + TRY(HTML::serialize_string(vm, record, m_type)); + + // 2. Set serialized.[[ByteSequence]] to value’s underlying byte sequence. + TRY(HTML::serialize_bytes(vm, record, m_byte_buffer.bytes())); + + // 3. Set serialized.[[Name]] to the value of value’s name attribute. + TRY(HTML::serialize_string(vm, record, m_name)); + + // 4. Set serialized.[[LastModified]] to the value of value’s lastModified attribute. + record.append(bit_cast(&m_last_modified), 2); + + return {}; +} + +WebIDL::ExceptionOr File::deserialization_steps(ReadonlySpan const& record, size_t& position) +{ + auto& vm = this->vm(); + + // FIXME: 1. Set value’s snapshot state to serialized.[[SnapshotState]]. + + // NON-STANDARD: FileAPI spec doesn't specify that type should be deserialized, although + // to be conformant with other browsers this needs to be deserialized. + m_type = TRY(HTML::deserialize_string(vm, record, position)); + + // 2. Set value’s underlying byte sequence to serialized.[[ByteSequence]]. + m_byte_buffer = TRY(HTML::deserialize_bytes(vm, record, position)); + + // 3. Initialize the value of value’s name attribute to serialized.[[Name]]. + m_name = TRY(HTML::deserialize_string(vm, record, position)); + + // 4. Initialize the value of value’s lastModified attribute to serialized.[[LastModified]]. + u32 bits[2] = {}; + bits[0] = record[position++]; + bits[1] = record[position++]; + m_last_modified = *bit_cast(&bits); + + return {}; +} + } diff --git a/Userland/Libraries/LibWeb/FileAPI/File.h b/Userland/Libraries/LibWeb/FileAPI/File.h index 3cfc9f88fc..100a8eca76 100644 --- a/Userland/Libraries/LibWeb/FileAPI/File.h +++ b/Userland/Libraries/LibWeb/FileAPI/File.h @@ -1,5 +1,5 @@ /* - * Copyright (c) 2022-2023, Kenneth Myhra + * Copyright (c) 2022-2024, Kenneth Myhra * * SPDX-License-Identifier: BSD-2-Clause */ @@ -19,6 +19,7 @@ class File : public Blob { JS_DECLARE_ALLOCATOR(File); public: + static JS::NonnullGCPtr create(JS::Realm& realm); static WebIDL::ExceptionOr> create(JS::Realm&, Vector const& file_bits, String const& file_name, Optional const& options = {}); static WebIDL::ExceptionOr> construct_impl(JS::Realm&, Vector const& file_bits, String const& file_name, Optional const& options = {}); @@ -29,8 +30,14 @@ public: // https://w3c.github.io/FileAPI/#dfn-lastModified i64 last_modified() const { return m_last_modified; } + virtual StringView interface_name() const override { return "File"sv; } + + virtual WebIDL::ExceptionOr serialization_steps(HTML::SerializationRecord& record, bool for_storage) override; + virtual WebIDL::ExceptionOr deserialization_steps(ReadonlySpan const&, size_t& position) override; + private: File(JS::Realm&, ByteBuffer, String file_name, String type, i64 last_modified); + explicit File(JS::Realm&); virtual void initialize(JS::Realm&) override; diff --git a/Userland/Libraries/LibWeb/HTML/StructuredSerialize.cpp b/Userland/Libraries/LibWeb/HTML/StructuredSerialize.cpp index 022d98f441..ca26f943b2 100644 --- a/Userland/Libraries/LibWeb/HTML/StructuredSerialize.cpp +++ b/Userland/Libraries/LibWeb/HTML/StructuredSerialize.cpp @@ -34,6 +34,7 @@ #include #include #include +#include #include #include #include @@ -927,6 +928,8 @@ private: { if (interface_name == "Blob"sv) return FileAPI::Blob::create(realm); + if (interface_name == "File"sv) + return FileAPI::File::create(realm); VERIFY_NOT_REACHED(); }