LibWeb: Implement two module related host hooks

This patch adds support for the HostGetSupportedImportAssertions and
HostResolveImportedModule host hooks.

Co-authored-by: davidot <davidot@serenityos.org>
This commit is contained in:
networkException 2022-10-03 21:06:00 +02:00 committed by Andreas Kling
parent f0c4f8931c
commit c51cf66347
Notes: sideshowbarker 2024-07-17 06:18:10 +09:00

View file

@ -1,6 +1,7 @@
/*
* Copyright (c) 2021-2022, Andreas Kling <kling@serenityos.org>
* Copyright (c) 2021, Luke Wilde <lukew@serenityos.org>
* Copyright (c) 2022, networkException <networkexception@serenityos.org>
*
* SPDX-License-Identifier: BSD-2-Clause
*/
@ -20,6 +21,7 @@
#include <LibWeb/HTML/Scripting/ClassicScript.h>
#include <LibWeb/HTML/Scripting/Environments.h>
#include <LibWeb/HTML/Scripting/ExceptionReporter.h>
#include <LibWeb/HTML/Scripting/Fetching.h>
#include <LibWeb/HTML/Window.h>
#include <LibWeb/HTML/WindowProxy.h>
#include <LibWeb/Platform/EventLoopPlugin.h>
@ -306,10 +308,60 @@ JS::VM& main_thread_vm()
// FIXME: Implement 8.1.5.5.1 HostGetImportMetaProperties(moduleRecord), https://html.spec.whatwg.org/multipage/webappapis.html#hostgetimportmetaproperties
// FIXME: Implement 8.1.5.5.2 HostImportModuleDynamically(referencingScriptOrModule, moduleRequest, promiseCapability), https://html.spec.whatwg.org/multipage/webappapis.html#hostimportmoduledynamically(referencingscriptormodule,-modulerequest,-promisecapability)
// FIXME: Implement 8.1.5.5.3 HostResolveImportedModule(referencingScriptOrModule, moduleRequest), https://html.spec.whatwg.org/multipage/webappapis.html#hostresolveimportedmodule(referencingscriptormodule,-modulerequest)
// FIXME: Implement 8.1.5.5.4 HostGetSupportedImportAssertions(), https://html.spec.whatwg.org/multipage/webappapis.html#hostgetsupportedimportassertions
vm->host_resolve_imported_module = [](JS::ScriptOrModule, JS::ModuleRequest const&) -> JS::ThrowCompletionOr<JS::NonnullGCPtr<JS::Module>> {
return vm->throw_completion<JS::InternalError>(JS::ErrorType::NotImplemented, "Modules in the browser");
// 8.1.5.5.4 HostGetSupportedImportAssertions(), https://html.spec.whatwg.org/multipage/webappapis.html#hostgetsupportedimportassertions
vm->host_get_supported_import_assertions = []() -> Vector<String> {
// 1. Return « "type" ».
return { "type"sv };
};
// 8.1.5.5.3 HostResolveImportedModule(referencingScriptOrModule, moduleRequest), https://html.spec.whatwg.org/multipage/webappapis.html#hostresolveimportedmodule(referencingscriptormodule,-modulerequest)
vm->host_resolve_imported_module = [](JS::ScriptOrModule const& referencing_string_or_module, JS::ModuleRequest const& module_request) -> JS::ThrowCompletionOr<JS::NonnullGCPtr<JS::Module>> {
// 1. Let settings object be the current settings object.
auto* settings_object = &HTML::current_settings_object();
// 2. Let base URL be settings object's API base URL.
auto base_url = settings_object->api_base_url();
// 3. If referencingScriptOrModule is not null, then:
if (!referencing_string_or_module.has<Empty>()) {
// 1. Let referencing script be referencingScriptOrModule.[[HostDefined]].
auto const& referencing_script = verify_cast<HTML::Script>(referencing_string_or_module.has<JS::NonnullGCPtr<JS::Script>>() ? referencing_string_or_module.get<JS::NonnullGCPtr<JS::Script>>()->host_defined() : referencing_string_or_module.get<JS::NonnullGCPtr<JS::Module>>()->host_defined());
// 2. Set settings object to referencing script's settings object.
settings_object = &referencing_script->settings_object();
// 3. Set base URL to referencing script's base URL.
base_url = referencing_script->base_url();
// 4. Assert: base URL is not null, as referencing script is a classic script or a JavaScript module script.
VERIFY(base_url.is_valid());
}
// 4. Let moduleMap be settings object's module map.
auto& module_map = settings_object->module_map();
// 5. Let url be the result of resolving a module specifier given base URL and moduleRequest.[[Specifier]].
auto url = HTML::resolve_module_specifier(module_request, base_url);
// 6. Assert: url is never failure, because resolving a module specifier must have been previously successful
// with these same two arguments (either while creating the corresponding module script, or in fetch an import() module script graph).
VERIFY(url.is_valid());
// 7. Let moduleType be the result of running the module type from module request steps given moduleRequest.
auto module_type = HTML::module_type_from_module_request(module_request);
// 8. Let resolved module script be moduleMap[(url, moduleType)]. (This entry must exist for us to have gotten to this point.)
auto resolved_module = module_map.get(url, module_type).value();
// 9. Assert: resolved module script is a module script (i.e., is not null or "fetching").
VERIFY(resolved_module.type == HTML::ModuleMap::EntryType::ModuleScript);
// 10. Assert: resolved module script's record is not null.
VERIFY(resolved_module.module_script->record());
// 11. Return resolved module script's record.
return JS::NonnullGCPtr(*resolved_module.module_script->record());
};
// NOTE: We push a dummy execution context onto the JS execution context stack,