LibWeb: Allow creating a MessagePort with a different primary interface

This is needed to transfer streams, which use message ports as the means
of transport.
This commit is contained in:
Timothy Flynn 2025-04-18 16:22:31 -04:00 committed by Tim Flynn
commit ee9d860ba2
Notes: github-actions[bot] 2025-05-21 10:56:14 +00:00
2 changed files with 11 additions and 7 deletions

View file

@ -37,13 +37,14 @@ static HashTable<GC::RawPtr<MessagePort>>& all_message_ports()
return ports;
}
GC::Ref<MessagePort> MessagePort::create(JS::Realm& realm)
GC::Ref<MessagePort> MessagePort::create(JS::Realm& realm, HTML::TransferType primary_interface)
{
return realm.create<MessagePort>(realm);
return realm.create<MessagePort>(realm, primary_interface);
}
MessagePort::MessagePort(JS::Realm& realm)
MessagePort::MessagePort(JS::Realm& realm, HTML::TransferType primary_interface)
: DOM::EventTarget(realm)
, m_primary_interface(primary_interface)
{
all_message_ports().set(this);
}

View file

@ -20,13 +20,14 @@
namespace Web::HTML {
// https://html.spec.whatwg.org/multipage/web-messaging.html#message-ports
class MessagePort final : public DOM::EventTarget
class MessagePort final
: public DOM::EventTarget
, public Bindings::Transferable {
WEB_PLATFORM_OBJECT(MessagePort, DOM::EventTarget);
GC_DECLARE_ALLOCATOR(MessagePort);
public:
[[nodiscard]] static GC::Ref<MessagePort> create(JS::Realm&);
[[nodiscard]] static GC::Ref<MessagePort> create(JS::Realm&, HTML::TransferType primary_interface = HTML::TransferType::MessagePort);
static void for_each_message_port(Function<void(MessagePort&)>);
@ -59,14 +60,14 @@ public:
// ^Transferable
virtual WebIDL::ExceptionOr<void> transfer_steps(HTML::TransferDataHolder&) override;
virtual WebIDL::ExceptionOr<void> transfer_receiving_steps(HTML::TransferDataHolder&) override;
virtual HTML::TransferType primary_interface() const override { return HTML::TransferType::MessagePort; }
virtual HTML::TransferType primary_interface() const override { return m_primary_interface; }
void set_worker_event_target(GC::Ref<DOM::EventTarget>);
WebIDL::ExceptionOr<void> message_port_post_message_steps(GC::Ptr<MessagePort> target_port, JS::Value message, StructuredSerializeOptions const& options);
private:
explicit MessagePort(JS::Realm&);
explicit MessagePort(JS::Realm&, HTML::TransferType primary_interface);
virtual void initialize(JS::Realm&) override;
virtual void finalize() override;
@ -79,6 +80,8 @@ private:
ErrorOr<void> send_message_on_transport(SerializedTransferRecord const&);
void read_from_transport();
HTML::TransferType m_primary_interface { HTML::TransferType::MessagePort };
// The HTML spec implies(!) that this is MessagePort.[[RemotePort]]
GC::Ptr<MessagePort> m_remote_port;