Skip to content

Rename Scope JsContext #770

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Jun 13, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/browser/dom/mutation_observer.zig
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ pub const MutationObserver = struct {
cbk: Env.Function,
arena: Allocator,

// List of records which were observed. When the scopeEnds, we need to
// List of records which were observed. When the call scope ends, we need to
// execute our callback with it.
observed: std.ArrayListUnmanaged(*MutationRecord),

Expand Down
24 changes: 12 additions & 12 deletions src/browser/page.zig
Original file line number Diff line number Diff line change
Expand Up @@ -85,7 +85,7 @@ pub const Page = struct {

// Our JavaScript context for this specific page. This is what we use to
// execute any JavaScript
scope: *Env.Scope,
main_context: *Env.JsContext,

// List of modules currently fetched/loaded.
module_map: std.StringHashMapUnmanaged([]const u8),
Expand Down Expand Up @@ -118,13 +118,13 @@ pub const Page = struct {
.request_factory = browser.http_client.requestFactory(.{
.notification = browser.notification,
}),
.scope = undefined,
.main_context = undefined,
.module_map = .empty,
};
self.scope = try session.executor.startScope(&self.window, self, self, true);
self.main_context = try session.executor.createJsContext(&self.window, self, self, true);

// load polyfills
try polyfill.load(self.arena, self.scope);
try polyfill.load(self.arena, self.main_context);

_ = try session.browser.app.loop.timeout(1 * std.time.ns_per_ms, &self.microtask_node);
}
Expand Down Expand Up @@ -166,7 +166,7 @@ pub const Page = struct {

pub fn wait(self: *Page) !void {
var try_catch: Env.TryCatch = undefined;
try_catch.init(self.scope);
try_catch.init(self.main_context);
defer try_catch.deinit();

try self.session.browser.app.loop.run();
Expand Down Expand Up @@ -798,7 +798,7 @@ pub const Page = struct {

pub fn stackTrace(self: *Page) !?[]const u8 {
if (comptime builtin.mode == .Debug) {
return self.scope.stackTrace();
return self.main_context.stackTrace();
}
return null;
}
Expand All @@ -818,7 +818,7 @@ const DelayedNavigation = struct {
//
// In the first phase, when self.initial == true, we'll shutdown the page
// and create a new one. The shutdown is important, because it resets the
// loop ctx_id and closes the scope. Closing the scope calls our XHR
// loop ctx_id and removes the JsContext. Removing the context calls our XHR
// destructors which aborts requests. This is necessary to make sure our
// [blocking] navigate won't block.
//
Expand Down Expand Up @@ -982,14 +982,14 @@ const Script = struct {

fn eval(self: *const Script, page: *Page, body: []const u8) !void {
var try_catch: Env.TryCatch = undefined;
try_catch.init(page.scope);
try_catch.init(page.main_context);
defer try_catch.deinit();

const src = self.src orelse "inline";
_ = switch (self.kind) {
.javascript => page.scope.exec(body, src),
.javascript => page.main_context.exec(body, src),
.module => blk: {
switch (try page.scope.module(body, src)) {
switch (try page.main_context.module(body, src)) {
.value => |v| break :blk v,
.exception => |e| {
log.warn(.user_script, "eval module", .{
Expand Down Expand Up @@ -1023,9 +1023,9 @@ const Script = struct {
switch (callback) {
.string => |str| {
var try_catch: Env.TryCatch = undefined;
try_catch.init(page.scope);
try_catch.init(page.main_context);
defer try_catch.deinit();
_ = page.scope.exec(str, typ) catch {
_ = page.main_context.exec(str, typ) catch {
if (try try_catch.err(page.arena)) |msg| {
log.warn(.user_script, "script callback", .{
.src = self.src,
Expand Down
2 changes: 1 addition & 1 deletion src/browser/polyfill/fetch.zig
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ test "Browser.fetch" {
var runner = try testing.jsRunner(testing.tracking_allocator, .{});
defer runner.deinit();

try @import("polyfill.zig").load(testing.allocator, runner.page.scope);
try @import("polyfill.zig").load(testing.allocator, runner.page.main_context);

try runner.testCases(&.{
.{
Expand Down
6 changes: 3 additions & 3 deletions src/browser/polyfill/polyfill.zig
Original file line number Diff line number Diff line change
Expand Up @@ -30,13 +30,13 @@ const modules = [_]struct {
.{ .name = "polyfill-fetch", .source = @import("fetch.zig").source },
};

pub fn load(allocator: Allocator, scope: *Env.Scope) !void {
pub fn load(allocator: Allocator, js_context: *Env.JsContext) !void {
var try_catch: Env.TryCatch = undefined;
try_catch.init(scope);
try_catch.init(js_context);
defer try_catch.deinit();

for (modules) |m| {
_ = scope.exec(m.source, m.name) catch |err| {
_ = js_context.exec(m.source, m.name) catch |err| {
if (try try_catch.err(allocator)) |msg| {
defer allocator.free(msg);
log.fatal(.app, "polyfill error", .{ .name = m.name, .err = msg });
Expand Down
4 changes: 2 additions & 2 deletions src/browser/session.zig
Original file line number Diff line number Diff line change
Expand Up @@ -116,11 +116,11 @@ pub const Session = struct {
// phase. It's important that we clean these up, as they're holding onto
// limited resources (like our fixed-sized http state pool).
//
// First thing we do, is endScope() which will execute the destructor
// First thing we do, is removeJsContext() which will execute the destructor
// of any type that registered a destructor (e.g. XMLHttpRequest).
// This will shutdown any pending sockets, which begins our cleaning
// processed
self.executor.endScope();
self.executor.removeJsContext();

// Second thing we do is reset the loop. This increments the loop ctx_id
// so that any "stale" timeouts we process will get ignored. We need to
Expand Down
8 changes: 4 additions & 4 deletions src/cdp/cdp.zig
Original file line number Diff line number Diff line change
Expand Up @@ -555,8 +555,8 @@ const IsolatedWorld = struct {
self.executor.deinit();
}
pub fn removeContext(self: *IsolatedWorld) !void {
if (self.executor.scope == null) return error.NoIsolatedContextToRemove;
self.executor.endScope();
if (self.executor.js_context == null) return error.NoIsolatedContextToRemove;
self.executor.removeJsContext();
}

// The isolate world must share at least some of the state with the related page, specifically the DocumentHTML
Expand All @@ -565,8 +565,8 @@ const IsolatedWorld = struct {
// This also means this pointer becomes invalid after removePage untill a new page is created.
// Currently we have only 1 page/frame and thus also only 1 state in the isolate world.
pub fn createContext(self: *IsolatedWorld, page: *Page) !void {
if (self.executor.scope != null) return error.Only1IsolatedContextSupported;
_ = try self.executor.startScope(&page.window, page, {}, false);
if (self.executor.js_context != null) return error.Only1IsolatedContextSupported;
_ = try self.executor.createJsContext(&page.window, page, {}, false);
}
};

Expand Down
10 changes: 5 additions & 5 deletions src/cdp/domains/dom.zig
Original file line number Diff line number Diff line change
Expand Up @@ -259,13 +259,13 @@ fn resolveNode(cmd: anytype) !void {
const bc = cmd.browser_context orelse return error.BrowserContextNotLoaded;
const page = bc.session.currentPage() orelse return error.PageNotLoaded;

var scope = page.scope;
var js_context = page.main_context;
if (params.executionContextId) |context_id| {
if (scope.context.debugContextId() != context_id) {
if (js_context.v8_context.debugContextId() != context_id) {
var isolated_world = bc.isolated_world orelse return error.ContextNotFound;
scope = &(isolated_world.executor.scope orelse return error.ContextNotFound);
js_context = &(isolated_world.executor.js_context orelse return error.ContextNotFound);

if (scope.context.debugContextId() != context_id) return error.ContextNotFound;
if (js_context.v8_context.debugContextId() != context_id) return error.ContextNotFound;
}
}

Expand All @@ -275,7 +275,7 @@ fn resolveNode(cmd: anytype) !void {
// node._node is a *parser.Node we need this to be able to find its most derived type e.g. Node -> Element -> HTMLElement
// So we use the Node.Union when retrieve the value from the environment
const remote_object = try bc.inspector.getRemoteObject(
scope,
js_context,
params.objectGroup orelse "",
try dom_node.Node.toInterface(node._node),
);
Expand Down
12 changes: 6 additions & 6 deletions src/cdp/domains/page.zig
Original file line number Diff line number Diff line change
Expand Up @@ -117,14 +117,14 @@ fn createIsolatedWorld(cmd: anytype) !void {
const world = try bc.createIsolatedWorld(params.worldName, params.grantUniveralAccess);
const page = bc.session.currentPage() orelse return error.PageNotLoaded;
try pageCreated(bc, page);
const scope = &world.executor.scope.?;
const js_context = &world.executor.js_context.?;

// Create the auxdata json for the contextCreated event
// Calling contextCreated will assign a Id to the context and send the contextCreated event
const aux_data = try std.fmt.allocPrint(cmd.arena, "{{\"isDefault\":false,\"type\":\"isolated\",\"frameId\":\"{s}\"}}", .{params.frameId});
bc.inspector.contextCreated(scope, world.name, "", aux_data, false);
bc.inspector.contextCreated(js_context, world.name, "", aux_data, false);

return cmd.sendResult(.{ .executionContextId = scope.context.debugContextId() }, .{});
return cmd.sendResult(.{ .executionContextId = js_context.v8_context.debugContextId() }, .{});
}

fn navigate(cmd: anytype) !void {
Expand Down Expand Up @@ -253,7 +253,7 @@ pub fn pageNavigate(arena: Allocator, bc: anytype, event: *const Notification.Pa
const page = bc.session.currentPage() orelse return error.PageNotLoaded;
const aux_data = try std.fmt.allocPrint(arena, "{{\"isDefault\":true,\"type\":\"default\",\"frameId\":\"{s}\"}}", .{target_id});
bc.inspector.contextCreated(
page.scope,
page.main_context,
"",
try page.origin(arena),
aux_data,
Expand All @@ -264,7 +264,7 @@ pub fn pageNavigate(arena: Allocator, bc: anytype, event: *const Notification.Pa
const aux_json = try std.fmt.allocPrint(arena, "{{\"isDefault\":false,\"type\":\"isolated\",\"frameId\":\"{s}\"}}", .{target_id});
// Calling contextCreated will assign a new Id to the context and send the contextCreated event
bc.inspector.contextCreated(
&isolated_world.executor.scope.?,
&isolated_world.executor.js_context.?,
isolated_world.name,
"://",
aux_json,
Expand All @@ -286,7 +286,7 @@ pub fn pageCreated(bc: anytype, page: *Page) !void {
try isolated_world.createContext(page);

const polyfill = @import("../../browser/polyfill/polyfill.zig");
try polyfill.load(bc.arena, &isolated_world.executor.scope.?);
try polyfill.load(bc.arena, &isolated_world.executor.js_context.?);
}
}

Expand Down
2 changes: 1 addition & 1 deletion src/cdp/domains/target.zig
Original file line number Diff line number Diff line change
Expand Up @@ -127,7 +127,7 @@ fn createTarget(cmd: anytype) !void {
{
const aux_data = try std.fmt.allocPrint(cmd.arena, "{{\"isDefault\":true,\"type\":\"default\",\"frameId\":\"{s}\"}}", .{target_id});
bc.inspector.contextCreated(
page.scope,
page.main_context,
"",
try page.origin(cmd.arena),
aux_data,
Expand Down
4 changes: 2 additions & 2 deletions src/main_wpt.zig
Original file line number Diff line number Diff line change
Expand Up @@ -113,7 +113,7 @@ fn run(arena: Allocator, test_file: []const u8, loader: *FileLoader, err_out: *?
});
defer runner.deinit();

try polyfill.load(arena, runner.page.scope);
try polyfill.load(arena, runner.page.main_context);

// loop over the scripts.
const doc = parser.documentHTMLToDocument(runner.page.window.document);
Expand Down Expand Up @@ -155,7 +155,7 @@ fn run(arena: Allocator, test_file: []const u8, loader: *FileLoader, err_out: *?
{
// wait for all async executions
var try_catch: Env.TryCatch = undefined;
try_catch.init(runner.page.scope);
try_catch.init(runner.page.main_context);
defer try_catch.deinit();
try runner.page.loop.run();

Expand Down
Loading