From 474b748275d3900849b491f65ba7dfe7acbe7d5f Mon Sep 17 00:00:00 2001 From: stelar7 Date: Mon, 11 Aug 2025 22:30:18 +0200 Subject: [PATCH] LibWeb/IDB: Check the request error instead of the transaction --- Libraries/LibWeb/IndexedDB/IDBRequest.cpp | 8 +++++--- Libraries/LibWeb/IndexedDB/IDBRequest.h | 6 ++++-- Libraries/LibWeb/IndexedDB/Internal/Algorithms.cpp | 13 +++++-------- Libraries/LibWeb/IndexedDB/Internal/Algorithms.h | 2 +- 4 files changed, 15 insertions(+), 14 deletions(-) diff --git a/Libraries/LibWeb/IndexedDB/IDBRequest.cpp b/Libraries/LibWeb/IndexedDB/IDBRequest.cpp index 9923e0bcd52..b46e70e2453 100644 --- a/Libraries/LibWeb/IndexedDB/IDBRequest.cpp +++ b/Libraries/LibWeb/IndexedDB/IDBRequest.cpp @@ -39,9 +39,11 @@ GC::Ref IDBRequest::create(JS::Realm& realm, IDBRequestSource source void IDBRequest::visit_edges(Visitor& visitor) { Base::visit_edges(visitor); - visitor.visit(m_error); visitor.visit(m_result); visitor.visit(m_transaction); + + if (m_error.has_value()) + visitor.visit(*m_error); } // https://w3c.github.io/IndexedDB/#dom-idbrequest-onsuccess @@ -83,7 +85,7 @@ WebIDL::CallbackType* IDBRequest::onerror() return WebIDL::InvalidStateError::create(realm(), "The request is not done"_utf16); // 2. Otherwise, return this's error, or null if no error occurred. - return m_error; + return m_error.value_or(nullptr); } // https://w3c.github.io/IndexedDB/#dom-idbrequest-result @@ -94,7 +96,7 @@ WebIDL::CallbackType* IDBRequest::onerror() return WebIDL::InvalidStateError::create(realm(), "The request is not done"_utf16); // 2. Otherwise, return this's result, or undefined if the request resulted in an error. - if (m_error) + if (m_error.has_value()) return JS::js_undefined(); return m_result; diff --git a/Libraries/LibWeb/IndexedDB/IDBRequest.h b/Libraries/LibWeb/IndexedDB/IDBRequest.h index 5ba29ca15a9..ff1181b5bd0 100644 --- a/Libraries/LibWeb/IndexedDB/IDBRequest.h +++ b/Libraries/LibWeb/IndexedDB/IDBRequest.h @@ -38,11 +38,13 @@ public: void set_done(bool done) { m_done = done; } void set_result(JS::Value result) { m_result = result; } - void set_error(GC::Ptr error) { m_error = error; } + void set_error(Optional> error) { m_error = error; } void set_processed(bool processed) { m_processed = processed; } void set_source(IDBRequestSource source) { m_source = source; } void set_transaction(GC::Ptr transaction) { m_transaction = transaction; } + bool has_error() const { return m_error.has_value(); } + void set_onsuccess(WebIDL::CallbackType*); WebIDL::CallbackType* onsuccess(); void set_onerror(WebIDL::CallbackType*); @@ -63,7 +65,7 @@ private: // A request has a result and an error JS::Value m_result; - GC::Ptr m_error; + Optional> m_error; // A request has a source object. IDBRequestSource m_source; diff --git a/Libraries/LibWeb/IndexedDB/Internal/Algorithms.cpp b/Libraries/LibWeb/IndexedDB/Internal/Algorithms.cpp index abc5d4871fc..480f7e27c2d 100644 --- a/Libraries/LibWeb/IndexedDB/Internal/Algorithms.cpp +++ b/Libraries/LibWeb/IndexedDB/Internal/Algorithms.cpp @@ -164,16 +164,15 @@ WebIDL::ExceptionOr> open_a_database_connection(JS::Realm& })); // 6. Run upgrade a database using connection, version and request. - // AD-HOC: https://github.com/w3c/IndexedDB/issues/433#issuecomment-2512330086 - auto upgrade_transaction = upgrade_a_database(realm, connection, version, request); + upgrade_a_database(realm, connection, version, request); // 7. If connection was closed, return a newly created "AbortError" DOMException and abort these steps. if (connection->state() == IDBDatabase::ConnectionState::Closed) return WebIDL::AbortError::create(realm, "Connection was closed"_utf16); - // 8. If the upgrade transaction was aborted, run the steps to close a database connection with connection, + // 8. If request's error is set, run the steps to close a database connection with connection, // return a newly created "AbortError" DOMException and abort these steps. - if (upgrade_transaction->aborted()) { + if (request->has_error()) { close_a_database_connection(*connection); return WebIDL::AbortError::create(realm, "Upgrade transaction was aborted"_utf16); } @@ -360,7 +359,7 @@ void close_a_database_connection(GC::Ref connection, bool forced) } // https://w3c.github.io/IndexedDB/#upgrade-a-database -GC::Ref upgrade_a_database(JS::Realm& realm, GC::Ref connection, u64 version, GC::Ref request) +void upgrade_a_database(JS::Realm& realm, GC::Ref connection, u64 version, GC::Ref request) { // 1. Let db be connection’s database. auto db = connection->associated_database(); @@ -431,8 +430,6 @@ GC::Ref upgrade_a_database(JS::Realm& realm, GC::Refis_finished(); })); - - return transaction; } // https://w3c.github.io/IndexedDB/#deleting-a-database @@ -1209,7 +1206,7 @@ GC::Ref asynchronously_execute_a_request(JS::Realm& realm, IDBReques request->set_result(result.release_value()); // 2. Set request’s error to undefined. - request->set_error(nullptr); + request->set_error(Optional> {}); // 3. Fire a success event at request. fire_a_success_event(realm, request); diff --git a/Libraries/LibWeb/IndexedDB/Internal/Algorithms.h b/Libraries/LibWeb/IndexedDB/Internal/Algorithms.h index ce04060a78c..1d85ae9ebbb 100644 --- a/Libraries/LibWeb/IndexedDB/Internal/Algorithms.h +++ b/Libraries/LibWeb/IndexedDB/Internal/Algorithms.h @@ -24,7 +24,7 @@ WebIDL::ExceptionOr> open_a_database_connection(JS::Realm&, bool fire_a_version_change_event(JS::Realm&, FlyString const&, GC::Ref, u64, Optional); WebIDL::ExceptionOr> convert_a_value_to_a_key(JS::Realm&, JS::Value, Vector = {}); void close_a_database_connection(GC::Ref, bool forced = false); -GC::Ref upgrade_a_database(JS::Realm&, GC::Ref, u64, GC::Ref); +void upgrade_a_database(JS::Realm&, GC::Ref, u64, GC::Ref); WebIDL::ExceptionOr delete_a_database(JS::Realm&, StorageAPI::StorageKey, String, GC::Ref); void abort_a_transaction(GC::Ref, GC::Ptr); JS::Value convert_a_key_to_a_value(JS::Realm&, GC::Ref);