mirror of
https://github.com/LadybirdBrowser/ladybird.git
synced 2025-07-28 19:59:17 +00:00
LibWeb/WebSockets: Implement the garbage collection rules
This commit is contained in:
parent
b8f234719d
commit
3224f8acb5
Notes:
github-actions[bot]
2025-02-26 10:48:34 +00:00
Author: https://github.com/Lubrsi
Commit: 3224f8acb5
Pull-request: https://github.com/LadybirdBrowser/ladybird/pull/3694
2 changed files with 60 additions and 0 deletions
|
@ -112,6 +112,7 @@ WebIDL::ExceptionOr<GC::Ref<WebSocket>> WebSocket::construct_impl(JS::Realm& rea
|
||||||
WebSocket::WebSocket(JS::Realm& realm)
|
WebSocket::WebSocket(JS::Realm& realm)
|
||||||
: EventTarget(realm)
|
: EventTarget(realm)
|
||||||
{
|
{
|
||||||
|
set_overrides_must_survive_garbage_collection(true);
|
||||||
}
|
}
|
||||||
|
|
||||||
WebSocket::~WebSocket() = default;
|
WebSocket::~WebSocket() = default;
|
||||||
|
@ -122,6 +123,63 @@ void WebSocket::initialize(JS::Realm& realm)
|
||||||
WEB_SET_PROTOTYPE_FOR_INTERFACE(WebSocket);
|
WEB_SET_PROTOTYPE_FOR_INTERFACE(WebSocket);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// https://html.spec.whatwg.org/multipage/server-sent-events.html#garbage-collection
|
||||||
|
void WebSocket::finalize()
|
||||||
|
{
|
||||||
|
auto ready_state = this->ready_state();
|
||||||
|
|
||||||
|
// If a WebSocket object is garbage collected while its connection is still open, the user agent must start the
|
||||||
|
// WebSocket closing handshake, with no status code for the Close message. [WSP]
|
||||||
|
if (ready_state != Requests::WebSocket::ReadyState::Closing && ready_state != Requests::WebSocket::ReadyState::Closed) {
|
||||||
|
// FIXME: LibProtocol does not yet support sending empty Close messages, so we use default values for now
|
||||||
|
m_websocket->close(1000);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// https://html.spec.whatwg.org/multipage/server-sent-events.html#garbage-collection
|
||||||
|
bool WebSocket::must_survive_garbage_collection() const
|
||||||
|
{
|
||||||
|
auto ready_state = this->ready_state();
|
||||||
|
|
||||||
|
// FIXME: "as of the last time the event loop reached step 1"
|
||||||
|
|
||||||
|
// A WebSocket object whose ready state was set to CONNECTING (0) as of the last time the event loop reached step 1
|
||||||
|
// must not be garbage collected if there are any event listeners registered for open events, message events, error
|
||||||
|
// events, or close events.
|
||||||
|
if (ready_state == Requests::WebSocket::ReadyState::Connecting) {
|
||||||
|
if (has_event_listener(HTML::EventNames::open))
|
||||||
|
return true;
|
||||||
|
if (has_event_listener(HTML::EventNames::message))
|
||||||
|
return true;
|
||||||
|
if (has_event_listener(HTML::EventNames::error))
|
||||||
|
return true;
|
||||||
|
if (has_event_listener(HTML::EventNames::close))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// A WebSocket object whose ready state was set to OPEN (1) as of the last time the event loop reached step 1 must
|
||||||
|
// not be garbage collected if there are any event listeners registered for message events, error, or close events.
|
||||||
|
if (ready_state == Requests::WebSocket::ReadyState::Open) {
|
||||||
|
if (has_event_listener(HTML::EventNames::message))
|
||||||
|
return true;
|
||||||
|
if (has_event_listener(HTML::EventNames::error))
|
||||||
|
return true;
|
||||||
|
if (has_event_listener(HTML::EventNames::close))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
// A WebSocket object whose ready state was set to CLOSING (2) as of the last time the event loop reached step 1
|
||||||
|
// must not be garbage collected if there are any event listeners registered for error or close events.
|
||||||
|
if (ready_state == Requests::WebSocket::ReadyState::Closing) {
|
||||||
|
if (has_event_listener(HTML::EventNames::error))
|
||||||
|
return true;
|
||||||
|
if (has_event_listener(HTML::EventNames::close))
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
ErrorOr<void> WebSocket::establish_web_socket_connection(URL::URL const& url_record, Vector<String> const& protocols, HTML::EnvironmentSettingsObject& client)
|
ErrorOr<void> WebSocket::establish_web_socket_connection(URL::URL const& url_record, Vector<String> const& protocols, HTML::EnvironmentSettingsObject& client)
|
||||||
{
|
{
|
||||||
// FIXME: Integrate properly with FETCH as per https://fetch.spec.whatwg.org/#websocket-opening-handshake
|
// FIXME: Integrate properly with FETCH as per https://fetch.spec.whatwg.org/#websocket-opening-handshake
|
||||||
|
|
|
@ -64,6 +64,8 @@ private:
|
||||||
WebSocket(JS::Realm&);
|
WebSocket(JS::Realm&);
|
||||||
|
|
||||||
virtual void initialize(JS::Realm&) override;
|
virtual void initialize(JS::Realm&) override;
|
||||||
|
virtual void finalize() override;
|
||||||
|
virtual bool must_survive_garbage_collection() const override;
|
||||||
|
|
||||||
ErrorOr<void> establish_web_socket_connection(URL::URL const& url_record, Vector<String> const& protocols, HTML::EnvironmentSettingsObject& client);
|
ErrorOr<void> establish_web_socket_connection(URL::URL const& url_record, Vector<String> const& protocols, HTML::EnvironmentSettingsObject& client);
|
||||||
|
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue