aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGravatar Jarred Sumner <jarred@jarredsumner.com> 2021-06-26 23:12:57 -0700
committerGravatar Jarred Sumner <jarred@jarredsumner.com> 2021-06-26 23:12:57 -0700
commit506d9b81a7c9dac5dd870f6735c39df105e72fd4 (patch)
tree4dc6e2f51867acf1cf5d601aa5444a99a9f95142
parent3a95a74b7feadb59a215ff06446ccebff4a4008e (diff)
downloadbun-506d9b81a7c9dac5dd870f6735c39df105e72fd4.tar.gz
bun-506d9b81a7c9dac5dd870f6735c39df105e72fd4.tar.zst
bun-506d9b81a7c9dac5dd870f6735c39df105e72fd4.zip
wip
-rw-r--r--.vscode/launch.json14
-rw-r--r--build.zig17
-rw-r--r--src/api/schema.d.ts7
-rw-r--r--src/api/schema.js8
-rw-r--r--src/api/schema.peechy1
-rw-r--r--src/api/schema.zig2288
-rw-r--r--src/bundler.zig17
-rw-r--r--src/cli.zig2
-rw-r--r--src/hash_map.zig13
-rw-r--r--src/javascript/jsc/JavascriptCore.zig122
-rw-r--r--src/javascript/jsc/javascript.zig1264
-rw-r--r--src/main_javascript.zig374
-rw-r--r--src/options.zig20
-rw-r--r--src/string_immutable.zig7
-rw-r--r--src/wtf_string_mutable.zig14
15 files changed, 2803 insertions, 1365 deletions
diff --git a/.vscode/launch.json b/.vscode/launch.json
index 8ed5db09e..3f9b8d7be 100644
--- a/.vscode/launch.json
+++ b/.vscode/launch.json
@@ -11,6 +11,20 @@
// "cwd": "${workspaceFolder}",
// "console": "internalConsole"
// },
+ {
+ "type": "lldb",
+ "request": "launch",
+ "name": "Eval",
+ "program": "${workspaceFolder}/build/debug/macos-x86_64/spjs",
+ "args": [
+ "./simple.css",
+ "--resolve=dev",
+ "--outdir=outcss",
+ "--public-url=https://localhost:9000/"
+ ],
+ "cwd": "${workspaceFolder}/src/test/fixtures",
+ "console": "internalConsole"
+ },
{
"type": "lldb",
diff --git a/build.zig b/build.zig
index 9814ad4fd..0fddb9297 100644
--- a/build.zig
+++ b/build.zig
@@ -27,7 +27,6 @@ pub fn build(b: *std.build.Builder) void {
var cwd_buf = [_]u8{0} ** 4096;
var cwd = std.os.getcwd(&cwd_buf) catch unreachable;
var exe: *std.build.LibExeObjStep = undefined;
- var javascript: *std.build.LibExeObjStep = undefined;
var output_dir_buf = std.mem.zeroes([4096]u8);
var bin_label = if (mode == std.builtin.Mode.Debug) "/debug/" else "/";
@@ -90,7 +89,7 @@ pub fn build(b: *std.build.Builder) void {
}
// exe.setLibCFile("libc.txt");
exe.linkLibC();
-
+ exe.linkLibCpp();
exe.addPackage(.{
.name = "clap",
.path = .{ .path = "src/deps/zig-clap/clap.zig" },
@@ -130,6 +129,20 @@ pub fn build(b: *std.build.Builder) void {
// exe.addSystemIncludeDir(sys);
// }
addPicoHTTP(exe, cwd);
+ var javascript = b.addExecutable("spjs", "src/main_javascript.zig");
+ javascript.packages = exe.packages;
+ javascript.setOutputDir(output_dir);
+ javascript.setBuildMode(mode);
+ javascript.linkLibC();
+ javascript.linkLibCpp();
+
+ if (target.getOsTag() == .macos) {
+ javascript.linkFramework("JavaScriptCore");
+ exe.linkFramework("JavascriptCore");
+ }
+
+ javascript.strip = false;
+ javascript.install();
}
exe.install();
diff --git a/src/api/schema.d.ts b/src/api/schema.d.ts
index a15f7b878..a78156e10 100644
--- a/src/api/schema.d.ts
+++ b/src/api/schema.d.ts
@@ -55,13 +55,16 @@ type uint32 = number;
}
export enum Platform {
browser = 1,
- node = 2
+ node = 2,
+ speedy = 3
}
export const PlatformKeys = {
1: "browser",
browser: "browser",
2: "node",
- node: "node"
+ node: "node",
+ 3: "speedy",
+ speedy: "speedy"
}
export enum JSXRuntime {
automatic = 1,
diff --git a/src/api/schema.js b/src/api/schema.js
index c4341c1d4..e48d857a6 100644
--- a/src/api/schema.js
+++ b/src/api/schema.js
@@ -53,14 +53,18 @@ const ResolveModeKeys = {
const Platform = {
"1": 1,
"2": 2,
+ "3": 3,
"browser": 1,
- "node": 2
+ "node": 2,
+ "speedy": 3
};
const PlatformKeys = {
"1": "browser",
"2": "node",
+ "3": "speedy",
"browser": "browser",
- "node": "node"
+ "node": "node",
+ "speedy": "speedy"
};
const JSXRuntime = {
"1": 1,
diff --git a/src/api/schema.peechy b/src/api/schema.peechy
index 74050e90f..1da6c8c67 100644
--- a/src/api/schema.peechy
+++ b/src/api/schema.peechy
@@ -20,6 +20,7 @@ smol ResolveMode {
smol Platform {
browser = 1;
node = 2;
+ speedy = 3;
}
smol JSXRuntime {
diff --git a/src/api/schema.zig b/src/api/schema.zig
index 8227f5e88..0805ddfc1 100644
--- a/src/api/schema.zig
+++ b/src/api/schema.zig
@@ -1,3 +1,4 @@
+
const std = @import("std");
pub const Reader = struct {
@@ -281,1386 +282,1487 @@ pub fn Writer(comptime WritableStream: type) type {
pub const ByteWriter = Writer(*std.io.FixedBufferStream([]u8));
pub const FileWriter = Writer(std.fs.File);
-pub const Api = struct {
- pub const Loader = enum(u8) {
- _none,
- /// jsx
- jsx,
- /// js
- js,
- /// ts
- ts,
- /// tsx
- tsx,
+pub const Api = struct {
- /// css
- css,
+pub const Loader = enum(u8) {
- /// file
- file,
+_none,
+ /// jsx
+ jsx,
- /// json
- json,
+ /// js
+ js,
- _,
+ /// ts
+ ts,
- pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
- return try std.json.stringify(@tagName(self), opts, o);
- }
- };
+ /// tsx
+ tsx,
- pub const ResolveMode = enum(u8) {
- _none,
- /// disable
- disable,
+ /// css
+ css,
- /// lazy
- lazy,
+ /// file
+ file,
- /// dev
- dev,
+ /// json
+ json,
- /// bundle
- bundle,
+_,
- _,
+ pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
+ return try std.json.stringify(@tagName(self), opts, o);
+ }
- pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
- return try std.json.stringify(@tagName(self), opts, o);
- }
- };
+
+};
- pub const Platform = enum(u8) {
- _none,
- /// browser
- browser,
+pub const ResolveMode = enum(u8) {
- /// node
- node,
+_none,
+ /// disable
+ disable,
- _,
+ /// lazy
+ lazy,
- pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
- return try std.json.stringify(@tagName(self), opts, o);
- }
- };
+ /// dev
+ dev,
- pub const JsxRuntime = enum(u8) {
- _none,
- /// automatic
- automatic,
+ /// bundle
+ bundle,
- /// classic
- classic,
+_,
- _,
+ pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
+ return try std.json.stringify(@tagName(self), opts, o);
+ }
- pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
- return try std.json.stringify(@tagName(self), opts, o);
- }
- };
+
+};
- pub const Jsx = struct {
- /// factory
- factory: []const u8,
+pub const Platform = enum(u8) {
- /// runtime
- runtime: JsxRuntime,
+_none,
+ /// browser
+ browser,
- /// fragment
- fragment: []const u8,
+ /// node
+ node,
- /// development
- development: bool = false,
+ /// speedy
+ speedy,
- /// import_source
- import_source: []const u8,
+_,
- /// react_fast_refresh
- react_fast_refresh: bool = false,
+ pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
+ return try std.json.stringify(@tagName(self), opts, o);
+ }
- pub fn decode(reader: anytype) anyerror!Jsx {
- var this = std.mem.zeroes(Jsx);
+
+};
- this.factory = try reader.readValue([]const u8);
- this.runtime = try reader.readValue(JsxRuntime);
- this.fragment = try reader.readValue([]const u8);
- this.development = try reader.readValue(bool);
- this.import_source = try reader.readValue([]const u8);
- this.react_fast_refresh = try reader.readValue(bool);
- return this;
- }
+pub const JsxRuntime = enum(u8) {
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeValue(this.factory);
- try writer.writeEnum(this.runtime);
- try writer.writeValue(this.fragment);
- try writer.writeInt(@intCast(u8, @boolToInt(this.development)));
- try writer.writeValue(this.import_source);
- try writer.writeInt(@intCast(u8, @boolToInt(this.react_fast_refresh)));
- }
- };
+_none,
+ /// automatic
+ automatic,
- pub const StringPointer = packed struct {
- /// offset
- offset: u32 = 0,
+ /// classic
+ classic,
- /// length
- length: u32 = 0,
+_,
- pub fn decode(reader: anytype) anyerror!StringPointer {
- var this = std.mem.zeroes(StringPointer);
+ pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
+ return try std.json.stringify(@tagName(self), opts, o);
+ }
- this.offset = try reader.readValue(u32);
- this.length = try reader.readValue(u32);
- return this;
- }
+
+};
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeInt(this.offset);
- try writer.writeInt(this.length);
- }
- };
+pub const Jsx = struct {
+/// factory
+factory: []const u8,
- pub const JavascriptBundledModule = struct {
- /// path
- path: StringPointer,
+/// runtime
+runtime: JsxRuntime,
- /// code
- code: StringPointer,
+/// fragment
+fragment: []const u8,
- /// package_id
- package_id: u32 = 0,
+/// development
+development: bool = false,
- /// id
- id: u32 = 0,
+/// import_source
+import_source: []const u8,
- /// path_extname_length
- path_extname_length: u8 = 0,
+/// react_fast_refresh
+react_fast_refresh: bool = false,
- pub fn decode(reader: anytype) anyerror!JavascriptBundledModule {
- var this = std.mem.zeroes(JavascriptBundledModule);
- this.path = try reader.readValue(StringPointer);
- this.code = try reader.readValue(StringPointer);
- this.package_id = try reader.readValue(u32);
- this.id = try reader.readValue(u32);
- this.path_extname_length = try reader.readValue(u8);
- return this;
- }
+pub fn decode(reader: anytype) anyerror!Jsx {
+ var this = std.mem.zeroes(Jsx);
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeValue(this.path);
- try writer.writeValue(this.code);
- try writer.writeInt(this.package_id);
- try writer.writeInt(this.id);
- try writer.writeInt(this.path_extname_length);
- }
- };
+ this.factory = try reader.readValue([]const u8);
+ this.runtime = try reader.readValue(JsxRuntime);
+ this.fragment = try reader.readValue([]const u8);
+ this.development = try reader.readValue(bool);
+ this.import_source = try reader.readValue([]const u8);
+ this.react_fast_refresh = try reader.readValue(bool);
+ return this;
+}
- pub const JavascriptBundledPackage = struct {
- /// name
- name: StringPointer,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeValue(this.factory);
+ try writer.writeEnum(this.runtime);
+ try writer.writeValue(this.fragment);
+ try writer.writeInt(@intCast(u8, @boolToInt(this.development)));
+ try writer.writeValue(this.import_source);
+ try writer.writeInt(@intCast(u8, @boolToInt(this.react_fast_refresh)));
+}
- /// version
- version: StringPointer,
+};
- /// hash
- hash: u32 = 0,
+pub const StringPointer = packed struct {
+/// offset
+offset: u32 = 0,
- /// modules_offset
- modules_offset: u32 = 0,
+/// length
+length: u32 = 0,
- /// modules_length
- modules_length: u32 = 0,
- pub fn decode(reader: anytype) anyerror!JavascriptBundledPackage {
- var this = std.mem.zeroes(JavascriptBundledPackage);
+pub fn decode(reader: anytype) anyerror!StringPointer {
+ var this = std.mem.zeroes(StringPointer);
- this.name = try reader.readValue(StringPointer);
- this.version = try reader.readValue(StringPointer);
- this.hash = try reader.readValue(u32);
- this.modules_offset = try reader.readValue(u32);
- this.modules_length = try reader.readValue(u32);
- return this;
- }
+ this.offset = try reader.readValue(u32);
+ this.length = try reader.readValue(u32);
+ return this;
+}
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeValue(this.name);
- try writer.writeValue(this.version);
- try writer.writeInt(this.hash);
- try writer.writeInt(this.modules_offset);
- try writer.writeInt(this.modules_length);
- }
- };
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeInt(this.offset);
+ try writer.writeInt(this.length);
+}
- pub const JavascriptBundle = struct {
- /// modules
- modules: []const JavascriptBundledModule,
+};
- /// packages
- packages: []const JavascriptBundledPackage,
+pub const JavascriptBundledModule = struct {
+/// path
+path: StringPointer,
- /// etag
- etag: []const u8,
+/// code
+code: StringPointer,
- /// generated_at
- generated_at: u32 = 0,
+/// package_id
+package_id: u32 = 0,
- /// app_package_json_dependencies_hash
- app_package_json_dependencies_hash: []const u8,
+/// id
+id: u32 = 0,
- /// import_from_name
- import_from_name: []const u8,
+/// path_extname_length
+path_extname_length: u8 = 0,
- /// manifest_string
- manifest_string: []const u8,
- pub fn decode(reader: anytype) anyerror!JavascriptBundle {
- var this = std.mem.zeroes(JavascriptBundle);
+pub fn decode(reader: anytype) anyerror!JavascriptBundledModule {
+ var this = std.mem.zeroes(JavascriptBundledModule);
- this.modules = try reader.readArray(JavascriptBundledModule);
- this.packages = try reader.readArray(JavascriptBundledPackage);
- this.etag = try reader.readArray(u8);
- this.generated_at = try reader.readValue(u32);
- this.app_package_json_dependencies_hash = try reader.readArray(u8);
- this.import_from_name = try reader.readArray(u8);
- this.manifest_string = try reader.readArray(u8);
- return this;
- }
+ this.path = try reader.readValue(StringPointer);
+ this.code = try reader.readValue(StringPointer);
+ this.package_id = try reader.readValue(u32);
+ this.id = try reader.readValue(u32);
+ this.path_extname_length = try reader.readValue(u8);
+ return this;
+}
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeArray(JavascriptBundledModule, this.modules);
- try writer.writeArray(JavascriptBundledPackage, this.packages);
- try writer.writeArray(u8, this.etag);
- try writer.writeInt(this.generated_at);
- try writer.writeArray(u8, this.app_package_json_dependencies_hash);
- try writer.writeArray(u8, this.import_from_name);
- try writer.writeArray(u8, this.manifest_string);
- }
- };
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeValue(this.path);
+ try writer.writeValue(this.code);
+ try writer.writeInt(this.package_id);
+ try writer.writeInt(this.id);
+ try writer.writeInt(this.path_extname_length);
+}
- pub const JavascriptBundleContainer = struct {
- /// bundle_format_version
- bundle_format_version: ?u32 = null,
+};
- /// bundle
- bundle: ?JavascriptBundle = null,
+pub const JavascriptBundledPackage = struct {
+/// name
+name: StringPointer,
- /// code_length
- code_length: ?u32 = null,
+/// version
+version: StringPointer,
- pub fn decode(reader: anytype) anyerror!JavascriptBundleContainer {
- var this = std.mem.zeroes(JavascriptBundleContainer);
+/// hash
+hash: u32 = 0,
- while (true) {
- switch (try reader.readByte()) {
- 0 => {
- return this;
- },
+/// modules_offset
+modules_offset: u32 = 0,
- 1 => {
- this.bundle_format_version = try reader.readValue(u32);
- },
- 2 => {
- this.bundle = try reader.readValue(JavascriptBundle);
- },
- 3 => {
- this.code_length = try reader.readValue(u32);
- },
- else => {
- return error.InvalidMessage;
- },
+/// modules_length
+modules_length: u32 = 0,
+
+
+pub fn decode(reader: anytype) anyerror!JavascriptBundledPackage {
+ var this = std.mem.zeroes(JavascriptBundledPackage);
+
+ this.name = try reader.readValue(StringPointer);
+ this.version = try reader.readValue(StringPointer);
+ this.hash = try reader.readValue(u32);
+ this.modules_offset = try reader.readValue(u32);
+ this.modules_length = try reader.readValue(u32);
+ return this;
+}
+
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeValue(this.name);
+ try writer.writeValue(this.version);
+ try writer.writeInt(this.hash);
+ try writer.writeInt(this.modules_offset);
+ try writer.writeInt(this.modules_length);
+}
+
+};
+
+pub const JavascriptBundle = struct {
+/// modules
+modules: []const JavascriptBundledModule,
+
+/// packages
+packages: []const JavascriptBundledPackage,
+
+/// etag
+etag: []const u8,
+
+/// generated_at
+generated_at: u32 = 0,
+
+/// app_package_json_dependencies_hash
+app_package_json_dependencies_hash: []const u8,
+
+/// import_from_name
+import_from_name: []const u8,
+
+/// manifest_string
+manifest_string: []const u8,
+
+
+pub fn decode(reader: anytype) anyerror!JavascriptBundle {
+ var this = std.mem.zeroes(JavascriptBundle);
+
+ this.modules = try reader.readArray(JavascriptBundledModule);
+ this.packages = try reader.readArray(JavascriptBundledPackage);
+ this.etag = try reader.readArray(u8);
+ this.generated_at = try reader.readValue(u32);
+ this.app_package_json_dependencies_hash = try reader.readArray(u8);
+ this.import_from_name = try reader.readArray(u8);
+ this.manifest_string = try reader.readArray(u8);
+ return this;
+}
+
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeArray(JavascriptBundledModule, this.modules);
+ try writer.writeArray(JavascriptBundledPackage, this.packages);
+ try writer.writeArray(u8, this.etag);
+ try writer.writeInt(this.generated_at);
+ try writer.writeArray(u8, this.app_package_json_dependencies_hash);
+ try writer.writeArray(u8, this.import_from_name);
+ try writer.writeArray(u8, this.manifest_string);
+}
+
+};
+
+pub const JavascriptBundleContainer = struct {
+/// bundle_format_version
+bundle_format_version: ?u32 = null,
+
+/// bundle
+bundle: ?JavascriptBundle = null,
+
+/// code_length
+code_length: ?u32 = null,
+
+
+pub fn decode(reader: anytype) anyerror!JavascriptBundleContainer {
+ var this = std.mem.zeroes(JavascriptBundleContainer);
+
+ while(true) {
+ switch (try reader.readByte()) {
+ 0 => { return this; },
+
+ 1 => {
+ this.bundle_format_version = try reader.readValue(u32);
+},
+ 2 => {
+ this.bundle = try reader.readValue(JavascriptBundle);
+},
+ 3 => {
+ this.code_length = try reader.readValue(u32);
+},
+ else => {
+ return error.InvalidMessage;
+ },
+ }
+ }
+unreachable;
+}
+
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+if (this.bundle_format_version) |bundle_format_version| {
+ try writer.writeFieldID(1);
+ try writer.writeInt(bundle_format_version);
+}
+if (this.bundle) |bundle| {
+ try writer.writeFieldID(2);
+ try writer.writeValue(bundle);
+}
+if (this.code_length) |code_length| {
+ try writer.writeFieldID(3);
+ try writer.writeInt(code_length);
+}
+try writer.endMessage();
+}
+
+};
+
+pub const ScanDependencyMode = enum(u8) {
+
+_none,
+ /// app
+ app,
+
+ /// all
+ all,
+
+_,
+
+ pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
+ return try std.json.stringify(@tagName(self), opts, o);
}
- }
- unreachable;
- }
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- if (this.bundle_format_version) |bundle_format_version| {
- try writer.writeFieldID(1);
- try writer.writeInt(bundle_format_version);
- }
- if (this.bundle) |bundle| {
- try writer.writeFieldID(2);
- try writer.writeValue(bundle);
- }
- if (this.code_length) |code_length| {
- try writer.writeFieldID(3);
- try writer.writeInt(code_length);
- }
- try writer.endMessage();
- }
- };
+
+};
- pub const ScanDependencyMode = enum(u8) {
- _none,
- /// app
- app,
+pub const ModuleImportType = enum(u8) {
- /// all
- all,
+_none,
+ /// import
+ import,
- _,
+ /// require
+ require,
- pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
- return try std.json.stringify(@tagName(self), opts, o);
- }
- };
+_,
- pub const ModuleImportType = enum(u8) {
- _none,
- /// import
- import,
+ pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
+ return try std.json.stringify(@tagName(self), opts, o);
+ }
- /// require
- require,
+
+};
- _,
+pub const ModuleImportRecord = struct {
+/// kind
+kind: ModuleImportType,
- pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
- return try std.json.stringify(@tagName(self), opts, o);
- }
- };
+/// path
+path: []const u8,
- pub const ModuleImportRecord = struct {
- /// kind
- kind: ModuleImportType,
+/// dynamic
+dynamic: bool = false,
- /// path
- path: []const u8,
- /// dynamic
- dynamic: bool = false,
+pub fn decode(reader: anytype) anyerror!ModuleImportRecord {
+ var this = std.mem.zeroes(ModuleImportRecord);
- pub fn decode(reader: anytype) anyerror!ModuleImportRecord {
- var this = std.mem.zeroes(ModuleImportRecord);
+ this.kind = try reader.readValue(ModuleImportType);
+ this.path = try reader.readValue([]const u8);
+ this.dynamic = try reader.readValue(bool);
+ return this;
+}
- this.kind = try reader.readValue(ModuleImportType);
- this.path = try reader.readValue([]const u8);
- this.dynamic = try reader.readValue(bool);
- return this;
- }
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeEnum(this.kind);
+ try writer.writeValue(this.path);
+ try writer.writeInt(@intCast(u8, @boolToInt(this.dynamic)));
+}
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeEnum(this.kind);
- try writer.writeValue(this.path);
- try writer.writeInt(@intCast(u8, @boolToInt(this.dynamic)));
- }
- };
+};
- pub const Module = struct {
- /// path
- path: []const u8,
+pub const Module = struct {
+/// path
+path: []const u8,
- /// imports
- imports: []const ModuleImportRecord,
+/// imports
+imports: []const ModuleImportRecord,
- pub fn decode(reader: anytype) anyerror!Module {
- var this = std.mem.zeroes(Module);
- this.path = try reader.readValue([]const u8);
- this.imports = try reader.readArray(ModuleImportRecord);
- return this;
- }
+pub fn decode(reader: anytype) anyerror!Module {
+ var this = std.mem.zeroes(Module);
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeValue(this.path);
- try writer.writeArray(ModuleImportRecord, this.imports);
- }
- };
+ this.path = try reader.readValue([]const u8);
+ this.imports = try reader.readArray(ModuleImportRecord);
+ return this;
+}
- pub const StringMap = struct {
- /// keys
- keys: []const []const u8,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeValue(this.path);
+ try writer.writeArray(ModuleImportRecord, this.imports);
+}
- /// values
- values: []const []const u8,
+};
- pub fn decode(reader: anytype) anyerror!StringMap {
- var this = std.mem.zeroes(StringMap);
+pub const StringMap = struct {
+/// keys
+keys: []const []const u8,
- this.keys = try reader.readArray([]const u8);
- this.values = try reader.readArray([]const u8);
- return this;
- }
+/// values
+values: []const []const u8,
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeArray([]const u8, this.keys);
- try writer.writeArray([]const u8, this.values);
- }
- };
- pub const LoaderMap = struct {
- /// extensions
- extensions: []const []const u8,
+pub fn decode(reader: anytype) anyerror!StringMap {
+ var this = std.mem.zeroes(StringMap);
- /// loaders
- loaders: []const Loader,
+ this.keys = try reader.readArray([]const u8);
+ this.values = try reader.readArray([]const u8);
+ return this;
+}
- pub fn decode(reader: anytype) anyerror!LoaderMap {
- var this = std.mem.zeroes(LoaderMap);
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeArray([]const u8, this.keys);
+ try writer.writeArray([]const u8, this.values);
+}
- this.extensions = try reader.readArray([]const u8);
- this.loaders = try reader.readArray(Loader);
- return this;
- }
+};
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeArray([]const u8, this.extensions);
- try writer.writeArray(Loader, this.loaders);
- }
- };
+pub const LoaderMap = struct {
+/// extensions
+extensions: []const []const u8,
- pub const TransformOptions = struct {
- /// jsx
- jsx: ?Jsx = null,
+/// loaders
+loaders: []const Loader,
- /// tsconfig_override
- tsconfig_override: ?[]const u8 = null,
- /// resolve
- resolve: ?ResolveMode = null,
+pub fn decode(reader: anytype) anyerror!LoaderMap {
+ var this = std.mem.zeroes(LoaderMap);
- /// public_url
- public_url: ?[]const u8 = null,
+ this.extensions = try reader.readArray([]const u8);
+ this.loaders = try reader.readArray(Loader);
+ return this;
+}
- /// absolute_working_dir
- absolute_working_dir: ?[]const u8 = null,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeArray([]const u8, this.extensions);
+ try writer.writeArray(Loader, this.loaders);
+}
- /// define
- define: ?StringMap = null,
+};
- /// preserve_symlinks
- preserve_symlinks: ?bool = null,
+pub const TransformOptions = struct {
+/// jsx
+jsx: ?Jsx = null,
+
+/// tsconfig_override
+tsconfig_override: ?[]const u8 = null,
+
+/// resolve
+resolve: ?ResolveMode = null,
+
+/// public_url
+public_url: ?[]const u8 = null,
+
+/// absolute_working_dir
+absolute_working_dir: ?[]const u8 = null,
+
+/// define
+define: ?StringMap = null,
+
+/// preserve_symlinks
+preserve_symlinks: ?bool = null,
+
+/// entry_points
+entry_points: []const []const u8,
+
+/// write
+write: ?bool = null,
+
+/// inject
+inject: []const []const u8,
+
+/// output_dir
+output_dir: ?[]const u8 = null,
+
+/// external
+external: []const []const u8,
+
+/// loaders
+loaders: ?LoaderMap = null,
+
+/// main_fields
+main_fields: []const []const u8,
+
+/// platform
+platform: ?Platform = null,
+
+/// serve
+serve: ?bool = null,
+
+/// extension_order
+extension_order: []const []const u8,
+
+/// public_dir
+public_dir: ?[]const u8 = null,
+
+/// only_scan_dependencies
+only_scan_dependencies: ?ScanDependencyMode = null,
+
+/// generate_node_module_bundle
+generate_node_module_bundle: ?bool = null,
+
+/// node_modules_bundle_path
+node_modules_bundle_path: ?[]const u8 = null,
+
+
+pub fn decode(reader: anytype) anyerror!TransformOptions {
+ var this = std.mem.zeroes(TransformOptions);
+
+ while(true) {
+ switch (try reader.readByte()) {
+ 0 => { return this; },
+
+ 1 => {
+ this.jsx = try reader.readValue(Jsx);
+},
+ 2 => {
+ this.tsconfig_override = try reader.readValue([]const u8);
+},
+ 3 => {
+ this.resolve = try reader.readValue(ResolveMode);
+},
+ 4 => {
+ this.public_url = try reader.readValue([]const u8);
+},
+ 5 => {
+ this.absolute_working_dir = try reader.readValue([]const u8);
+},
+ 6 => {
+ this.define = try reader.readValue(StringMap);
+},
+ 7 => {
+ this.preserve_symlinks = try reader.readValue(bool);
+},
+ 8 => {
+ this.entry_points = try reader.readArray([]const u8);
+},
+ 9 => {
+ this.write = try reader.readValue(bool);
+},
+ 10 => {
+ this.inject = try reader.readArray([]const u8);
+},
+ 11 => {
+ this.output_dir = try reader.readValue([]const u8);
+},
+ 12 => {
+ this.external = try reader.readArray([]const u8);
+},
+ 13 => {
+ this.loaders = try reader.readValue(LoaderMap);
+},
+ 14 => {
+ this.main_fields = try reader.readArray([]const u8);
+},
+ 15 => {
+ this.platform = try reader.readValue(Platform);
+},
+ 16 => {
+ this.serve = try reader.readValue(bool);
+},
+ 17 => {
+ this.extension_order = try reader.readArray([]const u8);
+},
+ 18 => {
+ this.public_dir = try reader.readValue([]const u8);
+},
+ 19 => {
+ this.only_scan_dependencies = try reader.readValue(ScanDependencyMode);
+},
+ 20 => {
+ this.generate_node_module_bundle = try reader.readValue(bool);
+},
+ 21 => {
+ this.node_modules_bundle_path = try reader.readValue([]const u8);
+},
+ else => {
+ return error.InvalidMessage;
+ },
+ }
+ }
+unreachable;
+}
- /// entry_points
- entry_points: []const []const u8,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+if (this.jsx) |jsx| {
+ try writer.writeFieldID(1);
+ try writer.writeValue(jsx);
+}
+if (this.tsconfig_override) |tsconfig_override| {
+ try writer.writeFieldID(2);
+ try writer.writeValue(tsconfig_override);
+}
+if (this.resolve) |resolve| {
+ try writer.writeFieldID(3);
+ try writer.writeEnum(resolve);
+}
+if (this.public_url) |public_url| {
+ try writer.writeFieldID(4);
+ try writer.writeValue(public_url);
+}
+if (this.absolute_working_dir) |absolute_working_dir| {
+ try writer.writeFieldID(5);
+ try writer.writeValue(absolute_working_dir);
+}
+if (this.define) |define| {
+ try writer.writeFieldID(6);
+ try writer.writeValue(define);
+}
+if (this.preserve_symlinks) |preserve_symlinks| {
+ try writer.writeFieldID(7);
+ try writer.writeInt(@intCast(u8, @boolToInt(preserve_symlinks)));
+}
+if (this.entry_points) |entry_points| {
+ try writer.writeFieldID(8);
+ try writer.writeArray([]const u8, entry_points);
+}
+if (this.write) |write| {
+ try writer.writeFieldID(9);
+ try writer.writeInt(@intCast(u8, @boolToInt(write)));
+}
+if (this.inject) |inject| {
+ try writer.writeFieldID(10);
+ try writer.writeArray([]const u8, inject);
+}
+if (this.output_dir) |output_dir| {
+ try writer.writeFieldID(11);
+ try writer.writeValue(output_dir);
+}
+if (this.external) |external| {
+ try writer.writeFieldID(12);
+ try writer.writeArray([]const u8, external);
+}
+if (this.loaders) |loaders| {
+ try writer.writeFieldID(13);
+ try writer.writeValue(loaders);
+}
+if (this.main_fields) |main_fields| {
+ try writer.writeFieldID(14);
+ try writer.writeArray([]const u8, main_fields);
+}
+if (this.platform) |platform| {
+ try writer.writeFieldID(15);
+ try writer.writeEnum(platform);
+}
+if (this.serve) |serve| {
+ try writer.writeFieldID(16);
+ try writer.writeInt(@intCast(u8, @boolToInt(serve)));
+}
+if (this.extension_order) |extension_order| {
+ try writer.writeFieldID(17);
+ try writer.writeArray([]const u8, extension_order);
+}
+if (this.public_dir) |public_dir| {
+ try writer.writeFieldID(18);
+ try writer.writeValue(public_dir);
+}
+if (this.only_scan_dependencies) |only_scan_dependencies| {
+ try writer.writeFieldID(19);
+ try writer.writeEnum(only_scan_dependencies);
+}
+if (this.generate_node_module_bundle) |generate_node_module_bundle| {
+ try writer.writeFieldID(20);
+ try writer.writeInt(@intCast(u8, @boolToInt(generate_node_module_bundle)));
+}
+if (this.node_modules_bundle_path) |node_modules_bundle_path| {
+ try writer.writeFieldID(21);
+ try writer.writeValue(node_modules_bundle_path);
+}
+try writer.endMessage();
+}
- /// write
- write: ?bool = null,
+};
- /// inject
- inject: []const []const u8,
+pub const FileHandle = struct {
+/// path
+path: []const u8,
- /// output_dir
- output_dir: ?[]const u8 = null,
+/// size
+size: u32 = 0,
- /// external
- external: []const []const u8,
+/// fd
+fd: u32 = 0,
- /// loaders
- loaders: ?LoaderMap = null,
- /// main_fields
- main_fields: []const []const u8,
+pub fn decode(reader: anytype) anyerror!FileHandle {
+ var this = std.mem.zeroes(FileHandle);
- /// platform
- platform: ?Platform = null,
+ this.path = try reader.readValue([]const u8);
+ this.size = try reader.readValue(u32);
+ this.fd = try reader.readValue(u32);
+ return this;
+}
- /// serve
- serve: ?bool = null,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeValue(this.path);
+ try writer.writeInt(this.size);
+ try writer.writeInt(this.fd);
+}
- /// extension_order
- extension_order: []const []const u8,
+};
- /// public_dir
- public_dir: ?[]const u8 = null,
+pub const Transform = struct {
+/// handle
+handle: ?FileHandle = null,
+
+/// path
+path: ?[]const u8 = null,
+
+/// contents
+contents: []const u8,
+
+/// loader
+loader: ?Loader = null,
+
+/// options
+options: ?TransformOptions = null,
+
+
+pub fn decode(reader: anytype) anyerror!Transform {
+ var this = std.mem.zeroes(Transform);
+
+ while(true) {
+ switch (try reader.readByte()) {
+ 0 => { return this; },
+
+ 1 => {
+ this.handle = try reader.readValue(FileHandle);
+},
+ 2 => {
+ this.path = try reader.readValue([]const u8);
+},
+ 3 => {
+ this.contents = try reader.readArray(u8);
+},
+ 4 => {
+ this.loader = try reader.readValue(Loader);
+},
+ 5 => {
+ this.options = try reader.readValue(TransformOptions);
+},
+ else => {
+ return error.InvalidMessage;
+ },
+ }
+ }
+unreachable;
+}
- /// only_scan_dependencies
- only_scan_dependencies: ?ScanDependencyMode = null,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+if (this.handle) |handle| {
+ try writer.writeFieldID(1);
+ try writer.writeValue(handle);
+}
+if (this.path) |path| {
+ try writer.writeFieldID(2);
+ try writer.writeValue(path);
+}
+if (this.contents) |contents| {
+ try writer.writeFieldID(3);
+ try writer.writeArray(u8, contents);
+}
+if (this.loader) |loader| {
+ try writer.writeFieldID(4);
+ try writer.writeEnum(loader);
+}
+if (this.options) |options| {
+ try writer.writeFieldID(5);
+ try writer.writeValue(options);
+}
+try writer.endMessage();
+}
- /// generate_node_module_bundle
- generate_node_module_bundle: ?bool = null,
+};
- /// node_modules_bundle_path
- node_modules_bundle_path: ?[]const u8 = null,
+pub const TransformResponseStatus = enum(u32) {
- pub fn decode(reader: anytype) anyerror!TransformOptions {
- var this = std.mem.zeroes(TransformOptions);
+_none,
+ /// success
+ success,
- while (true) {
- switch (try reader.readByte()) {
- 0 => {
- return this;
- },
+ /// fail
+ fail,
- 1 => {
- this.jsx = try reader.readValue(Jsx);
- },
- 2 => {
- this.tsconfig_override = try reader.readValue([]const u8);
- },
- 3 => {
- this.resolve = try reader.readValue(ResolveMode);
- },
- 4 => {
- this.public_url = try reader.readValue([]const u8);
- },
- 5 => {
- this.absolute_working_dir = try reader.readValue([]const u8);
- },
- 6 => {
- this.define = try reader.readValue(StringMap);
- },
- 7 => {
- this.preserve_symlinks = try reader.readValue(bool);
- },
- 8 => {
- this.entry_points = try reader.readArray([]const u8);
- },
- 9 => {
- this.write = try reader.readValue(bool);
- },
- 10 => {
- this.inject = try reader.readArray([]const u8);
- },
- 11 => {
- this.output_dir = try reader.readValue([]const u8);
- },
- 12 => {
- this.external = try reader.readArray([]const u8);
- },
- 13 => {
- this.loaders = try reader.readValue(LoaderMap);
- },
- 14 => {
- this.main_fields = try reader.readArray([]const u8);
- },
- 15 => {
- this.platform = try reader.readValue(Platform);
- },
- 16 => {
- this.serve = try reader.readValue(bool);
- },
- 17 => {
- this.extension_order = try reader.readArray([]const u8);
- },
- 18 => {
- this.public_dir = try reader.readValue([]const u8);
- },
- 19 => {
- this.only_scan_dependencies = try reader.readValue(ScanDependencyMode);
- },
- 20 => {
- this.generate_node_module_bundle = try reader.readValue(bool);
- },
- 21 => {
- this.node_modules_bundle_path = try reader.readValue([]const u8);
- },
- else => {
- return error.InvalidMessage;
- },
+_,
+
+ pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
+ return try std.json.stringify(@tagName(self), opts, o);
}
- }
- unreachable;
- }
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- if (this.jsx) |jsx| {
- try writer.writeFieldID(1);
- try writer.writeValue(jsx);
- }
- if (this.tsconfig_override) |tsconfig_override| {
- try writer.writeFieldID(2);
- try writer.writeValue(tsconfig_override);
- }
- if (this.resolve) |resolve| {
- try writer.writeFieldID(3);
- try writer.writeEnum(resolve);
- }
- if (this.public_url) |public_url| {
- try writer.writeFieldID(4);
- try writer.writeValue(public_url);
- }
- if (this.absolute_working_dir) |absolute_working_dir| {
- try writer.writeFieldID(5);
- try writer.writeValue(absolute_working_dir);
- }
- if (this.define) |define| {
- try writer.writeFieldID(6);
- try writer.writeValue(define);
- }
- if (this.preserve_symlinks) |preserve_symlinks| {
- try writer.writeFieldID(7);
- try writer.writeInt(@intCast(u8, @boolToInt(preserve_symlinks)));
- }
- if (this.entry_points) |entry_points| {
- try writer.writeFieldID(8);
- try writer.writeArray([]const u8, entry_points);
- }
- if (this.write) |write| {
- try writer.writeFieldID(9);
- try writer.writeInt(@intCast(u8, @boolToInt(write)));
- }
- if (this.inject) |inject| {
- try writer.writeFieldID(10);
- try writer.writeArray([]const u8, inject);
- }
- if (this.output_dir) |output_dir| {
- try writer.writeFieldID(11);
- try writer.writeValue(output_dir);
- }
- if (this.external) |external| {
- try writer.writeFieldID(12);
- try writer.writeArray([]const u8, external);
- }
- if (this.loaders) |loaders| {
- try writer.writeFieldID(13);
- try writer.writeValue(loaders);
- }
- if (this.main_fields) |main_fields| {
- try writer.writeFieldID(14);
- try writer.writeArray([]const u8, main_fields);
- }
- if (this.platform) |platform| {
- try writer.writeFieldID(15);
- try writer.writeEnum(platform);
- }
- if (this.serve) |serve| {
- try writer.writeFieldID(16);
- try writer.writeInt(@intCast(u8, @boolToInt(serve)));
- }
- if (this.extension_order) |extension_order| {
- try writer.writeFieldID(17);
- try writer.writeArray([]const u8, extension_order);
- }
- if (this.public_dir) |public_dir| {
- try writer.writeFieldID(18);
- try writer.writeValue(public_dir);
- }
- if (this.only_scan_dependencies) |only_scan_dependencies| {
- try writer.writeFieldID(19);
- try writer.writeEnum(only_scan_dependencies);
- }
- if (this.generate_node_module_bundle) |generate_node_module_bundle| {
- try writer.writeFieldID(20);
- try writer.writeInt(@intCast(u8, @boolToInt(generate_node_module_bundle)));
- }
- if (this.node_modules_bundle_path) |node_modules_bundle_path| {
- try writer.writeFieldID(21);
- try writer.writeValue(node_modules_bundle_path);
- }
- try writer.endMessage();
- }
- };
+
+};
- pub const FileHandle = struct {
- /// path
- path: []const u8,
+pub const OutputFile = struct {
+/// data
+data: []const u8,
- /// size
- size: u32 = 0,
+/// path
+path: []const u8,
- /// fd
- fd: u32 = 0,
- pub fn decode(reader: anytype) anyerror!FileHandle {
- var this = std.mem.zeroes(FileHandle);
+pub fn decode(reader: anytype) anyerror!OutputFile {
+ var this = std.mem.zeroes(OutputFile);
- this.path = try reader.readValue([]const u8);
- this.size = try reader.readValue(u32);
- this.fd = try reader.readValue(u32);
- return this;
- }
+ this.data = try reader.readArray(u8);
+ this.path = try reader.readValue([]const u8);
+ return this;
+}
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeValue(this.path);
- try writer.writeInt(this.size);
- try writer.writeInt(this.fd);
- }
- };
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeArray(u8, this.data);
+ try writer.writeValue(this.path);
+}
- pub const Transform = struct {
- /// handle
- handle: ?FileHandle = null,
+};
- /// path
- path: ?[]const u8 = null,
+pub const TransformResponse = struct {
+/// status
+status: TransformResponseStatus,
- /// contents
- contents: []const u8,
+/// files
+files: []const OutputFile,
- /// loader
- loader: ?Loader = null,
+/// errors
+errors: []const Message,
- /// options
- options: ?TransformOptions = null,
- pub fn decode(reader: anytype) anyerror!Transform {
- var this = std.mem.zeroes(Transform);
+pub fn decode(reader: anytype) anyerror!TransformResponse {
+ var this = std.mem.zeroes(TransformResponse);
- while (true) {
- switch (try reader.readByte()) {
- 0 => {
- return this;
- },
+ this.status = try reader.readValue(TransformResponseStatus);
+ this.files = try reader.readArray(OutputFile);
+ this.errors = try reader.readArray(Message);
+ return this;
+}
- 1 => {
- this.handle = try reader.readValue(FileHandle);
- },
- 2 => {
- this.path = try reader.readValue([]const u8);
- },
- 3 => {
- this.contents = try reader.readArray(u8);
- },
- 4 => {
- this.loader = try reader.readValue(Loader);
- },
- 5 => {
- this.options = try reader.readValue(TransformOptions);
- },
- else => {
- return error.InvalidMessage;
- },
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeEnum(this.status);
+ try writer.writeArray(OutputFile, this.files);
+ try writer.writeArray(Message, this.errors);
+}
+
+};
+
+pub const MessageKind = enum(u32) {
+
+_none,
+ /// err
+ err,
+
+ /// warn
+ warn,
+
+ /// note
+ note,
+
+ /// debug
+ debug,
+
+_,
+
+ pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
+ return try std.json.stringify(@tagName(self), opts, o);
}
- }
- unreachable;
- }
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- if (this.handle) |handle| {
- try writer.writeFieldID(1);
- try writer.writeValue(handle);
- }
- if (this.path) |path| {
- try writer.writeFieldID(2);
- try writer.writeValue(path);
- }
- if (this.contents) |contents| {
- try writer.writeFieldID(3);
- try writer.writeArray(u8, contents);
- }
- if (this.loader) |loader| {
- try writer.writeFieldID(4);
- try writer.writeEnum(loader);
- }
- if (this.options) |options| {
- try writer.writeFieldID(5);
- try writer.writeValue(options);
- }
- try writer.endMessage();
- }
- };
+
+};
- pub const TransformResponseStatus = enum(u32) {
- _none,
- /// success
- success,
+pub const Location = struct {
+/// file
+file: []const u8,
- /// fail
- fail,
+/// namespace
+namespace: []const u8,
- _,
+/// line
+line: i32 = 0,
- pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
- return try std.json.stringify(@tagName(self), opts, o);
- }
- };
+/// column
+column: i32 = 0,
- pub const OutputFile = struct {
- /// data
- data: []const u8,
+/// line_text
+line_text: []const u8,
- /// path
- path: []const u8,
+/// suggestion
+suggestion: []const u8,
- pub fn decode(reader: anytype) anyerror!OutputFile {
- var this = std.mem.zeroes(OutputFile);
+/// offset
+offset: u32 = 0,
- this.data = try reader.readArray(u8);
- this.path = try reader.readValue([]const u8);
- return this;
- }
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeArray(u8, this.data);
- try writer.writeValue(this.path);
- }
- };
+pub fn decode(reader: anytype) anyerror!Location {
+ var this = std.mem.zeroes(Location);
- pub const TransformResponse = struct {
- /// status
- status: TransformResponseStatus,
+ this.file = try reader.readValue([]const u8);
+ this.namespace = try reader.readValue([]const u8);
+ this.line = try reader.readValue(i32);
+ this.column = try reader.readValue(i32);
+ this.line_text = try reader.readValue([]const u8);
+ this.suggestion = try reader.readValue([]const u8);
+ this.offset = try reader.readValue(u32);
+ return this;
+}
- /// files
- files: []const OutputFile,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeValue(this.file);
+ try writer.writeValue(this.namespace);
+ try writer.writeInt(this.line);
+ try writer.writeInt(this.column);
+ try writer.writeValue(this.line_text);
+ try writer.writeValue(this.suggestion);
+ try writer.writeInt(this.offset);
+}
- /// errors
- errors: []const Message,
+};
- pub fn decode(reader: anytype) anyerror!TransformResponse {
- var this = std.mem.zeroes(TransformResponse);
+pub const MessageData = struct {
+/// text
+text: ?[]const u8 = null,
+
+/// location
+location: ?Location = null,
+
+
+pub fn decode(reader: anytype) anyerror!MessageData {
+ var this = std.mem.zeroes(MessageData);
+
+ while(true) {
+ switch (try reader.readByte()) {
+ 0 => { return this; },
+
+ 1 => {
+ this.text = try reader.readValue([]const u8);
+},
+ 2 => {
+ this.location = try reader.readValue(Location);
+},
+ else => {
+ return error.InvalidMessage;
+ },
+ }
+ }
+unreachable;
+}
- this.status = try reader.readValue(TransformResponseStatus);
- this.files = try reader.readArray(OutputFile);
- this.errors = try reader.readArray(Message);
- return this;
- }
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+if (this.text) |text| {
+ try writer.writeFieldID(1);
+ try writer.writeValue(text);
+}
+if (this.location) |location| {
+ try writer.writeFieldID(2);
+ try writer.writeValue(location);
+}
+try writer.endMessage();
+}
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeEnum(this.status);
- try writer.writeArray(OutputFile, this.files);
- try writer.writeArray(Message, this.errors);
- }
- };
+};
- pub const MessageKind = enum(u32) {
- _none,
- /// err
- err,
+pub const Message = struct {
+/// kind
+kind: MessageKind,
- /// warn
- warn,
+/// data
+data: MessageData,
- /// note
- note,
+/// notes
+notes: []const MessageData,
- /// debug
- debug,
- _,
+pub fn decode(reader: anytype) anyerror!Message {
+ var this = std.mem.zeroes(Message);
- pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
- return try std.json.stringify(@tagName(self), opts, o);
- }
- };
+ this.kind = try reader.readValue(MessageKind);
+ this.data = try reader.readValue(MessageData);
+ this.notes = try reader.readArray(MessageData);
+ return this;
+}
- pub const Location = struct {
- /// file
- file: []const u8,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeEnum(this.kind);
+ try writer.writeValue(this.data);
+ try writer.writeArray(MessageData, this.notes);
+}
- /// namespace
- namespace: []const u8,
+};
- /// line
- line: i32 = 0,
+pub const Log = struct {
+/// warnings
+warnings: u32 = 0,
- /// column
- column: i32 = 0,
+/// errors
+errors: u32 = 0,
- /// line_text
- line_text: []const u8,
+/// msgs
+msgs: []const Message,
- /// suggestion
- suggestion: []const u8,
- /// offset
- offset: u32 = 0,
+pub fn decode(reader: anytype) anyerror!Log {
+ var this = std.mem.zeroes(Log);
- pub fn decode(reader: anytype) anyerror!Location {
- var this = std.mem.zeroes(Location);
+ this.warnings = try reader.readValue(u32);
+ this.errors = try reader.readValue(u32);
+ this.msgs = try reader.readArray(Message);
+ return this;
+}
- this.file = try reader.readValue([]const u8);
- this.namespace = try reader.readValue([]const u8);
- this.line = try reader.readValue(i32);
- this.column = try reader.readValue(i32);
- this.line_text = try reader.readValue([]const u8);
- this.suggestion = try reader.readValue([]const u8);
- this.offset = try reader.readValue(u32);
- return this;
- }
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeInt(this.warnings);
+ try writer.writeInt(this.errors);
+ try writer.writeArray(Message, this.msgs);
+}
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeValue(this.file);
- try writer.writeValue(this.namespace);
- try writer.writeInt(this.line);
- try writer.writeInt(this.column);
- try writer.writeValue(this.line_text);
- try writer.writeValue(this.suggestion);
- try writer.writeInt(this.offset);
- }
- };
+};
- pub const MessageData = struct {
- /// text
- text: ?[]const u8 = null,
+pub const Reloader = enum(u8) {
- /// location
- location: ?Location = null,
+_none,
+ /// disable
+ disable,
- pub fn decode(reader: anytype) anyerror!MessageData {
- var this = std.mem.zeroes(MessageData);
+ /// live
+ live,
- while (true) {
- switch (try reader.readByte()) {
- 0 => {
- return this;
- },
+ /// fast_refresh
+ fast_refresh,
- 1 => {
- this.text = try reader.readValue([]const u8);
- },
- 2 => {
- this.location = try reader.readValue(Location);
- },
- else => {
- return error.InvalidMessage;
- },
+_,
+
+ pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
+ return try std.json.stringify(@tagName(self), opts, o);
}
- }
- unreachable;
- }
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- if (this.text) |text| {
- try writer.writeFieldID(1);
- try writer.writeValue(text);
- }
- if (this.location) |location| {
- try writer.writeFieldID(2);
- try writer.writeValue(location);
- }
- try writer.endMessage();
- }
- };
+
+};
- pub const Message = struct {
- /// kind
- kind: MessageKind,
+pub const WebsocketMessageKind = enum(u8) {
- /// data
- data: MessageData,
+_none,
+ /// welcome
+ welcome,
- /// notes
- notes: []const MessageData,
+ /// file_change_notification
+ file_change_notification,
- pub fn decode(reader: anytype) anyerror!Message {
- var this = std.mem.zeroes(Message);
+ /// build_success
+ build_success,
- this.kind = try reader.readValue(MessageKind);
- this.data = try reader.readValue(MessageData);
- this.notes = try reader.readArray(MessageData);
- return this;
- }
+ /// build_fail
+ build_fail,
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeEnum(this.kind);
- try writer.writeValue(this.data);
- try writer.writeArray(MessageData, this.notes);
- }
- };
+ /// manifest_success
+ manifest_success,
- pub const Log = struct {
- /// warnings
- warnings: u32 = 0,
+ /// manifest_fail
+ manifest_fail,
- /// errors
- errors: u32 = 0,
+_,
- /// msgs
- msgs: []const Message,
+ pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
+ return try std.json.stringify(@tagName(self), opts, o);
+ }
- pub fn decode(reader: anytype) anyerror!Log {
- var this = std.mem.zeroes(Log);
+
+};
- this.warnings = try reader.readValue(u32);
- this.errors = try reader.readValue(u32);
- this.msgs = try reader.readArray(Message);
- return this;
- }
+pub const WebsocketCommandKind = enum(u8) {
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeInt(this.warnings);
- try writer.writeInt(this.errors);
- try writer.writeArray(Message, this.msgs);
- }
- };
+_none,
+ /// build
+ build,
- pub const Reloader = enum(u8) {
- _none,
- /// disable
- disable,
+ /// manifest
+ manifest,
- /// live
- live,
+_,
- /// fast_refresh
- fast_refresh,
+ pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
+ return try std.json.stringify(@tagName(self), opts, o);
+ }
- _,
+
+};
- pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
- return try std.json.stringify(@tagName(self), opts, o);
- }
- };
+pub const WebsocketMessage = struct {
+/// timestamp
+timestamp: u32 = 0,
- pub const WebsocketMessageKind = enum(u8) {
- _none,
- /// welcome
- welcome,
+/// kind
+kind: WebsocketMessageKind,
- /// file_change_notification
- file_change_notification,
- /// build_success
- build_success,
+pub fn decode(reader: anytype) anyerror!WebsocketMessage {
+ var this = std.mem.zeroes(WebsocketMessage);
- /// build_fail
- build_fail,
+ this.timestamp = try reader.readValue(u32);
+ this.kind = try reader.readValue(WebsocketMessageKind);
+ return this;
+}
- /// manifest_success
- manifest_success,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeInt(this.timestamp);
+ try writer.writeEnum(this.kind);
+}
- /// manifest_fail
- manifest_fail,
+};
- _,
+pub const WebsocketMessageWelcome = struct {
+/// epoch
+epoch: u32 = 0,
- pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
- return try std.json.stringify(@tagName(self), opts, o);
- }
- };
+/// javascriptReloader
+javascript_reloader: Reloader,
- pub const WebsocketCommandKind = enum(u8) {
- _none,
- /// build
- build,
- /// manifest
- manifest,
+pub fn decode(reader: anytype) anyerror!WebsocketMessageWelcome {
+ var this = std.mem.zeroes(WebsocketMessageWelcome);
- _,
+ this.epoch = try reader.readValue(u32);
+ this.javascript_reloader = try reader.readValue(Reloader);
+ return this;
+}
- pub fn jsonStringify(self: *const @This(), opts: anytype, o: anytype) !void {
- return try std.json.stringify(@tagName(self), opts, o);
- }
- };
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeInt(this.epoch);
+ try writer.writeEnum(this.javascript_reloader);
+}
- pub const WebsocketMessage = struct {
- /// timestamp
- timestamp: u32 = 0,
+};
- /// kind
- kind: WebsocketMessageKind,
+pub const WebsocketMessageFileChangeNotification = struct {
+/// id
+id: u32 = 0,
- pub fn decode(reader: anytype) anyerror!WebsocketMessage {
- var this = std.mem.zeroes(WebsocketMessage);
+/// loader
+loader: Loader,
- this.timestamp = try reader.readValue(u32);
- this.kind = try reader.readValue(WebsocketMessageKind);
- return this;
- }
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeInt(this.timestamp);
- try writer.writeEnum(this.kind);
- }
- };
+pub fn decode(reader: anytype) anyerror!WebsocketMessageFileChangeNotification {
+ var this = std.mem.zeroes(WebsocketMessageFileChangeNotification);
- pub const WebsocketMessageWelcome = struct {
- /// epoch
- epoch: u32 = 0,
+ this.id = try reader.readValue(u32);
+ this.loader = try reader.readValue(Loader);
+ return this;
+}
- /// javascriptReloader
- javascript_reloader: Reloader,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeInt(this.id);
+ try writer.writeEnum(this.loader);
+}
- pub fn decode(reader: anytype) anyerror!WebsocketMessageWelcome {
- var this = std.mem.zeroes(WebsocketMessageWelcome);
+};
- this.epoch = try reader.readValue(u32);
- this.javascript_reloader = try reader.readValue(Reloader);
- return this;
- }
+pub const WebsocketCommand = struct {
+/// kind
+kind: WebsocketCommandKind,
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeInt(this.epoch);
- try writer.writeEnum(this.javascript_reloader);
- }
- };
+/// timestamp
+timestamp: u32 = 0,
- pub const WebsocketMessageFileChangeNotification = struct {
- /// id
- id: u32 = 0,
- /// loader
- loader: Loader,
+pub fn decode(reader: anytype) anyerror!WebsocketCommand {
+ var this = std.mem.zeroes(WebsocketCommand);
- pub fn decode(reader: anytype) anyerror!WebsocketMessageFileChangeNotification {
- var this = std.mem.zeroes(WebsocketMessageFileChangeNotification);
+ this.kind = try reader.readValue(WebsocketCommandKind);
+ this.timestamp = try reader.readValue(u32);
+ return this;
+}
- this.id = try reader.readValue(u32);
- this.loader = try reader.readValue(Loader);
- return this;
- }
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeEnum(this.kind);
+ try writer.writeInt(this.timestamp);
+}
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeInt(this.id);
- try writer.writeEnum(this.loader);
- }
- };
+};
- pub const WebsocketCommand = struct {
- /// kind
- kind: WebsocketCommandKind,
+pub const WebsocketCommandBuild = packed struct {
+/// id
+id: u32 = 0,
- /// timestamp
- timestamp: u32 = 0,
- pub fn decode(reader: anytype) anyerror!WebsocketCommand {
- var this = std.mem.zeroes(WebsocketCommand);
+pub fn decode(reader: anytype) anyerror!WebsocketCommandBuild {
+ var this = std.mem.zeroes(WebsocketCommandBuild);
- this.kind = try reader.readValue(WebsocketCommandKind);
- this.timestamp = try reader.readValue(u32);
- return this;
- }
+ this.id = try reader.readValue(u32);
+ return this;
+}
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeEnum(this.kind);
- try writer.writeInt(this.timestamp);
- }
- };
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeInt(this.id);
+}
- pub const WebsocketCommandBuild = packed struct {
- /// id
- id: u32 = 0,
+};
- pub fn decode(reader: anytype) anyerror!WebsocketCommandBuild {
- var this = std.mem.zeroes(WebsocketCommandBuild);
+pub const WebsocketCommandManifest = packed struct {
+/// id
+id: u32 = 0,
- this.id = try reader.readValue(u32);
- return this;
- }
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeInt(this.id);
- }
- };
+pub fn decode(reader: anytype) anyerror!WebsocketCommandManifest {
+ var this = std.mem.zeroes(WebsocketCommandManifest);
- pub const WebsocketCommandManifest = packed struct {
- /// id
- id: u32 = 0,
+ this.id = try reader.readValue(u32);
+ return this;
+}
- pub fn decode(reader: anytype) anyerror!WebsocketCommandManifest {
- var this = std.mem.zeroes(WebsocketCommandManifest);
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeInt(this.id);
+}
- this.id = try reader.readValue(u32);
- return this;
- }
+};
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeInt(this.id);
- }
- };
+pub const WebsocketMessageBuildSuccess = struct {
+/// id
+id: u32 = 0,
- pub const WebsocketMessageBuildSuccess = struct {
- /// id
- id: u32 = 0,
+/// from_timestamp
+from_timestamp: u32 = 0,
- /// from_timestamp
- from_timestamp: u32 = 0,
+/// loader
+loader: Loader,
- /// loader
- loader: Loader,
+/// module_path
+module_path: []const u8,
- /// module_path
- module_path: []const u8,
+/// blob_length
+blob_length: u32 = 0,
- /// blob_length
- blob_length: u32 = 0,
- pub fn decode(reader: anytype) anyerror!WebsocketMessageBuildSuccess {
- var this = std.mem.zeroes(WebsocketMessageBuildSuccess);
+pub fn decode(reader: anytype) anyerror!WebsocketMessageBuildSuccess {
+ var this = std.mem.zeroes(WebsocketMessageBuildSuccess);
- this.id = try reader.readValue(u32);
- this.from_timestamp = try reader.readValue(u32);
- this.loader = try reader.readValue(Loader);
- this.module_path = try reader.readValue([]const u8);
- this.blob_length = try reader.readValue(u32);
- return this;
- }
+ this.id = try reader.readValue(u32);
+ this.from_timestamp = try reader.readValue(u32);
+ this.loader = try reader.readValue(Loader);
+ this.module_path = try reader.readValue([]const u8);
+ this.blob_length = try reader.readValue(u32);
+ return this;
+}
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeInt(this.id);
- try writer.writeInt(this.from_timestamp);
- try writer.writeEnum(this.loader);
- try writer.writeValue(this.module_path);
- try writer.writeInt(this.blob_length);
- }
- };
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeInt(this.id);
+ try writer.writeInt(this.from_timestamp);
+ try writer.writeEnum(this.loader);
+ try writer.writeValue(this.module_path);
+ try writer.writeInt(this.blob_length);
+}
- pub const WebsocketMessageBuildFailure = struct {
- /// id
- id: u32 = 0,
+};
- /// from_timestamp
- from_timestamp: u32 = 0,
+pub const WebsocketMessageBuildFailure = struct {
+/// id
+id: u32 = 0,
- /// loader
- loader: Loader,
+/// from_timestamp
+from_timestamp: u32 = 0,
- /// module_path
- module_path: []const u8,
+/// loader
+loader: Loader,
- /// log
- log: Log,
+/// module_path
+module_path: []const u8,
- pub fn decode(reader: anytype) anyerror!WebsocketMessageBuildFailure {
- var this = std.mem.zeroes(WebsocketMessageBuildFailure);
+/// log
+log: Log,
- this.id = try reader.readValue(u32);
- this.from_timestamp = try reader.readValue(u32);
- this.loader = try reader.readValue(Loader);
- this.module_path = try reader.readValue([]const u8);
- this.log = try reader.readValue(Log);
- return this;
- }
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeInt(this.id);
- try writer.writeInt(this.from_timestamp);
- try writer.writeEnum(this.loader);
- try writer.writeValue(this.module_path);
- try writer.writeValue(this.log);
- }
- };
+pub fn decode(reader: anytype) anyerror!WebsocketMessageBuildFailure {
+ var this = std.mem.zeroes(WebsocketMessageBuildFailure);
- pub const DependencyManifest = struct {
- /// ids
- ids: []const u32,
+ this.id = try reader.readValue(u32);
+ this.from_timestamp = try reader.readValue(u32);
+ this.loader = try reader.readValue(Loader);
+ this.module_path = try reader.readValue([]const u8);
+ this.log = try reader.readValue(Log);
+ return this;
+}
- pub fn decode(reader: anytype) anyerror!DependencyManifest {
- var this = std.mem.zeroes(DependencyManifest);
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeInt(this.id);
+ try writer.writeInt(this.from_timestamp);
+ try writer.writeEnum(this.loader);
+ try writer.writeValue(this.module_path);
+ try writer.writeValue(this.log);
+}
- this.ids = try reader.readArray(u32);
- return this;
- }
+};
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeArray(u32, this.ids);
- }
- };
+pub const DependencyManifest = struct {
+/// ids
+ids: []const u32,
- pub const FileList = struct {
- /// ptrs
- ptrs: []const StringPointer,
- /// files
- files: []const u8,
+pub fn decode(reader: anytype) anyerror!DependencyManifest {
+ var this = std.mem.zeroes(DependencyManifest);
- pub fn decode(reader: anytype) anyerror!FileList {
- var this = std.mem.zeroes(FileList);
+ this.ids = try reader.readArray(u32);
+ return this;
+}
- this.ptrs = try reader.readArray(StringPointer);
- this.files = try reader.readValue([]const u8);
- return this;
- }
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeArray(u32, this.ids);
+}
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeArray(StringPointer, this.ptrs);
- try writer.writeValue(this.files);
- }
- };
+};
- pub const WebsocketMessageResolveIDs = struct {
- /// id
- id: []const u32,
+pub const FileList = struct {
+/// ptrs
+ptrs: []const StringPointer,
- /// list
- list: FileList,
+/// files
+files: []const u8,
- pub fn decode(reader: anytype) anyerror!WebsocketMessageResolveIDs {
- var this = std.mem.zeroes(WebsocketMessageResolveIDs);
- this.id = try reader.readArray(u32);
- this.list = try reader.readValue(FileList);
- return this;
- }
+pub fn decode(reader: anytype) anyerror!FileList {
+ var this = std.mem.zeroes(FileList);
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeArray(u32, this.id);
- try writer.writeValue(this.list);
- }
- };
+ this.ptrs = try reader.readArray(StringPointer);
+ this.files = try reader.readValue([]const u8);
+ return this;
+}
- pub const WebsocketCommandResolveIDs = struct {
- /// ptrs
- ptrs: []const StringPointer,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeArray(StringPointer, this.ptrs);
+ try writer.writeValue(this.files);
+}
- /// files
- files: []const u8,
+};
- pub fn decode(reader: anytype) anyerror!WebsocketCommandResolveIDs {
- var this = std.mem.zeroes(WebsocketCommandResolveIDs);
+pub const WebsocketMessageResolveIDs = struct {
+/// id
+id: []const u32,
- this.ptrs = try reader.readArray(StringPointer);
- this.files = try reader.readValue([]const u8);
- return this;
- }
+/// list
+list: FileList,
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeArray(StringPointer, this.ptrs);
- try writer.writeValue(this.files);
- }
- };
- pub const WebsocketMessageManifestSuccess = struct {
- /// id
- id: u32 = 0,
+pub fn decode(reader: anytype) anyerror!WebsocketMessageResolveIDs {
+ var this = std.mem.zeroes(WebsocketMessageResolveIDs);
- /// module_path
- module_path: []const u8,
+ this.id = try reader.readArray(u32);
+ this.list = try reader.readValue(FileList);
+ return this;
+}
- /// loader
- loader: Loader,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeArray(u32, this.id);
+ try writer.writeValue(this.list);
+}
- /// manifest
- manifest: DependencyManifest,
+};
- pub fn decode(reader: anytype) anyerror!WebsocketMessageManifestSuccess {
- var this = std.mem.zeroes(WebsocketMessageManifestSuccess);
+pub const WebsocketCommandResolveIDs = struct {
+/// ptrs
+ptrs: []const StringPointer,
- this.id = try reader.readValue(u32);
- this.module_path = try reader.readValue([]const u8);
- this.loader = try reader.readValue(Loader);
- this.manifest = try reader.readValue(DependencyManifest);
- return this;
- }
+/// files
+files: []const u8,
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeInt(this.id);
- try writer.writeValue(this.module_path);
- try writer.writeEnum(this.loader);
- try writer.writeValue(this.manifest);
- }
- };
- pub const WebsocketMessageManifestFailure = struct {
- /// id
- id: u32 = 0,
+pub fn decode(reader: anytype) anyerror!WebsocketCommandResolveIDs {
+ var this = std.mem.zeroes(WebsocketCommandResolveIDs);
- /// from_timestamp
- from_timestamp: u32 = 0,
+ this.ptrs = try reader.readArray(StringPointer);
+ this.files = try reader.readValue([]const u8);
+ return this;
+}
- /// loader
- loader: Loader,
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeArray(StringPointer, this.ptrs);
+ try writer.writeValue(this.files);
+}
- /// log
- log: Log,
+};
- pub fn decode(reader: anytype) anyerror!WebsocketMessageManifestFailure {
- var this = std.mem.zeroes(WebsocketMessageManifestFailure);
+pub const WebsocketMessageManifestSuccess = struct {
+/// id
+id: u32 = 0,
+
+/// module_path
+module_path: []const u8,
+
+/// loader
+loader: Loader,
+
+/// manifest
+manifest: DependencyManifest,
+
+
+pub fn decode(reader: anytype) anyerror!WebsocketMessageManifestSuccess {
+ var this = std.mem.zeroes(WebsocketMessageManifestSuccess);
+
+ this.id = try reader.readValue(u32);
+ this.module_path = try reader.readValue([]const u8);
+ this.loader = try reader.readValue(Loader);
+ this.manifest = try reader.readValue(DependencyManifest);
+ return this;
+}
+
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeInt(this.id);
+ try writer.writeValue(this.module_path);
+ try writer.writeEnum(this.loader);
+ try writer.writeValue(this.manifest);
+}
+
+};
+
+pub const WebsocketMessageManifestFailure = struct {
+/// id
+id: u32 = 0,
+
+/// from_timestamp
+from_timestamp: u32 = 0,
+
+/// loader
+loader: Loader,
+
+/// log
+log: Log,
+
+
+pub fn decode(reader: anytype) anyerror!WebsocketMessageManifestFailure {
+ var this = std.mem.zeroes(WebsocketMessageManifestFailure);
+
+ this.id = try reader.readValue(u32);
+ this.from_timestamp = try reader.readValue(u32);
+ this.loader = try reader.readValue(Loader);
+ this.log = try reader.readValue(Log);
+ return this;
+}
+
+pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
+ try writer.writeInt(this.id);
+ try writer.writeInt(this.from_timestamp);
+ try writer.writeEnum(this.loader);
+ try writer.writeValue(this.log);
+}
+
+};
- this.id = try reader.readValue(u32);
- this.from_timestamp = try reader.readValue(u32);
- this.loader = try reader.readValue(Loader);
- this.log = try reader.readValue(Log);
- return this;
- }
- pub fn encode(this: *const @This(), writer: anytype) anyerror!void {
- try writer.writeInt(this.id);
- try writer.writeInt(this.from_timestamp);
- try writer.writeEnum(this.loader);
- try writer.writeValue(this.log);
- }
- };
};
+
const ExamplePackedStruct = packed struct {
len: u32 = 0,
offset: u32 = 0,
diff --git a/src/bundler.zig b/src/bundler.zig
index 87c34a5ff..143c57c50 100644
--- a/src/bundler.zig
+++ b/src/bundler.zig
@@ -131,7 +131,7 @@ pub const ScanResult = struct {
pub fn NewBundler(cache_files: bool) type {
return struct {
- const Linker = if (cache_files) linker.Linker else linker.ServeLinker;
+ pub const Linker = if (cache_files) linker.Linker else linker.ServeLinker;
pub const Resolver = if (cache_files) _resolver.Resolver else _resolver.ResolverUncached;
const ThisBundler = @This();
@@ -164,8 +164,6 @@ pub fn NewBundler(cache_files: bool) type {
) !ThisBundler {
js_ast.Expr.Data.Store.create(allocator);
js_ast.Stmt.Data.Store.create(allocator);
- js_ast.Expr.Data.Store.reset();
- js_ast.Stmt.Data.Store.reset();
var fs = try Fs.FileSystem.init1(allocator, opts.absolute_working_dir, opts.serve orelse false);
const bundle_options = try options.BundleOptions.fromApi(
allocator,
@@ -941,7 +939,14 @@ pub fn NewBundler(cache_files: bool) type {
};
},
else => {
- var result = bundler.parse(allocator, file_path, loader, resolve_result.dirname_fd, file_descriptor, filepath_hash) orelse {
+ var result = bundler.parse(
+ allocator,
+ file_path,
+ loader,
+ resolve_result.dirname_fd,
+ file_descriptor,
+ filepath_hash,
+ ) orelse {
bundler.resetStore();
return BuildResolveResultPair{
.written = 0,
@@ -1241,9 +1246,9 @@ pub fn NewBundler(cache_files: bool) type {
jsx.parse = loader.isJSX();
var opts = js_parser.Parser.Options.init(jsx, loader);
opts.enable_bundling = false;
- opts.transform_require_to_import = true;
+ opts.transform_require_to_import = bundler.options.platform != .speedy;
opts.can_import_from_bundle = bundler.options.node_modules_bundle != null;
- opts.features.hot_module_reloading = bundler.options.hot_module_reloading;
+ opts.features.hot_module_reloading = bundler.options.hot_module_reloading and bundler.options.platform != .speedy;
opts.features.react_fast_refresh = opts.features.hot_module_reloading and jsx.parse and bundler.options.jsx.supports_fast_refresh;
opts.filepath_hash_for_hmr = file_hash orelse 0;
const value = (bundler.resolver.caches.js.parse(allocator, opts, bundler.options.define, bundler.log, &source) catch null) orelse return null;
diff --git a/src/cli.zig b/src/cli.zig
index f5d3ed4c0..0471b4e07 100644
--- a/src/cli.zig
+++ b/src/cli.zig
@@ -1,4 +1,4 @@
-usingnamespace @import("global.zig");
+ usingnamespace @import("global.zig");
usingnamespace @import("./http.zig");
const std = @import("std");
diff --git a/src/hash_map.zig b/src/hash_map.zig
index e625ff83c..853ad39be 100644
--- a/src/hash_map.zig
+++ b/src/hash_map.zig
@@ -234,6 +234,13 @@ pub fn HashMap(
return self.unmanaged.putAssumeCapacityNoClobber(key, value);
}
+ /// Asserts there is enough capacity to store the new key-value pair.
+ /// Asserts that it does not clobber any existing data.
+ /// To detect if a put would clobber existing data, see `getOrPutAssumeCapacity`.
+ pub fn putAssumeCapacityNoClobberWithHash(self: *Self, key: K, hash: u64, value: V) void {
+ return self.unmanaged.putAssumeCapacityNoClobberWithHash(key, hash, value);
+ }
+
/// Inserts a new `Entry` into the hash map, returning the previous one, if any.
pub fn fetchPut(self: *Self, key: K, value: V) !?Entry {
return self.unmanaged.fetchPut(self.allocator, key, value);
@@ -537,6 +544,12 @@ pub fn HashMapUnmanaged(
assert(!self.contains(key));
const hash = hashFn(key);
+ putAssumeCapacityNoClobberWithHash(self, key, hash, value);
+ }
+
+ /// Insert an entry in the map. Assumes it is not already present,
+ /// and that no allocation is needed.
+ pub fn putAssumeCapacityNoClobberWithHash(self: *Self, key: K, hash: u64, value: V) void {
const mask = self.capacity() - 1;
var idx = @truncate(usize, hash & mask);
diff --git a/src/javascript/jsc/JavascriptCore.zig b/src/javascript/jsc/JavascriptCore.zig
index 1d5806fce..e1bab65b8 100644
--- a/src/javascript/jsc/JavascriptCore.zig
+++ b/src/javascript/jsc/JavascriptCore.zig
@@ -1,19 +1,21 @@
+const generic = opaque {};
+pub const Private = c_void;
pub const struct_OpaqueJSContextGroup = opaque {};
pub const JSContextGroupRef = ?*const struct_OpaqueJSContextGroup;
pub const struct_OpaqueJSContext = opaque {};
pub const JSContextRef = ?*const struct_OpaqueJSContext;
pub const JSGlobalContextRef = ?*struct_OpaqueJSContext;
-pub const struct_OpaqueJSString = opaque {};
+pub const struct_OpaqueJSString = generic;
pub const JSStringRef = ?*struct_OpaqueJSString;
-pub const struct_OpaqueJSClass = opaque {};
+pub const struct_OpaqueJSClass = generic;
pub const JSClassRef = ?*struct_OpaqueJSClass;
-pub const struct_OpaqueJSPropertyNameArray = opaque {};
+pub const struct_OpaqueJSPropertyNameArray = generic;
pub const JSPropertyNameArrayRef = ?*struct_OpaqueJSPropertyNameArray;
-pub const struct_OpaqueJSPropertyNameAccumulator = opaque {};
+pub const struct_OpaqueJSPropertyNameAccumulator = generic;
pub const JSPropertyNameAccumulatorRef = ?*struct_OpaqueJSPropertyNameAccumulator;
pub const JSTypedArrayBytesDeallocator = ?fn (?*c_void, ?*c_void) callconv(.C) void;
-pub const struct_OpaqueJSValue = opaque {};
-pub const JSValueRef = ?*const struct_OpaqueJSValue;
+pub const struct_OpaqueJSValue = generic;
+pub const JSValueRef = ?*struct_OpaqueJSValue;
pub const JSObjectRef = ?*struct_OpaqueJSValue;
pub extern fn JSEvaluateScript(ctx: JSContextRef, script: JSStringRef, thisObject: JSObjectRef, sourceURL: JSStringRef, startingLineNumber: c_int, exception: [*c]JSValueRef) JSValueRef;
pub extern fn JSCheckScriptSyntax(ctx: JSContextRef, script: JSStringRef, sourceURL: JSStringRef, startingLineNumber: c_int, exception: [*c]JSValueRef) bool;
@@ -115,7 +117,15 @@ pub const JSObjectGetPropertyCallback = ?fn (JSContextRef, JSObjectRef, JSString
pub const JSObjectSetPropertyCallback = ?fn (JSContextRef, JSObjectRef, JSStringRef, JSValueRef, [*c]JSValueRef) callconv(.C) bool;
pub const JSObjectDeletePropertyCallback = ?fn (JSContextRef, JSObjectRef, JSStringRef, [*c]JSValueRef) callconv(.C) bool;
pub const JSObjectGetPropertyNamesCallback = ?fn (JSContextRef, JSObjectRef, JSPropertyNameAccumulatorRef) callconv(.C) void;
-pub const JSObjectCallAsFunctionCallback = ?fn (ctx: JSContextRef, function: JSObjectRef, thisObject: JSObjectRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) callconv(.C) JSValueRef;
+
+pub const JSObjectCallAsFunctionCallback = ?fn (
+ ctx: JSContextRef,
+ function: JSObjectRef,
+ thisObject: JSObjectRef,
+ argumentCount: usize,
+ arguments: [*c]const JSValueRef,
+ exception: [*c]JSValueRef,
+) callconv(.C) JSValueRef;
pub const JSObjectCallAsConstructorCallback = ?fn (JSContextRef, JSObjectRef, usize, [*c]const JSValueRef, [*c]JSValueRef) callconv(.C) JSObjectRef;
pub const JSObjectHasInstanceCallback = ?fn (JSContextRef, JSObjectRef, JSValueRef, [*c]JSValueRef) callconv(.C) bool;
pub const JSObjectConvertToTypeCallback = ?fn (JSContextRef, JSObjectRef, JSType, [*c]JSValueRef) callconv(.C) JSValueRef;
@@ -150,54 +160,54 @@ pub const JSClassDefinition = extern struct {
convertToType: JSObjectConvertToTypeCallback,
};
pub extern const kJSClassDefinitionEmpty: JSClassDefinition;
-pub extern fn JSClassCreate(definition: [*c]const JSClassDefinition) JSClassRef;
-pub extern fn JSClassRetain(jsClass: JSClassRef) JSClassRef;
-pub extern fn JSClassRelease(jsClass: JSClassRef) void;
-pub extern fn JSObjectMake(ctx: JSContextRef, jsClass: JSClassRef, data: ?*c_void) JSObjectRef;
-pub extern fn JSObjectMakeFunctionWithCallback(ctx: JSContextRef, name: JSStringRef, callAsFunction: JSObjectCallAsFunctionCallback) JSObjectRef;
-pub extern fn JSObjectMakeConstructor(ctx: JSContextRef, jsClass: JSClassRef, callAsConstructor: JSObjectCallAsConstructorCallback) JSObjectRef;
-pub extern fn JSObjectMakeArray(ctx: JSContextRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSObjectRef;
-pub extern fn JSObjectMakeDate(ctx: JSContextRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSObjectRef;
-pub extern fn JSObjectMakeError(ctx: JSContextRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSObjectRef;
-pub extern fn JSObjectMakeRegExp(ctx: JSContextRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSObjectRef;
-pub extern fn JSObjectMakeDeferredPromise(ctx: JSContextRef, resolve: [*c]JSObjectRef, reject: [*c]JSObjectRef, exception: [*c]JSValueRef) JSObjectRef;
-pub extern fn JSObjectMakeFunction(ctx: JSContextRef, name: JSStringRef, parameterCount: c_uint, parameterNames: [*c]const JSStringRef, body: JSStringRef, sourceURL: JSStringRef, startingLineNumber: c_int, exception: [*c]JSValueRef) JSObjectRef;
-pub extern fn JSObjectGetPrototype(ctx: JSContextRef, object: JSObjectRef) JSValueRef;
-pub extern fn JSObjectSetPrototype(ctx: JSContextRef, object: JSObjectRef, value: JSValueRef) void;
-pub extern fn JSObjectHasProperty(ctx: JSContextRef, object: JSObjectRef, propertyName: JSStringRef) bool;
-pub extern fn JSObjectGetProperty(ctx: JSContextRef, object: JSObjectRef, propertyName: JSStringRef, exception: [*c]JSValueRef) JSValueRef;
-pub extern fn JSObjectSetProperty(ctx: JSContextRef, object: JSObjectRef, propertyName: JSStringRef, value: JSValueRef, attributes: JSPropertyAttributes, exception: [*c]JSValueRef) void;
-pub extern fn JSObjectDeleteProperty(ctx: JSContextRef, object: JSObjectRef, propertyName: JSStringRef, exception: [*c]JSValueRef) bool;
-pub extern fn JSObjectHasPropertyForKey(ctx: JSContextRef, object: JSObjectRef, propertyKey: JSValueRef, exception: [*c]JSValueRef) bool;
-pub extern fn JSObjectGetPropertyForKey(ctx: JSContextRef, object: JSObjectRef, propertyKey: JSValueRef, exception: [*c]JSValueRef) JSValueRef;
-pub extern fn JSObjectSetPropertyForKey(ctx: JSContextRef, object: JSObjectRef, propertyKey: JSValueRef, value: JSValueRef, attributes: JSPropertyAttributes, exception: [*c]JSValueRef) void;
-pub extern fn JSObjectDeletePropertyForKey(ctx: JSContextRef, object: JSObjectRef, propertyKey: JSValueRef, exception: [*c]JSValueRef) bool;
-pub extern fn JSObjectGetPropertyAtIndex(ctx: JSContextRef, object: JSObjectRef, propertyIndex: c_uint, exception: [*c]JSValueRef) JSValueRef;
-pub extern fn JSObjectSetPropertyAtIndex(ctx: JSContextRef, object: JSObjectRef, propertyIndex: c_uint, value: JSValueRef, exception: [*c]JSValueRef) void;
-pub extern fn JSObjectGetPrivate(object: JSObjectRef) ?*c_void;
-pub extern fn JSObjectSetPrivate(object: JSObjectRef, data: ?*c_void) bool;
-pub extern fn JSObjectIsFunction(ctx: JSContextRef, object: JSObjectRef) bool;
-pub extern fn JSObjectCallAsFunction(ctx: JSContextRef, object: JSObjectRef, thisObject: JSObjectRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSValueRef;
-pub extern fn JSObjectIsConstructor(ctx: JSContextRef, object: JSObjectRef) bool;
-pub extern fn JSObjectCallAsConstructor(ctx: JSContextRef, object: JSObjectRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSObjectRef;
-pub extern fn JSObjectCopyPropertyNames(ctx: JSContextRef, object: JSObjectRef) JSPropertyNameArrayRef;
-pub extern fn JSPropertyNameArrayRetain(array: JSPropertyNameArrayRef) JSPropertyNameArrayRef;
-pub extern fn JSPropertyNameArrayRelease(array: JSPropertyNameArrayRef) void;
-pub extern fn JSPropertyNameArrayGetCount(array: JSPropertyNameArrayRef) usize;
-pub extern fn JSPropertyNameArrayGetNameAtIndex(array: JSPropertyNameArrayRef, index: usize) JSStringRef;
-pub extern fn JSPropertyNameAccumulatorAddName(accumulator: JSPropertyNameAccumulatorRef, propertyName: JSStringRef) void;
-pub extern fn JSContextGroupCreate() JSContextGroupRef;
-pub extern fn JSContextGroupRetain(group: JSContextGroupRef) JSContextGroupRef;
-pub extern fn JSContextGroupRelease(group: JSContextGroupRef) void;
-pub extern fn JSGlobalContextCreate(globalObjectClass: JSClassRef) JSGlobalContextRef;
-pub extern fn JSGlobalContextCreateInGroup(group: JSContextGroupRef, globalObjectClass: JSClassRef) JSGlobalContextRef;
-pub extern fn JSGlobalContextRetain(ctx: JSGlobalContextRef) JSGlobalContextRef;
-pub extern fn JSGlobalContextRelease(ctx: JSGlobalContextRef) void;
-pub extern fn JSContextGetGlobalObject(ctx: JSContextRef) JSObjectRef;
-pub extern fn JSContextGetGroup(ctx: JSContextRef) JSContextGroupRef;
-pub extern fn JSContextGetGlobalContext(ctx: JSContextRef) JSGlobalContextRef;
-pub extern fn JSGlobalContextCopyName(ctx: JSGlobalContextRef) JSStringRef;
-pub extern fn JSGlobalContextSetName(ctx: JSGlobalContextRef, name: JSStringRef) void;
+pub extern "c" fn JSClassCreate(definition: [*c]const JSClassDefinition) JSClassRef;
+pub extern "c" fn JSClassRetain(jsClass: JSClassRef) JSClassRef;
+pub extern "c" fn JSClassRelease(jsClass: JSClassRef) void;
+pub extern "c" fn JSObjectMake(ctx: JSContextRef, jsClass: JSClassRef, data: ?*c_void) JSObjectRef;
+pub extern "c" fn JSObjectMakeFunctionWithCallback(ctx: JSContextRef, name: JSStringRef, callAsFunction: JSObjectCallAsFunctionCallback) JSObjectRef;
+pub extern "c" fn JSObjectMakeConstructor(ctx: JSContextRef, jsClass: JSClassRef, callAsConstructor: JSObjectCallAsConstructorCallback) JSObjectRef;
+pub extern "c" fn JSObjectMakeArray(ctx: JSContextRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSObjectRef;
+pub extern "c" fn JSObjectMakeDate(ctx: JSContextRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSObjectRef;
+pub extern "c" fn JSObjectMakeError(ctx: JSContextRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSObjectRef;
+pub extern "c" fn JSObjectMakeRegExp(ctx: JSContextRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSObjectRef;
+pub extern "c" fn JSObjectMakeDeferredPromise(ctx: JSContextRef, resolve: [*c]JSObjectRef, reject: [*c]JSObjectRef, exception: [*c]JSValueRef) JSObjectRef;
+pub extern "c" fn JSObjectMakeFunction(ctx: JSContextRef, name: JSStringRef, parameterCount: c_uint, parameterNames: [*c]const JSStringRef, body: JSStringRef, sourceURL: JSStringRef, startingLineNumber: c_int, exception: [*c]JSValueRef) JSObjectRef;
+pub extern "c" fn JSObjectGetPrototype(ctx: JSContextRef, object: JSObjectRef) JSValueRef;
+pub extern "c" fn JSObjectSetPrototype(ctx: JSContextRef, object: JSObjectRef, value: JSValueRef) void;
+pub extern "c" fn JSObjectHasProperty(ctx: JSContextRef, object: JSObjectRef, propertyName: JSStringRef) bool;
+pub extern "c" fn JSObjectGetProperty(ctx: JSContextRef, object: JSObjectRef, propertyName: JSStringRef, exception: [*c]JSValueRef) JSValueRef;
+pub extern "c" fn JSObjectSetProperty(ctx: JSContextRef, object: JSObjectRef, propertyName: JSStringRef, value: JSValueRef, attributes: c_uint, exception: [*c]JSValueRef) void;
+pub extern "c" fn JSObjectDeleteProperty(ctx: JSContextRef, object: JSObjectRef, propertyName: JSStringRef, exception: [*c]JSValueRef) bool;
+pub extern "c" fn JSObjectHasPropertyForKey(ctx: JSContextRef, object: JSObjectRef, propertyKey: JSValueRef, exception: [*c]JSValueRef) bool;
+pub extern "c" fn JSObjectGetPropertyForKey(ctx: JSContextRef, object: JSObjectRef, propertyKey: JSValueRef, exception: [*c]JSValueRef) JSValueRef;
+pub extern "c" fn JSObjectSetPropertyForKey(ctx: JSContextRef, object: JSObjectRef, propertyKey: JSValueRef, value: JSValueRef, attributes: JSPropertyAttributes, exception: [*c]JSValueRef) void;
+pub extern "c" fn JSObjectDeletePropertyForKey(ctx: JSContextRef, object: JSObjectRef, propertyKey: JSValueRef, exception: [*c]JSValueRef) bool;
+pub extern "c" fn JSObjectGetPropertyAtIndex(ctx: JSContextRef, object: JSObjectRef, propertyIndex: c_uint, exception: [*c]JSValueRef) JSValueRef;
+pub extern "c" fn JSObjectSetPropertyAtIndex(ctx: JSContextRef, object: JSObjectRef, propertyIndex: c_uint, value: JSValueRef, exception: [*c]JSValueRef) void;
+pub extern "c" fn JSObjectGetPrivate(object: JSObjectRef) ?*c_void;
+pub extern "c" fn JSObjectSetPrivate(object: JSObjectRef, data: ?*c_void) bool;
+pub extern "c" fn JSObjectIsFunction(ctx: JSContextRef, object: JSObjectRef) bool;
+pub extern "c" fn JSObjectCallAsFunction(ctx: JSContextRef, object: JSObjectRef, thisObject: JSObjectRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSValueRef;
+pub extern "c" fn JSObjectIsConstructor(ctx: JSContextRef, object: JSObjectRef) bool;
+pub extern "c" fn JSObjectCallAsConstructor(ctx: JSContextRef, object: JSObjectRef, argumentCount: usize, arguments: [*c]const JSValueRef, exception: [*c]JSValueRef) JSObjectRef;
+pub extern "c" fn JSObjectCopyPropertyNames(ctx: JSContextRef, object: JSObjectRef) JSPropertyNameArrayRef;
+pub extern "c" fn JSPropertyNameArrayRetain(array: JSPropertyNameArrayRef) JSPropertyNameArrayRef;
+pub extern "c" fn JSPropertyNameArrayRelease(array: JSPropertyNameArrayRef) void;
+pub extern "c" fn JSPropertyNameArrayGetCount(array: JSPropertyNameArrayRef) usize;
+pub extern "c" fn JSPropertyNameArrayGetNameAtIndex(array: JSPropertyNameArrayRef, index: usize) JSStringRef;
+pub extern "c" fn JSPropertyNameAccumulatorAddName(accumulator: JSPropertyNameAccumulatorRef, propertyName: JSStringRef) void;
+pub extern "c" fn JSContextGroupCreate() JSContextGroupRef;
+pub extern "c" fn JSContextGroupRetain(group: JSContextGroupRef) JSContextGroupRef;
+pub extern "c" fn JSContextGroupRelease(group: JSContextGroupRef) void;
+pub extern "c" fn JSGlobalContextCreate(globalObjectClass: JSClassRef) JSGlobalContextRef;
+pub extern "c" fn JSGlobalContextCreateInGroup(group: JSContextGroupRef, globalObjectClass: JSClassRef) JSGlobalContextRef;
+pub extern "c" fn JSGlobalContextRetain(ctx: JSGlobalContextRef) JSGlobalContextRef;
+pub extern "c" fn JSGlobalContextRelease(ctx: JSGlobalContextRef) void;
+pub extern "c" fn JSContextGetGlobalObject(ctx: JSContextRef) JSObjectRef;
+pub extern "c" fn JSContextGetGroup(ctx: JSContextRef) JSContextGroupRef;
+pub extern "c" fn JSContextGetGlobalContext(ctx: JSContextRef) JSGlobalContextRef;
+pub extern "c" fn JSGlobalContextCopyName(ctx: JSGlobalContextRef) JSStringRef;
+pub extern "c" fn JSGlobalContextSetName(ctx: JSGlobalContextRef, name: JSStringRef) void;
pub const JSChar = c_ushort;
pub extern fn JSStringCreateWithCharacters(chars: [*c]const JSChar, numChars: usize) JSStringRef;
pub extern fn JSStringCreateWithUTF8CString(string: [*c]const u8) JSStringRef;
@@ -235,4 +245,4 @@ pub const OpaqueJSValue = struct_OpaqueJSValue;
// StringImpl::createWithoutCopying
// https://github.com/WebKit/webkit/blob/main/Source/JavaScriptCore/API/JSStringRef.cpp#L62
pub extern fn JSStringCreateWithCharactersNoCopy(string: [*c]const JSChar, numChars: size_t) JSStringRef;
-
+const size_t = usize;
diff --git a/src/javascript/jsc/javascript.zig b/src/javascript/jsc/javascript.zig
index aff505f22..1b71c0197 100644
--- a/src/javascript/jsc/javascript.zig
+++ b/src/javascript/jsc/javascript.zig
@@ -3,10 +3,16 @@ const std = @import("std");
usingnamespace @import("../../global.zig");
const Fs = @import("../../fs.zig");
const resolver = @import("../../resolver/resolver.zig");
-const ast = @import("../../ast/base.zig");
+const ast = @import("../../import_record.zig");
const NodeModuleBundle = @import("../../node_module_bundle.zig").NodeModuleBundle;
const WTFString = @import("../../wtf_string_mutable.zig").WTFStringMutable;
const logger = @import("../../logger.zig");
+const Api = @import("../../api/schema.zig").Api;
+const options = @import("../../options.zig");
+const Bundler = @import("../../bundler.zig").ServeBundler;
+
+const hash_map = @import("../../hash_map.zig");
+
pub const ExportJavaScript = union(Tag) {
Module: *Module,
String: *String,
@@ -21,7 +27,7 @@ pub const ExportJavaScript = union(Tag) {
pub const ResolveFunctionType = fn (ctx: anytype, source_dir: string, import_path: string, import_kind: ast.ImportKind) anyerror!resolver.Result;
pub const TranspileFunctionType = fn (ctx: anytype, resolve_result: resolver.Result) anyerror![:0]const u8;
-
+const ExceptionValueRef = [*c]js.JSValueRef;
const JSStringMapContext = struct {
pub fn hash(self: @This(), s: js.JSStringRef) u64 {
return hashString(s);
@@ -35,61 +41,128 @@ pub fn JSStringMap(comptime V: type) type {
return std.HashMap(js.JSStringRef, V, JSStringMapContext, 60);
}
+pub fn configureTransformOptionsForSpeedy(allocator: *std.mem.Allocator, _args: Api.TransformOptions) !Api.TransformOptions {
+ var args = _args;
+
+ args.platform = Api.Platform.speedy;
+ args.serve = false;
+ args.write = false;
+ args.resolve = Api.ResolveMode.lazy;
+ args.generate_node_module_bundle = false;
+
+ // We inline process.env.* at bundle time but process.env is a proxy object which will otherwise return undefined.
+
+ var env_map = try getNodeEnvMap(allocator);
+ var env_count = env_map.count();
+
+ if (args.define) |def| {
+ for (def.keys) |key| {
+ env_count += @boolToInt((env_map.get(key) == null));
+ }
+ }
+ var needs_node_env = env._map.get("NODE_ENV") == null;
+
+ var needs_regenerate = args.define == null and env_count > 0;
+ if (args.define) |def| {
+ if (def.keys.len != env_count) {
+ needs_regenerate = true;
+ }
+ for (def.keys) |key| {
+ if (strings.eql(key, "process.env.NODE_ENV")) {
+ needs_node_env = false;
+ }
+ }
+ }
+
+ if (needs_regenerate) {
+ var new_list = try allocator.alloc([]u8, env_count * 2 + @boolToInt(needs_node_env) * 2);
+ var new_map = Api.StringMap{
+ .keys = new_list[0..env_count],
+ .values = new_list[env_count..],
+ };
+ var iter = env_map.iterator();
+
+ var last: usize = 0;
+ while (iter.next()) |entry| {
+ new_map.keys[last] = entry.key_ptr.*;
+ var value = entry.value_ptr.*;
+ if (value.len == 0 or value.len[0] != '"' or value.len[value.len - 1] != '"') {
+ value = try std.fmt.allocPrint(allocator, "\"{s}\"", .{value});
+ }
+ new_map.values[last] = value;
+ last += 1;
+ }
+
+ if (args.define) |def| {
+ var from_env = new_map.keys[0..last];
+
+ for (def.keys) |pre, i| {
+ if (env_map.get(pre) != null) {
+ for (from_env) |key, i| {
+ if (srings.eql(key, pre)) {
+ new_map.values[i] = def.values[i];
+ }
+ }
+ } else {
+ new_map.keys[last] = pre;
+ new_map.values[last] = def.values[i];
+ last += 1;
+ }
+ }
+ }
+
+ if (needs_node_env) {
+ new_map.keys[last] = options.DefaultUserDefines.NodeEnv.Key;
+ new_map.values[last] = options.DefaultUserDefines.NodeEnv.Value;
+ }
+ }
+
+ return args;
+}
+
// If you read JavascriptCore/API/JSVirtualMachine.mm - https://github.com/WebKit/WebKit/blob/acff93fb303baa670c055cb24c2bad08691a01a0/Source/JavaScriptCore/API/JSVirtualMachine.mm#L101
// We can see that it's sort of like std.mem.Allocator but for JSGlobalContextRef, to support Automatic Reference Counting
// Its unavailable on Linux
pub const VirtualMachine = struct {
- const RequireCacheType = std.AutoHashMap(u64, Module);
- ctx: js.JSGlobalContextRef,
+ const RequireCacheType = std.AutoHashMap(u32, Module);
+ root: js.JSGlobalContextRef,
+ ctx: js.JSGlobalContextRef = undefined,
group: js.JSContextGroupRef,
allocator: *std.mem.Allocator,
- transpile_ctx: *c_void = undefined,
- transpile: *TranspileFunctionType = undefined,
require_cache: RequireCacheType,
- resolve_: *ResolveFunctionType = undefined,
- resolve_ctx: *c_void = undefined,
node_modules: ?*NodeModuleBundle = null,
node_modules_ref: js.JSObjectRef = null,
- global: GlobalObject,
+ global: *GlobalObject,
+ bundler: Bundler,
+ log: *logger.Log,
- pub fn init(allocator: *std.mem.Allocator) !*VirtualMachine {
+ pub fn init(
+ allocator: *std.mem.Allocator,
+ _args: Api.TransformOptions,
+ ) !*VirtualMachine {
var group = js.JSContextGroupCreate();
var ctx = js.JSGlobalContextCreateInGroup(group, null);
-
- Properties.init();
+ var log = try allocator.create(logger.Log);
var vm = try allocator.create(VirtualMachine);
+ var global = try allocator.create(GlobalObject);
vm.* = .{
.allocator = allocator,
+ .bundler = try Bundler.init(allocator, log, try configureTransformOptionsForSpeedy(allocator, _args)),
.group = group,
- .ctx = ctx,
+ .root = ctx,
.require_cache = RequireCacheType.init(allocator),
- .global = undefined,
+ .global = global,
};
- vm.global = GlobalObject{ .vm = undefined };
- return vm;
- }
-
- pub fn setupGlobals(this: *VirtualMachine) void {}
+ Properties.init();
+ vm.bundler.configureLinker();
- pub fn resolve(
- this: *VirtualMachine,
- from: *const Module,
- to: string,
- ) !js.JSValueRef {
- return (try this.resolve_(this.resolve_ctx, from.path.dir, to, .require)) orelse return error.ModuleNotFound;
- }
- threadlocal var require_buf: [std.fs.MAX_PATH_BYTES]u8 = undefined;
+ global.* = GlobalObject{ .vm = vm };
+ try vm.global.boot();
+ vm.ctx = vm.global.ctx;
- // Assume bundle is already transpiled, so we skip transpiling in here.
- pub fn requireFromBundle(this: *VirtualMachine, import_path: string) !js.JSValueRef {}
+ Module.boot(vm);
- pub fn require(
- this: *VirtualMachine,
- module: *const Module,
- path_value: js.JSValueRef,
- ) !js.JSValueRef {
- var import_path = To.Zig.str(path_value, &require_buf);
- var resolve_result = try this.resolve(module, import_path);
+ return vm;
}
threadlocal var eval_buf: WTFString = undefined;
@@ -98,61 +171,46 @@ pub const VirtualMachine = struct {
pub fn evalUtf8(
this: *VirtualMachine,
path_text: string,
- contents: string,
+ contents: [:0]const u8,
) !js.JSValueRef {
- if (!eval_buf_loaded) {
- eval_buf = try WTFString.init(this.allocator, contents.len + path.text.len + 2);
- } else {
- eval_buf.reset();
- try eval_buf.growIfNeeded(contents.len + path.text.len + 2);
- }
- try eval_buf.append(contents);
- eval_buf.list.append(eval_buf.allocator, 0);
- var script_len = eval_buf.list.items.len;
- if (path_text.len > 0) {
- try eval_buf.append(path_text);
- eval_buf.list.append(eval_buf.allocator, 0);
- }
+ // if (!eval_buf_loaded) {
+ // eval_buf = try WTFString.init(this.allocator, contents.len + path_text.len);
+ // } else {
+ // eval_buf.reset();
+ // try eval_buf.growIfNeeded(contents.len + path_text.len);
+ // }
- var buf = eval_buf.toOwnedSliceLeaky();
- var script = js.JSStringCreateWithCharactersNoCopy(buf[0..script_len].ptr, script_len - 1);
- var sourceURL: js.JSStringRef = null;
+ // try eval_buf.append(contents);
+ // var script_len = eval_buf.list.items.len;
+ // if (path_text.len > 0) {
+ // try eval_buf.append(path_text);
+ // }
- if (path_text.len > 0) {
- sourceURL = js.JSStringCreateWithCharactersNoCopy(
- buf[script_len + 1 ..].ptr,
- buf[script_len + 1 ..].len - 1,
- );
- }
+ // var buf = eval_buf.toOwnedSliceLeaky();
+ // var script = js.JSStringCreateWithCharactersNoCopy(@as([*c]js.JSChar, buf[0..script_len].ptr), script_len);
+ // script = js.JSStringRetain(script);
+ // var sourceURL: js.JSStringRef = null;
- return js.JSEvaluateScript(
+ // if (path_text.len > 0) {
+ // sourceURL = js.JSStringCreateWithCharactersNoCopy(
+ // @as([*c]js.JSChar, buf[script_len + 1 ..].ptr),
+ // buf[script_len + 1 ..].len,
+ // );
+ // sourceURL = js.JSStringRetain(sourceURL);
+ // }
+ var exception: js.JSObjectRef = null;
+ var val = js.JSEvaluateScript(
this.ctx,
- script,
- js.JSValueMakeUndefined(this.ctx),
- sourceURL,
- 0,
+ js.JSStringCreateWithUTF8CString(contents.ptr),
+ this.global.ref,
null,
+ 0,
+ &exception,
);
- }
-};
-
-pub const BundleLoader = struct {
- bundle: *const NodeModuleBundle,
- allocator: *std.mem.Allocator,
- vm: *VirtualMachine,
- loaded: bool = false,
- ref: js.JSObjectRef = null,
- pub fn init(bundle: *const NodeModuleBundle, allocator: *std.mem.Allocator, vm: *VirtualMachine) BundleLoader {
- return BundleLoader{
- .bundle = bundle,
- .allocator = allocator,
- .vm = vm,
- };
+ return exception;
}
-
- pub fn loadBundle(this: *BundleLoader) !void {}
};
pub const To = struct {
@@ -171,12 +229,15 @@ pub const To = struct {
ctx: js.JSContextRef,
function: js.JSObjectRef,
thisObject: js.JSObjectRef,
- arguments: []js.JSValueRef,
- exception: [*c]js.JSValueRef,
+ arguments: []const js.JSValueRef,
+ exception: js.JSValueRef,
) js.JSValueRef,
) js.JSObjectRef {
- var function = js.JSObjectMakeFunctionWithCallback(ctx, name, Callback(ZigContextType, callback));
- js.JSObjectSetPrivate(function, @ptrCast(*c_void, zig));
+ var function = js.JSObjectMakeFunctionWithCallback(ctx, name, Callback(ZigContextType, callback).rfn);
+ js.JSObjectSetPrivate(
+ function,
+ @ptrCast(*c_void, @alignCast(@alignOf(*c_void), global)),
+ );
return function;
}
@@ -187,30 +248,37 @@ pub const To = struct {
ctx: js.JSContextRef,
function: js.JSObjectRef,
thisObject: js.JSObjectRef,
- arguments: []js.JSValueRef,
- exception: [*c]js.JSValueRef,
+ arguments: []const js.JSValueRef,
+ exception: js.JSValueRef,
) js.JSValueRef,
) type {
return struct {
- pub fn run(
+ pub fn rfn(
ctx: js.JSContextRef,
function: js.JSObjectRef,
thisObject: js.JSObjectRef,
argumentCount: usize,
arguments: [*c]const js.JSValueRef,
- exception: [*c]js.JSValueRef,
+ exception: ExceptionValueRef,
) callconv(.C) js.JSValueRef {
- var object_ptr = js.JSObjectGetPrivate(function) orelse {
+ var object_ptr_ = js.JSObjectGetPrivate(function);
+ if (object_ptr_ == null) {
+ object_ptr_ = js.JSObjectGetPrivate(thisObject);
+ }
+
+ if (object_ptr_ == null) {
return js.JSValueMakeUndefined(ctx);
- };
+ }
+
+ var object_ptr = object_ptr_.?;
return ctxfn(
- @intToPtr(ZigContextType, object_ptr),
+ @ptrCast(*ZigContextType, @alignCast(@alignOf(*ZigContextType), object_ptr)),
ctx,
function,
thisObject,
- arguments[0..argumentCount],
- exception,
+ if (arguments) |args| args[0..argumentCount] else &[_]js.JSValueRef{},
+ null,
);
}
};
@@ -237,6 +305,7 @@ pub const Properties = struct {
pub const exports = "exports";
pub const log = "log";
pub const debug = "debug";
+ pub const name = "name";
pub const info = "info";
pub const error_ = "error";
pub const warn = "warn";
@@ -246,38 +315,45 @@ pub const Properties = struct {
};
pub const UTF16 = struct {
- pub const module = std.unicode.utf8ToUtf16LeStringLiteral("module");
- pub const globalThis = std.unicode.utf8ToUtf16LeStringLiteral("globalThis");
- pub const exports = std.unicode.utf8ToUtf16LeStringLiteral("exports");
- pub const log = std.unicode.utf8ToUtf16LeStringLiteral("log");
- pub const debug = std.unicode.utf8ToUtf16LeStringLiteral("debug");
- pub const info = std.unicode.utf8ToUtf16LeStringLiteral("info");
- pub const error_ = std.unicode.utf8ToUtf16LeStringLiteral("error");
- pub const warn = std.unicode.utf8ToUtf16LeStringLiteral("warn");
- pub const console = std.unicode.utf8ToUtf16LeStringLiteral("console");
- pub const require = std.unicode.utf8ToUtf16LeStringLiteral("require");
- pub const description = std.unicode.utf8ToUtf16LeStringLiteral("description");
+ pub const module: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("module");
+ pub const globalThis: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("globalThis");
+ pub const exports: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("exports");
+ pub const log: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("log");
+ pub const debug: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("debug");
+ pub const info: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("info");
+ pub const error_: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("error");
+ pub const warn: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("warn");
+ pub const console: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("console");
+ pub const require: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("require");
+ pub const description: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("description");
+ pub const name: []c_ushort = std.unicode.utf8ToUtf16LeStringLiteral("name");
};
pub const Refs = struct {
- pub var module: js.JSStringRef = undefined;
- pub var globalThis: js.JSStringRef = undefined;
- pub var exports: js.JSStringRef = undefined;
- pub var log: js.JSStringRef = undefined;
- pub var debug: js.JSStringRef = undefined;
- pub var info: js.JSStringRef = undefined;
- pub var error_: js.JSStringRef = undefined;
- pub var warn: js.JSStringRef = undefined;
- pub var console: js.JSStringRef = undefined;
- pub var require: js.JSStringRef = undefined;
- pub var description: js.JSStringRef = undefined;
+ pub var module: js.JSStringRef = null;
+ pub var globalThis: js.JSStringRef = null;
+ pub var exports: js.JSStringRef = null;
+ pub var log: js.JSStringRef = null;
+ pub var debug: js.JSStringRef = null;
+ pub var info: js.JSStringRef = null;
+ pub var error_: js.JSStringRef = null;
+ pub var warn: js.JSStringRef = null;
+ pub var console: js.JSStringRef = null;
+ pub var require: js.JSStringRef = null;
+ pub var description: js.JSStringRef = null;
+ pub var name: js.JSStringRef = null;
};
pub fn init() void {
inline for (std.meta.fieldNames(UTF8)) |name| {
- @field(Refs, name) = js.JSStringCreateWithCharactersNoCopy(
- &@field(StringStore.UTF16, name),
- @field(StringStore.UTF16, name).len,
+ @field(Refs, name) = js.JSStringRetain(
+ js.JSStringCreateWithCharactersNoCopy(
+ @field(StringStore.UTF16, name).ptr,
+ @field(StringStore.UTF16, name).len - 1,
+ ),
+ );
+ std.debug.assert(
+ js.JSStringIsEqualToUTF8CString(@field(Refs, name), @field(UTF8, name)[0.. :0]),
);
}
}
@@ -291,7 +367,7 @@ pub const String = struct {
ref: js.JSStringRef,
len: usize,
- pub fn chars(this: *const String) []js.JSChar {
+ pub fn chars(this: *const String) []const js.JSChar {
return js.JSStringGetCharactersPtr(this.ref)[0..js.JSStringGetLength(this.ref)];
}
@@ -300,30 +376,571 @@ pub const String = struct {
}
};
+const GetterFn = fn (
+ this: anytype,
+ ctx: js.JSContextRef,
+ thisObject: js.JSValueRef,
+ prop: js.JSStringRef,
+ exception: [*c]JSValueRef,
+) js.JSValueRef;
+const SetterFn = fn (
+ this: anytype,
+ ctx: js.JSContextRef,
+ thisObject: js.JSValueRef,
+ prop: js.JSStringRef,
+ value: js.JSValueRef,
+ exception: [*c]JSValueRef,
+) js.JSValueRef;
+
+const JSProp = struct {
+ get: ?GetterFn = null,
+ set: ?SetterFn = null,
+ ro: bool = false,
+};
+
pub const Module = struct {
- path: Fs.PathName,
+ path: Fs.Path,
- require: RequireObject,
- hash: u64,
+ hashid: u32,
ref: js.JSObjectRef,
+ id: js.JSValueRef = null,
+ exports: js.JSValueRef = null,
+
+ global_ref: js.JSValueRef = null,
+
+ vm: *VirtualMachine,
+
+ pub var module_class: js.JSClassRef = undefined;
+ pub var module_global_class: js.JSClassRef = undefined;
+ pub var module_global_class_def: js.JSClassDefinition = undefined;
+ pub var module_class_def: js.JSClassDefinition = undefined;
+
+ pub const NodeModuleList = struct {
+ tempbuf: []u8,
+ property_names: [*]u8,
+ property_getters: []js.JSObjectRef,
+ module_property_map: ModuleIDMap,
+ node_module_global_class: js.JSClassRef,
+ node_module_global_class_def: js.JSClassDefinition,
+ bundle_ctx: js.JSGlobalContextRef,
+ vm: *VirtualMachine,
+
+ pub const Instance = struct {
+ module: Module,
+ ref: js.JSObjectRef,
+ ctx: js.JSGlobalContextRef,
+ node_module_list: *NodeModuleList,
+
+ const NodeModuleInstanceClassName = "NodeModule";
+ const ModuleLoadStaticFunctionName = "$$m";
+
+ var instance_class_definition: js.JSClassDefinition = undefined;
+
+ var instance_class_ref: js.JSClassRef = undefined;
+ var instance_class_loaded = false;
+
+ threadlocal var source_code_buffer: MutableString = undefined;
+ threadlocal var source_code_buffer_loaded = false;
+ pub fn evalBundledModule(
+ allocator: *std.mem.Allocator,
+ vm: *VirtualMachine,
+ node_module_list: *NodeModuleList,
+ ctx: js.JSContextRef,
+ id: u32,
+ ) !Instance {
+ const bundled_module = &vm.node_modules.?.bundle.modules[id];
+ if (!source_code_buffer_loaded) {
+ source_code_buffer = try MutableString.init(allocator, bundled_module.code.length + 1);
+ source_code_buffer_loaded = true;
+ } else {
+ source_code_buffer.reset();
+ source_code_buffer.growIfNeeded(bundled_module.code.length + 1);
+ }
+
+ var node_module_file = std.fs.File{ .handle = vm.node_modules.?.fd };
+ const read = try node_module_file.pread(source_code_buffer.list.items, bundled_module.code.offset);
+ source_code_buffer.list.items[read] = 0;
+ var buf = source_code_buffer.list.items[0..read :0];
+
+ const bundled_package = &vm.node_modules.?.bundle.packages[bundled_module.package_id];
+ // We want linear because we expect it to virtually always be at 0
+ // However, out of caution we check.
+ var start_at: usize = std.mem.indexOfPosLinear(u8, buf, 0, "export var $") orelse return error.FailedCorruptNodeModuleMissingExport;
+ start_at += "export var $".len;
+ start_at = std.mem.indexOfPosLinear(u8, "$$m(", start_at, buf) orelse return error.FailedCorruptNodeModuleMissingModuleWrapper;
+ var source_buf = source_code_buffer.list.items[start_at..read :0];
+ var source_string = js.JSStringCreateWithUTF8CString(source_buf.ptr);
+ defer js.JSStringRelease(source_string);
+ var source_url_buf = try std.fmt.allocPrintZ(
+ allocator,
+ "node_modules.jsb/{s}/{s}",
+ .{
+ vm.node_modules.?.str(bundled_package.path),
+ vm.node_modules.?.str(bundled_module.path),
+ },
+ );
+ defer allocator.free(source_url_buf);
+ var source_url = js.JSStringCreateWithUTF8CString(source_url_buf);
+ defer js.JSStringRelease(source_url);
+ var exception: js.JSValueRef = null;
+ var return_value = js.JSEvaluateScript(node_module_list.bundle_ctx, source_string, null, source_url, 1, &exception);
+ if (exception != null) {
+ var message = js.JSValueToStringCopy(node_module_list.bundle_ctx, exception.?, null);
+ defer js.JSStringRelease(message);
+ var message_str_size = js.JSStringGetMaximumUTF8CStringSize(message);
+ var message_str_buf = try allocator.alloc(u8, message_str_size);
+ defer allocator.free(message_str_buf);
+ var message_str_read = js.JSStringGetUTF8CString(message, message_str_buf, message_str_size);
+ defer Output.flush();
+ Output.prettyErrorln("<r>{s}\n--<r><red>error<r> loading <cyan>\"{s}/{s}\"<r>--", .{
+ message_str_buf[0..message_str_read],
+ vm.node_modules.?.str(bundled_package.name),
+ vm.node_modules.?.str(bundled_module.path),
+ });
+ return error.FailedException;
+ }
+
+
+
+
+
+
+
+ if (!js.JSValueIsObject(node_module_list.bundle_ctx, return_value) or js.JSObjectGetPrivate(return_value) == null) {
+ Output.prettyErrorln(
+ \\\<r><red>Failed<r> to load <cyan>"{s}/{s}"<r>.\n
+ \\This is an internal error. Every module in node_modules.jsb is expected to call a function
+ \\initializing the module on load, and that function is supposed to return an object.
+ \\It didn't return an object.
+ \\That doesn't mean there was a syntax error (syntax errors occur earlier).
+ \\If you weren't poking around in node_modules.jsb (or messing with object prototypes),
+ \\please file an issue and include your node_modules.jsb.
+ , .{
+ vm.node_modules.?.str(bundled_package.name),
+ vm.node_modules.?.str(bundled_module.path),
+ });
+ Output.flush();
+ return error.FailedReturnValueInvalid;
+ }
+
+
+
+
+
+
+
+
+ }
+ };
+
+ pub const RequireBundledModule = struct {
+ id: u32,
+ list: *NodeModuleList,
+ };
+
+ // key: hash of module.path
+ // value: index of module
+ const ModuleIDMap = hash_map.AutoHashMap(u64, u32);
+
+ pub fn initializeGlobal(ctx: JSContextRef, obj: JSObjectRef) callconv(.C) void {}
+
+ pub fn getRequireFromBundleProperty(ctx: js.JSContextRef, thisObject: js.JSObjectRef, prop: js.JSStringRef, exception: [*c]js.JSValueRef) js.JSValueRef {
+ var thisPtr = js.JSObjectGetPrivate(thisObject);
+ if (thisPtr == null) return null;
+
+ var this = @ptrCast(
+ *NodeModuleList,
+ @alignCast(
+ @alignOf(
+ *NodeModuleList,
+ ),
+ thisPtr.?,
+ ),
+ );
+
+ const size = js.JSStringGetUTF8CString(prop, this.tempbuf.ptr, this.tempbuf.len);
+ const key = std.hash.Wyhash.hash(0, this.tempbuf[0..size]);
+ const id = this.module_property_map.get(id) orelse return null;
+
+ if (this.property_getters[id] == null) {
+ var require_bundled = try this.vm.allocator.create(RequireBundledModule);
+ require_bundled.* = RequireBundledModule{ .id = id, .list = this };
+ this.property_getters[id] = To.JS.functionWithCallback(
+ RequireBundledModule,
+ require_bundled,
+ prop,
+ ctx,
+ requireBundledModule,
+ );
+ }
+
+ return this.property_getters[id];
+ }
+
+ // this is what $aosdi123() inside a node_modules.jsb calls
+ pub fn requireBundledModule(
+ obj: *const RequireBundledModule,
+ ctx: js.JSContextRef,
+ function: js.JSObjectRef,
+ thisObject: js.JSObjectRef,
+ arguments: []const js.JSValueRef,
+ exception: [*c]js.JSValueRef,
+ ) js.JSValueRef {
+ const bundle = &obj.list.vm.node_modules.?.bundle;
+ const bundled_module = &bundle.modules[obj.id];
+ const bundled_pkg = &bundle.packages[bundled_module.package_id];
+
+ const result = loadBundledModuleById(obj.list.vm, ctx, obj.id) catch |err| {
+ Output.prettyErrorln("<r><red>RequireError<r>: <b>{s}<r> in \"<cyan>{s}/{s}<r>\"", .{
+ @errorName(err),
+ obj.list.vm.node_modules.?.str(bundled_pkg.name),
+ obj.list.vm.node_modules.?.str(bundled_module.path),
+ });
+ var message = std.fmt.allocPrintZ(obj.list.vm.allocator, "RequireError: {s} in \"{s}/{s}\"", .{
+ @errorName(err),
+ obj.list.vm.node_modules.?.str(bundled_pkg.name),
+ obj.list.vm.node_modules.?.str(bundled_module.path),
+ }) catch unreachable;
+ defer Output.flush();
+ defer obj.list.vm.allocator.free(message);
+ var args = obj.list.vm.allocator.alloc(js.JSStringRef, 1) catch unreachable;
+ args[0] = js.JSStringCreateWithUTF8CString(message.ptr);
+ exception.* = js.JSObjectMakeError(ctx, 1, args, null);
+ return js.JSValueMakeUndefined(ctx);
+ };
+
+ return result.Module.internalGetExports();
+ }
+
+ pub fn init(vm: *VirtualMachine, ctx: js.JSContextRef, bundle: *const NodeModuleBundle) !NodeModuleList {
+ var size: usize = 0;
+ var longest_size: usize = 0;
+ for (bundle.bundle.modules) |module, i| {
+ var hasher = std.hash.Wyhash.init(0);
+ hasher.update(bundle.str(module.path));
+ hasher.update(
+ std.mem.asBytes(
+ &bundle.bundle.packages[module.package_id].hash,
+ ),
+ );
+ // Add one for null-terminated string offset
+ const this_size = std.fmt.count(
+ "${x}",
+ .{
+ @truncate(
+ u32,
+ hasher.final(),
+ ),
+ },
+ ) + 1;
+ size += this_size;
+ longest_size = std.math.max(this_size, longest_size);
+ }
+ var static_properties = try vm.allocator.alloc(js.JSStaticValue, bundle.bundle.modules.len);
+ var utf8 = try vm.allocator.alloc(u8, size + longest_size);
+
+ var tempbuf = utf8[size..];
+
+ var names_buf = utf8[0..size];
+ var module_property_map = ModuleIDMap.init(vm.allocator);
+ try module_property_map.ensureCapacity(bundle.bundle.modules.len);
+
+ for (bundle.bundle.modules) |module, i| {
+ var hasher = std.hash.Wyhash.init(0);
+ hasher.update(bundle.str(module.path));
+ hasher.update(
+ std.mem.asBytes(
+ &bundle.bundle.packages[module.package_id].hash,
+ ),
+ );
+
+ const hash = @truncate(
+ u32,
+ hasher.final(),
+ );
+
+ // The variable name is the hash of the module path
+ var name = std.fmt.bufPrint(names_buf, "${x}", .{hash}) catch unreachable;
+
+ // But we don't store that for the hash map. Instead, we store the hash of name.
+ // This lets us avoid storing pointers to the name in the hash table, so if we free it later
+ // or something it won't cause issues.
+ hasher = std.hash.Wyhash.init(0);
+ hasher.update(name);
+ var property_key = hasher.final();
+
+ name.ptr[name.len] = 0;
+ const name_len = name.len;
+
+ static_properties[i] = js.JSStaticValue{
+ .name = name[0.. :0],
+ .getProperty = getRequireFromBundleProperty,
+ .attributes = .kJSPropertyAttributeReadOnly,
+ };
+ names_buf = names_buf[name_len..];
+ module_property_map.putAssumeCapacityNoClobberWithHash(property_key, property_key, @truncate(u32, i));
+ }
+
+ var node_module_global_class_def = js.kJSClassDefinitionEmpty;
+ node_module_global_class_def.staticValues = static_properties;
+ node_module_global_class_def.className = node_module_global_class_name[0.. :0];
+ node_module_global_class_def.parentClass = vm.global.global_class;
+
+ var property_getters = try vm.allocator.alloc(js.JSObjectRef, bundle.bundle.modules.len);
+ std.mem.set(js.JSObjectRef, property_getters, null);
+
+ return NodeModuleList{
+ .module_property_map = module_property_map,
+ .node_module_global_class_def = node_module_global_class_def,
+ .vm = vm,
+ .tempbuf = tempbuf,
+ .property_getters = property_getters,
+ .node_module_global_class = js.JSClassCreate(node_module_global_class_def),
+ };
+ }
+ };
+ pub const node_module_global_class_name = "NodeModuleGlobal";
+ pub const ModuleGlobalClass = NewClass(
+ Module,
+ "ModuleGlobal",
+ .{ .@"require" = require },
+ .{},
+ false,
+ false,
+ );
+
+ const JSExport = NewClass(
+ Module,
+ "Module",
+ .{ .@"require" = require },
+ .{
+ .@"id" = JSProp{
+ .get = getId,
+ .ro = true,
+ },
+ .@"exports" = JSProp{
+ .get = getExports,
+ .set = setExports,
+ .ro = false,
+ },
+ },
+ false,
+ false,
+ );
+
+ pub fn boot(vm: *VirtualMachine) void {
+ module_global_class_def = ModuleGlobalClass.define(vm.root);
+ module_global_class_def.parentClass = vm.global.global_class;
+ module_global_class = js.JSClassRetain(js.JSClassCreate(&module_global_class_def));
+ module_class_def = JSExport.define(vm.root);
+ module_class = js.JSClassRetain(js.JSClassCreate(&module_class_def));
+ }
+
+ pub const LoadResult = union(Tag) {
+ Module: *Module,
+ Path: Fs.Path,
+
+ pub const Tag = enum {
+ Module,
+ Path,
+ };
+ };
+
+ pub fn loadBundledModuleById(vm: *VirtualMachine, ctx: js.JSContextRef, id: u32) !LoadResult {}
+
+ pub fn loadFromResolveResult(vm: *VirtualMachine, ctx: js.JSContextRef, resolved: resolver.Result) !LoadResult {
+ var hash = @truncate(u32, std.hash.Wyhash.hash(0, resolved.path_pair.primary.text));
+ if (vm.require_cache.getPtr(hash)) |mod| {
+ return .{ .Module = mod };
+ }
+
+ const path = resolved.path_pair.primary;
+ const loader = vm.bundler.options.loaders.get(path.name.ext) orelse .file;
+ switch (loader) {
+ .js,
+ .jsx,
+ .ts,
+ .tsx,
+ .json,
+ => {
+ if (resolved.package_json) |package_json| {
+ if (package_json.hash > 0) {
+ if (vm.node_modules) |node_modules| {
+ if (node_modules.getPackageIDByHash(package_json.hash)) |package_id| {
+ const package_relative_path = vm.bundler.fs.relative(
+ package_json.source.path.name.dirWithTrailingSlash(),
+ path.text,
+ );
+
+ if (node_modules.findModuleInPackage(
+ &node_modules.bundle.packages[package_id],
+ package_relative_path,
+ )) |found_module| {}
+ }
+ }
+ }
+ }
+
+ vm.bundler.resetStore();
+ var result = vm.bundler.parse(
+ vm.bundler.allocator,
+ path,
+ loader,
+ result.dirname_fd,
+ null,
+ null,
+ ) orelse {
+ return error.ParseError;
+ };
+ },
+
+ // Replace imports to non-executables with paths to those files.
+ // In SSR or on web, these become URLs.
+ // Otherwise, absolute file paths.
+ else => {
+ switch (vm.bundler.options.import_path_format) {
+ .absolute_path => {
+ return LoadResult{ .Path = path };
+ },
+ .absolute_url => {
+ var fs = vm.bundler.fs;
+
+ var base = fs.relativeTo(path.text);
+ if (strings.lastIndexOfChar(base, '.')) |dot| {
+ base = base[0..dot];
+ }
+
+ var dirname = std.fs.path.dirname(base) orelse "";
+
+ var basename = std.fs.path.basename(base);
+
+ const needs_slash = dirname.len > 0 and dirname[dirname.len - 1] != '/';
+
+ if (needs_slash) {
+ const absolute_url = try std.fmt.allocPrint(
+ vm.allocator,
+ "{s}{s}/{s}{s}",
+ .{
+ vm.bundler.options.public_url,
+ dirname,
+ basename,
+ path.name.ext,
+ },
+ );
+
+ return LoadResult{
+ .Path = Fs.Path.initWithPretty(absolute_url, absolute_url),
+ };
+ } else {
+ const absolute_url = try std.fmt.allocPrint(
+ vm.allocator,
+ "{s}{s}{s}{s}",
+ .{
+ vm.bundler.options.public_url,
+ dirname,
+ basename,
+ path.name.ext,
+ },
+ );
+
+ return LoadResult{
+ .Path = Fs.Path.initWithPretty(absolute_url, absolute_url),
+ };
+ }
+ },
+ }
+ },
+ }
+ }
+
+ pub fn getId(
+ this: *Module,
+ ctx: js.JSContextRef,
+ thisObject: js.JSValueRef,
+ prop: js.JSStringRef,
+ exception: [*c]js.JSValueRef,
+ ) js.JSValueRef {
+ if (this.id == null) {
+ this.id = js.JSStringCreateWithUTF8CString(this.path.text[0.. :0]);
+ }
+
+ return this.id;
+ }
+
+ pub fn getExports(
+ this: *Module,
+ ctx: js.JSContextRef,
+ thisObject: js.JSValueRef,
+ prop: js.JSStringRef,
+ exception: [*c]js.JSValueRef,
+ ) js.JSValueRef {
+ return this.internalGetExports();
+ }
+
+ pub fn internalGetExports(this: *Module) js.JSValueRef {
+ if (this.exports == null) {
+ this.exports = js.JSObjectMake(ctx, null, null);
+ }
+
+ return this.exports;
+ }
+
+ pub fn setExports(
+ this: *Module,
+ ctx: js.JSContextRef,
+ thisObject: js.JSValueRef,
+ prop: js.JSStringRef,
+ value: js.JSValueRef,
+ exception: [*c]JSValueRef,
+ ) JSValueRef {
+ if (this.exports != null) {
+ if (js.JSValueIsString(this.exports.?)) {
+ js.JSStringRelease(this.exports.?);
+ }
+ }
+
+ this.exports = value;
+ }
+
pub const RequireObject = struct {};
pub fn require(
this: *Module,
- arguments: [*c]const js.JSValueRef,
- arguments_len: usize,
+ ctx: js.JSContextRef,
+ thisObject: js.JSValueRef,
+ arguments: []js.JSValueRef,
exception: [*c]JSValueRef,
- ) js.JSValueRef {}
+ ) js.JSValueRef {
+ if (arguments.len == 0 or arguments.len > 1 or !js.JSValueIsString(ctx, arguments[0]) or js.JSStringGetLength(arguments[0]) == 0) {
+ defer Output.flush();
+ if (arguments.len == 0) {
+ Output.prettyErrorln("<r><red>error<r>: <s><b>require<r> needs a string, e.g. require(\"left-pad\")", .{});
+ } else if (arguments.len > 1) {
+ Output.prettyErrorln("<r><red>error<r>: <s><b>require<r> only accepts one argument and it must be a string, e.g. require(\"left-pad\")", .{});
+ } else if (!js.JSValueIsString(ctx, arguments[0])) {
+ Output.prettyErrorln("<r><red>error<r>: <s><b>require<r> only supports a string, e.g. require(\"left-pad\")", .{});
+ } else {
+ Output.prettyErrorln("<r><red>error<r>: <s><b>require(\"\")<r> string cannot be empty.", .{});
+ }
+ exception.* = js.JSObjectMakeError(ctx, 0, null, null);
+ return null;
+ }
+ }
};
pub const GlobalObject = struct {
ref: js.JSObjectRef = undefined,
vm: *VirtualMachine,
- console: js.JSClassRef = undefined,
+ ctx: js.JSGlobalContextRef = undefined,
+ console_class: js.JSClassRef = undefined,
+ console: js.JSObjectRef = undefined,
console_definition: js.JSClassDefinition = undefined,
+ global_class_def: js.JSClassDefinition = undefined,
+ global_class: js.JSClassRef = undefined,
+ root_obj: js.JSObjectRef = undefined,
- pub const ConsoleClass = NewSingletonClass(
+ pub const ConsoleClass = NewClass(
GlobalObject,
"Console",
.{
@@ -335,15 +952,53 @@ pub const GlobalObject = struct {
.@"error" = stderr,
.@"warn" = stderr,
},
+ .{},
// people sometimes modify console.log, let them.
false,
+ true,
+ );
+
+ pub const GlobalClass = NewClass(
+ GlobalObject,
+ "Global",
+ .{},
+ .{
+ .@"console" = getConsole,
+ },
+ false,
+ false,
);
- pub fn load(global: *GlobalObject) !void {
- global.console_definition = ConsoleClass.define(global, global.vm.ctx);
- global.console = js.JSClassCreate(&global.console_definition);
+ pub fn getConsole(global: *GlobalObject, ctx: js.JSContextRef, obj: js.JSObjectRef, exception: ExceptionValueRef) js.JSValueRef {
+ return global.console;
}
+ pub fn onMissingProperty(global: *GlobalObject, ctx: js.JSContextRef, obj: js.JSObjectRef, prop: js.JSStringRef, exception: ExceptionValueRef) js.JSValueRef {
+ if (js.JSObjectHasProperty(ctx, global.root_obj, prop)) {
+ return js.JSObjectGetProperty(ctx, global.root_obj, prop, exception);
+ } else {
+ return js.JSValueMakeUndefined(ctx);
+ }
+ }
+
+ pub fn boot(global: *GlobalObject) !void {
+ var private: ?*c_void = global;
+ global.root_obj = js.JSContextGetGlobalObject(global.vm.root);
+
+ global.console_definition = ConsoleClass.define(global.vm.root);
+ global.console_class = js.JSClassRetain(js.JSClassCreate(&global.console_definition));
+ global.console = js.JSObjectMake(global.vm.root, global.console_class, private);
+
+ global.global_class_def = GlobalClass.define(global.vm.root);
+ global.global_class = js.JSClassRetain(js.JSClassCreate(&global.global_class_def));
+
+ global.ctx = js.JSGlobalContextRetain(js.JSGlobalContextCreateInGroup(global.vm.group, global.global_class));
+
+ std.debug.assert(js.JSObjectSetPrivate(js.JSContextGetGlobalObject(global.ctx), private));
+ global.ref = js.JSContextGetGlobalObject(global.ctx);
+ }
+
+ threadlocal var printer_buf: [4092]u8 = undefined;
fn valuePrinter(comptime ValueType: js.JSType, ctx: js.JSContextRef, arg: js.JSValueRef, writer: anytype) !void {
switch (ValueType) {
.kJSTypeUndefined => {
@@ -360,29 +1015,14 @@ pub const GlobalObject = struct {
}
},
.kJSTypeNumber => {
- try writer.print("{d}", js.JSValueToNumber(ctx, arg, null));
+ try writer.print(
+ "{d}",
+ .{js.JSValueToNumber(ctx, arg, null)},
+ );
},
.kJSTypeString => {
- var str = String{ .ref = @as(js.JSStringRef, arg) };
- var chars = str.chars();
- switch (chars.len) {
- 0 => {
- try writer.writeAll("\"\"");
- },
- else => {
- for (chars) |c, i| {
- switch (c) {
- 0...127 => {
- // Since we're writing character by character
- // it will be really slow if we check for an error every time
- _ = writer.write(@intCast(u8, c)) catch 0;
- },
- // TODO:
- else => {},
- }
- }
- },
- }
+ const used = js.JSStringGetUTF8CString(arg, (&printer_buf), printer_buf.len);
+ try writer.writeAll(printer_buf[0..used]);
},
.kJSTypeObject => {
// TODO:
@@ -391,8 +1031,8 @@ pub const GlobalObject = struct {
.kJSTypeSymbol => {
var description = js.JSObjectGetPropertyForKey(ctx, arg, Properties.Refs.description, null);
return switch (js.JSValueGetType(ctx, description)) {
- .kJSTypeString => try valuePrinter(.kJSTypeString, ctx, description, writer),
- else => try valuePrinter(.kJSTypeUndefined, ctx, description, writer),
+ .kJSTypeString => try valuePrinter(.kJSTypeString, ctx, js.JSStringRetain(description), writer),
+ else => try valuePrinter(.kJSTypeUndefined, ctx, js.JSStringRetain(description), writer),
};
},
else => {},
@@ -402,15 +1042,16 @@ pub const GlobalObject = struct {
fn output(
writer: anytype,
ctx: js.JSContextRef,
- arguments: []js.JSValueRef,
+ arguments: []const js.JSValueRef,
) !void {
defer Output.flush();
// console.log();
if (arguments.len == 0) {
- return js.JSValueMakeUndefined(ctx);
+ return;
}
const last = arguments.len - 1;
+ defer writer.writeAll("\n") catch {};
for (arguments) |arg, i| {
switch (js.JSValueGetType(ctx, arg)) {
@@ -459,8 +1100,6 @@ pub const GlobalObject = struct {
else => {},
}
}
-
- return js.JSValueMakeUndefined(ctx);
}
pub fn stdout(
@@ -468,9 +1107,11 @@ pub const GlobalObject = struct {
ctx: js.JSContextRef,
function: js.JSObjectRef,
thisObject: js.JSObjectRef,
- arguments: []js.JSValueRef,
+ arguments: []const js.JSValueRef,
+ exception: js.JSValueRef,
) js.JSValueRef {
- return try output(Output.writer(), ctx, arguments);
+ output(Output.writer(), ctx, arguments) catch {};
+ return js.JSValueMakeUndefined(ctx);
}
pub fn stderr(
@@ -478,57 +1119,302 @@ pub const GlobalObject = struct {
ctx: js.JSContextRef,
function: js.JSObjectRef,
thisObject: js.JSObjectRef,
- arguments: []js.JSValueRef,
+ arguments: []const js.JSValueRef,
+ exception: js.JSValueRef,
) js.JSValueRef {
- return try output(Output.errorWriter(), ctx, arguments);
+ output(Output.errorWriter(), ctx, arguments) catch {};
+ return js.JSValueMakeUndefined(ctx);
// js.JSObjectMakeFunctionWithCallback(ctx: JSContextRef, name: JSStringRef, callAsFunction: JSObjectCallAsFunctionCallback)
}
};
-pub fn NewSingletonClass(
+pub fn NewClass(
comptime ZigType: type,
comptime name: string,
- comptime functions: anytype,
+ comptime staticFunctions: anytype,
+ comptime properties: anytype,
comptime read_only: bool,
+ comptime singleton: bool,
) type {
return struct {
const ClassDefinitionCreator = @This();
- const function_names = std.meta.fieldNames(functions);
- const function_name_literals: [function_names.len][]js.JSChar = brk: {
- var names = std.mem.zeroes([function_names.len][]js.JSChar);
-
+ const function_names = std.meta.fieldNames(@TypeOf(staticFunctions));
+ const names_buf = brk: {
+ var total_len: usize = 0;
+ for (function_names) |field, i| {
+ total_len += std.unicode.utf8ToUtf16LeStringLiteral(field).len;
+ }
+ var offset: usize = 0;
+ var names_buf_ = std.mem.zeroes([total_len]u16);
for (function_names) |field, i| {
- names[i] = std.unicode.utf8ToUtf16LeStringLiteral(field);
+ var name_ = std.unicode.utf8ToUtf16LeStringLiteral(field);
+ std.mem.copy(u16, names_buf_[offset .. name_.len + offset], name_[0..]);
+ offset += name_.len;
+ }
+ break :brk names_buf_;
+ };
+ const function_name_literals: [function_names.len][]const js.JSChar = brk: {
+ var names = std.mem.zeroes([function_names.len][]const js.JSChar);
+ var len: usize = 0;
+ for (function_names) |field, i| {
+ const end = len + std.unicode.utf8ToUtf16LeStringLiteral(field).len;
+ names[i] = names_buf[len..end];
+ len = end;
}
break :brk names;
};
var function_name_refs: [function_names.len]js.JSStringRef = undefined;
+ var class_name_str = name[0.. :0].ptr;
const class_name_literal = std.unicode.utf8ToUtf16LeStringLiteral(name);
- var static_functions: [function_name_refs.len + 1:0]js.JSStaticFunction = undefined;
-
- pub fn define(zig: *ZigType, ctx: js.JSContextRef) !js.JSClassDefinition {
- var def = std.mem.zeroes(js.JSClassDefinition);
-
- inline for (function_name_literals) |function_name, i| {
- function_name_refs[i] = js.JSStringCreateWithCharactersNoCopy(&function_name, function_name.len);
- static_functions[i] = js.JSStaticFunction{
- .name = (function_names[i][0.. :0]).ptr,
- .callAsFunction = To.JS.functionWithCallback(
- ZigType,
- zig,
- function_name_refs[i],
- ctx,
- @field(functions, function_names[i]),
+ var static_functions: [function_name_refs.len + 1]js.JSStaticFunction = undefined;
+ var instance_functions: [function_names.len]js.JSObjectRef = undefined;
+ const property_names = std.meta.fieldNames(@TypeOf(properties));
+ var property_name_refs: [property_names.len]js.JSStringRef = undefined;
+ const property_name_literals: [property_names.len][]const js.JSChar = brk: {
+ var list = std.mem.zeroes([property_names.len][]const js.JSChar);
+ for (property_names) |prop_name, i| {
+ list[i] = std.unicode.utf8ToUtf16LeStringLiteral(prop_name);
+ }
+ break :brk list;
+ };
+ var static_properties: [property_names.len]js.JSStaticValue = undefined;
+
+ pub fn getPropertyCallback(ctx: js.JSContextRef, obj: js.JSObjectRef, prop: js.JSStringRef, exception: ExceptionValueRef) callconv(.C) js.JSValueRef {
+ var instance_pointer_ = js.JSObjectGetPrivate(obj);
+ if (instance_pointer_ == null) return js.JSValueMakeUndefined(ctx);
+ var instance_pointer = instance_pointer_.?;
+ var ptr = @ptrCast(
+ *ZigType,
+ @alignCast(
+ @alignOf(
+ *ZigType,
),
- .attributes = comptime if (read_only) js.JSPropertyAttributes.kJSPropertyAttributeReadOnly else js.JSPropertyAttributes.kJSPropertyAttributeNone,
- };
+ instance_pointer,
+ ),
+ );
+
+ if (singleton) {
+ inline for (function_names) |propname, i| {
+ if (js.JSStringIsEqual(prop, function_name_refs[i])) {
+ return instance_functions[i];
+ }
+ }
+ if (comptime std.meta.trait.hasFn("onMissingProperty")(ZigType)) {
+ return ptr.onMissingProperty(ctx, obj, prop, exception);
+ }
+ } else {
+ inline for (property_names) |propname, i| {
+ if (js.JSStringIsEqual(prop, property_name_refs[i])) {
+ return @field(
+ properties,
+ propname,
+ )(ptr, ctx, obj, exception);
+ }
+ }
+
+ if (comptime std.meta.trait.hasFn("onMissingProperty")(ZigType)) {
+ return ptr.onMissingProperty(ctx, obj, prop, exception);
+ }
}
- static_functions[function_name_literals.len] = std.mem.zeroes(js.JSStaticFunction);
- def.staticFunctions = static_functions[0.. :0].ptr;
- def.className = name[0.. :0].ptr;
+
+ return js.JSValueMakeUndefined(ctx);
+ }
+
+ fn StaticProperty(comptime id: usize) type {
+ return struct {
+ pub fn getter(ctx: js.JSContextRef, obj: js.JSObjectRef, prop: js.JSStringRef, exception: [*c]js.JSValueRef) callconv(.C) js.JSValueRef {
+ var instance_pointer_ = js.JSObjectGetPrivate(obj);
+ if (instance_pointer_ == null) return js.JSValueMakeUndefined(ctx);
+ var ptr = @ptrCast(
+ *ZigType,
+ @alignCast(
+ @alignOf(
+ *ZigType,
+ ),
+ instance_pointer_.?,
+ ),
+ );
+
+ return @field(
+ properties,
+ property_names[id],
+ )(ptr, ctx, obj, exception);
+ }
+ };
+ }
+
+ pub fn define(ctx: js.JSContextRef) js.JSClassDefinition {
+ var def = js.kJSClassDefinitionEmpty;
+
+ if (static_functions.len > 0) {
+ inline for (function_name_literals) |function_name, i| {
+ var callback = To.JS.Callback(ZigType, @field(staticFunctions, function_names[i])).rfn;
+ function_name_refs[i] = js.JSStringCreateWithCharactersNoCopy(
+ function_name.ptr,
+ function_name.len,
+ );
+
+ static_functions[i] = js.JSStaticFunction{
+ .name = (function_names[i][0.. :0]).ptr,
+ .callAsFunction = callback,
+ .attributes = comptime if (read_only) js.JSPropertyAttributes.kJSPropertyAttributeReadOnly else js.JSPropertyAttributes.kJSPropertyAttributeNone,
+ };
+ // if (singleton) {
+ // var function = js.JSObjectMakeFunctionWithCallback(ctx, function_name_refs[i], callback);
+ // instance_functions[i] = function;
+ // }
+ }
+ def.staticFunctions = &static_functions;
+ }
+
+ if (property_names.len > 0) {
+ inline for (comptime property_name_literals) |prop_name, i| {
+ property_name_refs[i] = js.JSStringCreateWithCharactersNoCopy(
+ prop_name.ptr,
+ prop_name.len,
+ );
+ static_properties[i] = std.mem.zeroes(js.JSStaticValue);
+ static_properties[i].getProperty = StaticProperty(i).getter;
+ static_properties[i].name = property_names[i][0.. :0];
+ }
+
+ def.staticValues = (&static_properties);
+ }
+
+ def.className = class_name_str;
+ // def.getProperty = getPropertyCallback;
return def;
}
};
}
+
+// This makes it so we get the defines already formatted from the user's environment with the "process.env." prefix set
+// This also normalizes quoting
+// Currently, it truncates any environment variables to a max of 1024 bytes
+const NodeEnvBufMap = struct {
+ backing: std.BufMap,
+ pub fn init(allocator: *std.mem.Allocator) NodeEnvBufMap {
+ return NodeEnvBufMap{ .backing = std.BufMap.init(allocator) };
+ }
+ pub fn get(this: *const NodeEnvBufMap, key: string) ?string {
+ return this.backing.get(key);
+ }
+ pub threadlocal var bufkeybuf: [1024]u8 = undefined;
+ pub threadlocal var bufkeybuf_first = true;
+ pub fn put(this: *NodeEnvBufMap, key: string, value: string) !void {
+ if (value.len == 0) {
+ return;
+ }
+
+ if (bufkeybuf_first) {
+ bufkeybuf[0.."process.env.".len].* = "process.env.";
+ bufkeybuf_first = false;
+ }
+ std.mem.copy(u8, bufkeybuf_first["process.env.".len..], key);
+ var key_slice = bufkeybuf[0 .. key.len + "process.env.".len];
+ var value_slice = value;
+ const max_value_slice_len = std.math.min(value.len, bufkeybuf.len - key_slice.len);
+ if (value[0] != '"' and value[value.len - 1] != '"') {
+ value_slice = bufkeybuf[key_slice.len..][0 .. max_value_slice_len + 2];
+ value_slice[0] = '"';
+ std.mem.copy(u8, value_slice[1..], value[0..max_value_slice_len]);
+ value_slice[value_slice.len - 1] = '"';
+ } else if (value[0] != '"') {
+ value_slice[0] = '"';
+ std.mem.copy(u8, value_slice[1..], value[0..max_value_slice_len]);
+ } else if (value[value.len - 1] != '"') {
+ std.mem.copy(u8, value_slice[1..], value[0..max_value_slice_len]);
+ value_slice[value_slice.len - 1] = '"';
+ }
+
+ return this.backing.put(key_slice, value_slice);
+ }
+};
+
+pub fn getNodeEnvMap(allocator: *Allocator) !NodeEnvBufMap {
+ var result = NodeEnvBufMap.init(allocator);
+ errdefer result.deinit();
+
+ if (builtin.os.tag == .windows) {
+ const ptr = os.windows.peb().ProcessParameters.Environment;
+
+ var i: usize = 0;
+ while (ptr[i] != 0) {
+ const key_start = i;
+
+ while (ptr[i] != 0 and ptr[i] != '=') : (i += 1) {}
+ const key_w = ptr[key_start..i];
+ const key = try std.unicode.utf16leToUtf8Alloc(allocator, key_w);
+ errdefer allocator.free(key);
+
+ if (ptr[i] == '=') i += 1;
+
+ const value_start = i;
+ while (ptr[i] != 0) : (i += 1) {}
+ const value_w = ptr[value_start..i];
+ const value = try std.unicode.utf16leToUtf8Alloc(allocator, value_w);
+ errdefer allocator.free(value);
+
+ i += 1; // skip over null byte
+
+ try result.putMove(key, value);
+ }
+ return result;
+ } else if (builtin.os.tag == .wasi) {
+ var environ_count: usize = undefined;
+ var environ_buf_size: usize = undefined;
+
+ const environ_sizes_get_ret = os.wasi.environ_sizes_get(&environ_count, &environ_buf_size);
+ if (environ_sizes_get_ret != os.wasi.ESUCCESS) {
+ return os.unexpectedErrno(environ_sizes_get_ret);
+ }
+
+ var environ = try allocator.alloc([*:0]u8, environ_count);
+ defer allocator.free(environ);
+ var environ_buf = try allocator.alloc(u8, environ_buf_size);
+ defer allocator.free(environ_buf);
+
+ const environ_get_ret = os.wasi.environ_get(environ.ptr, environ_buf.ptr);
+ if (environ_get_ret != os.wasi.ESUCCESS) {
+ return os.unexpectedErrno(environ_get_ret);
+ }
+
+ for (environ) |env| {
+ const pair = mem.spanZ(env);
+ var parts = mem.split(pair, "=");
+ const key = parts.next().?;
+ const value = parts.next().?;
+ try result.put(key, value);
+ }
+ return result;
+ } else if (builtin.link_libc) {
+ var ptr = std.c.environ;
+ while (ptr.*) |line| : (ptr += 1) {
+ var line_i: usize = 0;
+ while (line[line_i] != 0 and line[line_i] != '=') : (line_i += 1) {}
+ const key = line[0..line_i];
+
+ var end_i: usize = line_i;
+ while (line[end_i] != 0) : (end_i += 1) {}
+ const value = line[line_i + 1 .. end_i];
+
+ try result.put(key, value);
+ }
+ return result;
+ } else {
+ for (os.environ) |line| {
+ var line_i: usize = 0;
+ while (line[line_i] != 0 and line[line_i] != '=') : (line_i += 1) {}
+ const key = line[0..line_i];
+
+ var end_i: usize = line_i;
+ while (line[end_i] != 0) : (end_i += 1) {}
+ const value = line[line_i + 1 .. end_i];
+
+ try result.put(key, value);
+ }
+ return result;
+ }
+}
diff --git a/src/main_javascript.zig b/src/main_javascript.zig
new file mode 100644
index 000000000..b637d8916
--- /dev/null
+++ b/src/main_javascript.zig
@@ -0,0 +1,374 @@
+const std = @import("std");
+const lex = @import("js_lexer.zig");
+const logger = @import("logger.zig");
+const alloc = @import("alloc.zig");
+const options = @import("options.zig");
+const js_parser = @import("js_parser.zig");
+const json_parser = @import("json_parser.zig");
+const js_printer = @import("js_printer.zig");
+const js_ast = @import("js_ast.zig");
+const linker = @import("linker.zig");
+usingnamespace @import("ast/base.zig");
+usingnamespace @import("defines.zig");
+usingnamespace @import("global.zig");
+const panicky = @import("panic_handler.zig");
+pub const MainPanicHandler = panicky.NewPanicHandler(panicky.default_panic);
+const Api = @import("api/schema.zig").Api;
+const resolve_path = @import("./resolver/resolve_path.zig");
+const clap = @import("clap");
+const bundler = @import("bundler.zig");
+const fs = @import("fs.zig");
+const NodeModuleBundle = @import("./node_module_bundle.zig").NodeModuleBundle;
+const js = @import("javascript/jsc/javascript.zig");
+const allocators = @import("allocators.zig");
+pub fn panic(msg: []const u8, error_return_trace: ?*std.builtin.StackTrace) noreturn {
+ if (MainPanicHandler.Singleton) |singleton| {
+ MainPanicHandler.handle_panic(msg, error_return_trace);
+ } else {
+ panicky.default_panic(msg, error_return_trace);
+ }
+}
+const constStrToU8 = allocators.constStrToU8;
+pub fn main() anyerror!void {
+ // The memory allocator makes a massive difference.
+ // std.heap.raw_c_allocator and std.heap.c_allocator perform similarly.
+ // std.heap.GeneralPurposeAllocator makes this about 3x _slower_ than esbuild.
+ // var root_alloc = std.heap.ArenaAllocator.init(std.heap.raw_c_allocator);
+ // var root_alloc_ = &root_alloc.allocator;
+ try alloc.setup(std.heap.c_allocator);
+ var stdout = std.io.getStdOut();
+ // var stdout = std.io.bufferedWriter(stdout_file.writer());
+ var stderr = std.io.getStdErr();
+ // var stderr = std.io.bufferedWriter(stderr_file.writer());
+ var output_source = Output.Source.init(stdout, stderr);
+ // defer stdout.flush() catch {};
+ // defer stderr.flush() catch {};
+ Output.Source.set(&output_source);
+ Output.enable_ansi_colors = stderr.isTty();
+ defer Output.flush();
+ try Cli.start(
+ std.heap.c_allocator,
+ stdout,
+ stderr,
+ );
+}
+
+pub const Cli = struct {
+ const LoaderMatcher = strings.ExactSizeMatcher(4);
+ pub fn ColonListType(comptime t: type, value_resolver: anytype) type {
+ return struct {
+ pub fn init(allocator: *std.mem.Allocator, count: usize) !@This() {
+ var keys = try allocator.alloc(string, count);
+ var values = try allocator.alloc(t, count);
+
+ return @This(){ .keys = keys, .values = values };
+ }
+ keys: []string,
+ values: []t,
+
+ pub fn load(self: *@This(), input: []const string) !void {
+ for (input) |str, i| {
+ // Support either ":" or "=" as the separator, preferring whichever is first.
+ // ":" is less confusing IMO because that syntax is used with flags
+ // but "=" is what esbuild uses and I want this to be somewhat familiar for people using esbuild
+ const midpoint = std.math.min(strings.indexOfChar(str, ':') orelse std.math.maxInt(usize), strings.indexOfChar(str, '=') orelse std.math.maxInt(usize));
+ if (midpoint == std.math.maxInt(usize)) {
+ return error.InvalidSeparator;
+ }
+
+ self.keys[i] = str[0..midpoint];
+ self.values[i] = try value_resolver(str[midpoint + 1 .. str.len]);
+ }
+ }
+
+ pub fn resolve(allocator: *std.mem.Allocator, input: []const string) !@This() {
+ var list = try init(allocator, input.len);
+ try list.load(input);
+ return list;
+ }
+ };
+ }
+ pub const LoaderColonList = ColonListType(Api.Loader, Arguments.loader_resolver);
+ pub const DefineColonList = ColonListType(string, Arguments.noop_resolver);
+
+ pub const Arguments = struct {
+ pub fn loader_resolver(in: string) !Api.Loader {
+ const Matcher = strings.ExactSizeMatcher(4);
+ switch (Matcher.match(in)) {
+ Matcher.case("jsx") => return Api.Loader.jsx,
+ Matcher.case("js") => return Api.Loader.js,
+ Matcher.case("ts") => return Api.Loader.ts,
+ Matcher.case("tsx") => return Api.Loader.tsx,
+ Matcher.case("css") => return Api.Loader.css,
+ Matcher.case("file") => return Api.Loader.file,
+ Matcher.case("json") => return Api.Loader.json,
+ else => {
+ return error.InvalidLoader;
+ },
+ }
+ }
+
+ pub fn noop_resolver(in: string) !string {
+ return in;
+ }
+
+ pub fn fileReadError(err: anyerror, stderr: anytype, filename: string, kind: string) noreturn {
+ stderr.writer().print("Error reading file \"{s}\" for {s}: {s}", .{ filename, kind, @errorName(err) }) catch {};
+ std.process.exit(1);
+ }
+
+ pub fn readFile(
+ allocator: *std.mem.Allocator,
+ cwd: string,
+ filename: string,
+ ) ![]u8 {
+ var paths = [_]string{ cwd, filename };
+ const outpath = try std.fs.path.resolve(allocator, &paths);
+ defer allocator.free(outpath);
+ var file = try std.fs.openFileAbsolute(outpath, std.fs.File.OpenFlags{ .read = true, .write = false });
+ defer file.close();
+ const stats = try file.stat();
+ return try file.readToEndAlloc(allocator, stats.size);
+ }
+
+ pub fn parse(allocator: *std.mem.Allocator, stdout: anytype, stderr: anytype) !Api.TransformOptions {
+ @setEvalBranchQuota(9999);
+ const params = comptime [_]clap.Param(clap.Help){
+ clap.parseParam("-h, --help Display this help and exit. ") catch unreachable,
+ clap.parseParam("-r, --resolve <STR> Determine import/require behavior. \"disable\" ignores. \"dev\" bundles node_modules and builds everything else as independent entry points") catch unreachable,
+ clap.parseParam("-d, --define <STR>... Substitute K:V while parsing, e.g. --define process.env.NODE_ENV:development") catch unreachable,
+ clap.parseParam("-l, --loader <STR>... Parse files with .ext:loader, e.g. --loader .js:jsx. Valid loaders: jsx, js, json, tsx (not implemented yet), ts (not implemented yet), css (not implemented yet)") catch unreachable,
+ clap.parseParam("-o, --outdir <STR> Save output to directory (default: \"out\" if none provided and multiple entry points passed)") catch unreachable,
+ clap.parseParam("-e, --external <STR>... Exclude module from transpilation (can use * wildcards). ex: -e react") catch unreachable,
+ clap.parseParam("-i, --inject <STR>... Inject module at the top of every file") catch unreachable,
+ clap.parseParam("--cwd <STR> Absolute path to resolve entry points from. Defaults to cwd") catch unreachable,
+ clap.parseParam("--public-url <STR> Rewrite import paths to start with --public-url. Useful for web browsers.") catch unreachable,
+ clap.parseParam("--serve Start a local dev server. This also sets resolve to \"lazy\".") catch unreachable,
+ clap.parseParam("--public-dir <STR> Top-level directory for .html files, fonts, images, or anything external. Only relevant with --serve. Defaults to \"<cwd>/public\", to match create-react-app and Next.js") catch unreachable,
+ clap.parseParam("--jsx-factory <STR> Changes the function called when compiling JSX elements using the classic JSX runtime") catch unreachable,
+ clap.parseParam("--jsx-fragment <STR> Changes the function called when compiling JSX fragments using the classic JSX runtime") catch unreachable,
+ clap.parseParam("--jsx-import-source <STR> Declares the module specifier to be used for importing the jsx and jsxs factory functions. Default: \"react\"") catch unreachable,
+ clap.parseParam("--jsx-runtime <STR> \"automatic\" (default) or \"classic\"") catch unreachable,
+ clap.parseParam("--jsx-production Use jsx instead of jsxDEV (default) for the automatic runtime") catch unreachable,
+ clap.parseParam("--extension-order <STR>... defaults to: .tsx,.ts,.jsx,.js,.json ") catch unreachable,
+ clap.parseParam("--disable-react-fast-refresh Disable React Fast Refresh. Enabled if --serve is set and --jsx-production is not set. Otherwise, it's a noop.") catch unreachable,
+ clap.parseParam("--tsconfig-override <STR> Load tsconfig from path instead of cwd/tsconfig.json") catch unreachable,
+ clap.parseParam("--platform <STR> \"browser\" or \"node\". Defaults to \"browser\"") catch unreachable,
+ clap.parseParam("--main-fields <STR>... Main fields to lookup in package.json. Defaults to --platform dependent") catch unreachable,
+ clap.parseParam("--scan Instead of bundling or transpiling, print a list of every file imported by an entry point, recursively") catch unreachable,
+ clap.parseParam("--new-jsb Generate a new node_modules.jsb file from node_modules and entry point(s)") catch unreachable,
+ clap.parseParam("--jsb <STR> Use a Speedy JavaScript Bundle (default: \"./node_modules.jsb\" if exists)") catch unreachable,
+ // clap.parseParam("--no-jsb Use a Speedy JavaScript Bundle (default: \"./node_modules.jsb\" if exists)") catch unreachable,
+ clap.parseParam("<POS>... Entry points to use") catch unreachable,
+ };
+
+ var diag = clap.Diagnostic{};
+
+ var args = clap.parse(clap.Help, &params, .{ .diagnostic = &diag }) catch |err| {
+ // Report useful error and exit
+ diag.report(stderr.writer(), err) catch {};
+ return err;
+ };
+
+ if (args.flag("--help")) {
+ try clap.help(stderr.writer(), &params);
+ std.process.exit(1);
+ }
+
+ var cwd_paths = [_]string{args.option("--cwd") orelse try std.process.getCwdAlloc(allocator)};
+ var cwd = try std.fs.path.resolve(allocator, &cwd_paths);
+ var tsconfig_override = if (args.option("--tsconfig-override")) |ts| (Arguments.readFile(allocator, cwd, ts) catch |err| fileReadError(err, stderr, ts, "tsconfig.json")) else null;
+ var public_url = args.option("--public-url");
+ var defines_tuple = try DefineColonList.resolve(allocator, args.options("--define"));
+ var loader_tuple = try LoaderColonList.resolve(allocator, args.options("--define"));
+
+ var define_keys = defines_tuple.keys;
+ var define_values = defines_tuple.values;
+ var loader_keys = loader_tuple.keys;
+ var loader_values = loader_tuple.values;
+ var entry_points = args.positionals();
+ var inject = args.options("--inject");
+ var output_dir = args.option("--outdir");
+ const serve = false;
+
+ var write = entry_points.len > 1 or output_dir != null;
+ if (write and output_dir == null) {
+ var _paths = [_]string{ cwd, "out" };
+ output_dir = try std.fs.path.resolve(allocator, &_paths);
+ }
+ var externals = std.mem.zeroes([][]u8);
+ if (args.options("--external").len > 0) {
+ externals = try allocator.alloc([]u8, args.options("--external").len);
+ for (args.options("--external")) |external, i| {
+ externals[i] = constStrToU8(external);
+ }
+ }
+
+ var jsx_factory = args.option("--jsx-factory");
+ var jsx_fragment = args.option("--jsx-fragment");
+ var jsx_import_source = args.option("--jsx-import-source");
+ var jsx_runtime = args.option("--jsx-runtime");
+ var jsx_production = args.flag("--jsx-production");
+ var react_fast_refresh = false;
+
+ if (serve or args.flag("--new-jsb")) {
+ react_fast_refresh = true;
+ if (args.flag("--disable-react-fast-refresh") or jsx_production) {
+ react_fast_refresh = false;
+ }
+ }
+
+ var main_fields = args.options("--main-fields");
+
+ var node_modules_bundle_path = args.option("--jsb") orelse brk: {
+ if (args.flag("--new-jsb")) {
+ break :brk null;
+ }
+
+ const node_modules_bundle_path_absolute = resolve_path.joinAbs(cwd, .auto, "node_modules.jsb");
+ std.fs.accessAbsolute(node_modules_bundle_path_absolute, .{}) catch |err| {
+ break :brk null;
+ };
+ break :brk try allocator.dupe(u8, node_modules_bundle_path_absolute);
+ };
+
+ if (args.flag("--new-jsb")) {
+ node_modules_bundle_path = null;
+ }
+
+ const PlatformMatcher = strings.ExactSizeMatcher(8);
+ const ResoveMatcher = strings.ExactSizeMatcher(8);
+
+ var resolve = Api.ResolveMode.lazy;
+ if (args.option("--resolve")) |_resolve| {
+ switch (PlatformMatcher.match(_resolve)) {
+ PlatformMatcher.case("disable") => {
+ resolve = Api.ResolveMode.disable;
+ },
+ PlatformMatcher.case("bundle") => {
+ resolve = Api.ResolveMode.bundle;
+ },
+ PlatformMatcher.case("dev") => {
+ resolve = Api.ResolveMode.dev;
+ },
+ PlatformMatcher.case("lazy") => {
+ resolve = Api.ResolveMode.lazy;
+ },
+ else => {
+ diag.name.long = "--resolve";
+ diag.arg = _resolve;
+ try diag.report(stderr.writer(), error.InvalidResolveOption);
+ std.process.exit(1);
+ },
+ }
+ }
+
+ var platform: ?Api.Platform = null;
+
+ if (args.option("--platform")) |_platform| {
+ switch (PlatformMatcher.match(_platform)) {
+ PlatformMatcher.case("browser") => {
+ platform = Api.Platform.browser;
+ },
+ PlatformMatcher.case("node") => {
+ platform = Api.Platform.node;
+ },
+ else => {
+ diag.name.long = "--platform";
+ diag.arg = _platform;
+ try diag.report(stderr.writer(), error.InvalidPlatform);
+ std.process.exit(1);
+ },
+ }
+ }
+
+ var jsx: ?Api.Jsx = null;
+ if (jsx_factory != null or
+ jsx_fragment != null or
+ jsx_import_source != null or
+ jsx_runtime != null or
+ jsx_production or react_fast_refresh)
+ {
+ var default_factory = "".*;
+ var default_fragment = "".*;
+ var default_import_source = "".*;
+ jsx = Api.Jsx{
+ .factory = constStrToU8(jsx_factory orelse &default_factory),
+ .fragment = constStrToU8(jsx_fragment orelse &default_fragment),
+ .import_source = constStrToU8(jsx_import_source orelse &default_import_source),
+ .runtime = if (jsx_runtime != null) try resolve_jsx_runtime(jsx_runtime.?) else Api.JsxRuntime.automatic,
+ .development = !jsx_production,
+ .react_fast_refresh = react_fast_refresh,
+ };
+ }
+
+ if (entry_points.len == 0) {
+ try clap.help(stderr.writer(), &params);
+ try diag.report(stderr.writer(), error.MissingEntryPoint);
+ std.process.exit(1);
+ }
+
+ return Api.TransformOptions{
+ .jsx = jsx,
+ .output_dir = output_dir,
+ .resolve = resolve,
+ .external = externals,
+ .absolute_working_dir = cwd,
+ .tsconfig_override = tsconfig_override,
+ .public_url = public_url,
+ .define = .{
+ .keys = define_keys,
+ .values = define_values,
+ },
+ .loaders = .{
+ .extensions = loader_keys,
+ .loaders = loader_values,
+ },
+ .node_modules_bundle_path = node_modules_bundle_path,
+ .public_dir = if (args.option("--public-dir")) |public_dir| allocator.dupe(u8, public_dir) catch unreachable else null,
+ .write = write,
+ .platform = .speedy,
+ .serve = serve,
+ .inject = inject,
+ .entry_points = entry_points,
+ .extension_order = args.options("--extension-order"),
+ .main_fields = args.options("--main-fields"),
+ .only_scan_dependencies = if (args.flag("--scan")) Api.ScanDependencyMode.all else Api.ScanDependencyMode._none,
+ .generate_node_module_bundle = if (args.flag("--new-jsb")) true else false,
+ };
+ }
+ };
+ pub fn resolve_jsx_runtime(str: string) !Api.JsxRuntime {
+ if (strings.eql(str, "automatic")) {
+ return Api.JsxRuntime.automatic;
+ } else if (strings.eql(str, "fallback")) {
+ return Api.JsxRuntime.classic;
+ } else {
+ return error.InvalidJSXRuntime;
+ }
+ }
+ pub fn printScanResults(scan_results: bundler.ScanResult.Summary, allocator: *std.mem.Allocator) !void {
+ var stdout = std.io.getStdOut();
+ const print_start = std.time.nanoTimestamp();
+ try std.json.stringify(scan_results.list(), .{}, stdout.writer());
+ Output.printError("\nJSON printing took: {d}\n", .{std.time.nanoTimestamp() - print_start});
+ }
+ pub fn startTransform(allocator: *std.mem.Allocator, args: Api.TransformOptions, log: *logger.Log) anyerror!void {}
+ pub fn start(allocator: *std.mem.Allocator, stdout: anytype, stderr: anytype) anyerror!void {
+ const start_time = std.time.nanoTimestamp();
+ var log = logger.Log.init(allocator);
+ var panicker = MainPanicHandler.init(&log);
+ MainPanicHandler.Singleton = &panicker;
+
+ // var args = try Arguments.parse(alloc.static, stdout, stderr);
+ // var serve_bundler = try bundler.ServeBundler.init(allocator, &log, args);
+ // var res = try serve_bundler.buildFile(&log, allocator, args.entry_points[0], std.fs.path.extension(args.entry_points[0]));
+
+ // var results = try bundler.Bundler.bundle(allocator, &log, args);
+ // var file = results.output_files[0];
+ var vm = try js.VirtualMachine.init(allocator);
+
+ _ = try vm.evalUtf8("test.js", "console.log(Number(10.1));"[0.. :0]);
+ Output.print("Done", .{});
+ }
+};
diff --git a/src/options.zig b/src/options.zig
index aca85ed31..9009fd88c 100644
--- a/src/options.zig
+++ b/src/options.zig
@@ -286,6 +286,7 @@ pub const Platform = enum {
return switch (plat orelse api.Api.Platform._none) {
.node => .node,
.browser => .browser,
+ .speedy => .speedy,
else => .browser,
};
}
@@ -674,12 +675,25 @@ pub const BundleOptions = struct {
}
if (transform.platform) |plat| {
- opts.platform = if (plat == .browser) .browser else .node;
+ opts.platform = switch (plat) {
+ .speedy => speedy,
+ .neutral => .neutral,
+ .browser => .browser,
+ .node => .node,
+ };
opts.main_fields = Platform.DefaultMainFields.get(opts.platform);
}
- if (opts.platform == .node) {
- opts.import_path_format = .relative_nodejs;
+ switch (opts.platform) {
+ .node => {
+ opts.import_path_format = .relative_nodejs;
+ },
+ .speedy => {
+ // If we're doing SSR, we want all the URLs to be the same as what it would be in the browser
+ // If we're not doing SSR, we want all the import paths to be absolute
+ opts.import_path_format = if (opts.import_path_format == .absolute_url) .absolute_url else .absolute_path;
+ },
+ else => {},
}
if (transform.main_fields.len > 0) {
diff --git a/src/string_immutable.zig b/src/string_immutable.zig
index 546ba8a4f..03382e7a2 100644
--- a/src/string_immutable.zig
+++ b/src/string_immutable.zig
@@ -431,11 +431,10 @@ pub const CodepointIterator = struct {
inline fn nextCodepointSlice(it: *CodepointIterator) []const u8 {
@setRuntimeSafety(false);
- const cp_len = utf8ByteSequenceLength(it.source.contents[it.current]);
- it.end = it.current;
- it.current += cp_len;
+ const cp_len = utf8ByteSequenceLength(it.bytes[it.i]);
+ it.i += cp_len;
- return if (!(it.current > it.source.contents.len)) it.source.contents[it.current - cp_len .. it.current] else "";
+ return if (!(it.i > it.bytes.len)) it.bytes[it.i - cp_len .. it.i] else "";
}
pub fn nextCodepoint(it: *CodepointIterator) CodePoint {
diff --git a/src/wtf_string_mutable.zig b/src/wtf_string_mutable.zig
index 2c94dae22..2d1aac522 100644
--- a/src/wtf_string_mutable.zig
+++ b/src/wtf_string_mutable.zig
@@ -139,7 +139,7 @@ pub const WTFStringMutable = struct {
self.list.appendAssumeCapacity(char);
}
pub inline fn append(self: *WTFStringMutable, str: []const u8) !void {
- self.growIfNeeded(str.len);
+ try self.growIfNeeded(str.len);
var iter = strings.CodepointIterator{ .bytes = str, .i = 0 };
while (true) {
@@ -148,12 +148,12 @@ pub const WTFStringMutable = struct {
return;
},
0...0xFFFF => {
- try self.list.append(@intCast(u16, iter.c));
+ try self.list.append(self.allocator, @intCast(u16, iter.c));
},
else => {
const c = iter.c - 0x10000;
- try self.list.append(@intCast(u16, 0xD800 + ((c >> 10) & 0x3FF)));
- try self.list.append(@intCast(u16, 0xDC00 + (c & 0x3FF)));
+ try self.list.append(self.allocator, @intCast(u16, 0xD800 + ((c >> 10) & 0x3FF)));
+ try self.list.append(self.allocator, @intCast(u16, 0xDC00 + (c & 0x3FF)));
},
}
}
@@ -186,15 +186,15 @@ pub const WTFStringMutable = struct {
return @intCast(i32, self.list.items.len);
}
- pub fn toOwnedSlice(self: *WTFStringMutable) string {
+ pub fn toOwnedSlice(self: *WTFStringMutable) []u16 {
return self.list.toOwnedSlice(self.allocator);
}
- pub fn toOwnedSliceLeaky(self: *WTFStringMutable) string {
+ pub fn toOwnedSliceLeaky(self: *WTFStringMutable) []u16 {
return self.list.items;
}
- pub fn toOwnedSliceLength(self: *WTFStringMutable, length: usize) string {
+ pub fn toOwnedSliceLength(self: *WTFStringMutable, length: usize) {
self.list.shrinkAndFree(self.allocator, length);
return self.list.toOwnedSlice(self.allocator);
}