@onda-lang/wasm-compiler 0.5.4 → 0.7.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/src/index.js CHANGED
@@ -3,6 +3,8 @@ import {
3
3
  PROCESSOR_ABI_VERSION,
4
4
  PROCESSOR_ARTIFACT_FORMAT,
5
5
  PROCESSOR_ARTIFACT_FORMAT_VERSION,
6
+ PROCESSOR_EXECUTION_OK,
7
+ PROCESSOR_EXECUTION_RUNTIME_SAFETY_FAILURE,
6
8
  PROCESSOR_SNAPSHOT_FORMAT_VERSION,
7
9
  createProcessorArtifactFiles,
8
10
  loadProcessorArtifactFiles,
@@ -27,6 +29,8 @@ export {
27
29
  PROCESSOR_ABI_VERSION,
28
30
  PROCESSOR_ARTIFACT_FORMAT,
29
31
  PROCESSOR_ARTIFACT_FORMAT_VERSION,
32
+ PROCESSOR_EXECUTION_OK,
33
+ PROCESSOR_EXECUTION_RUNTIME_SAFETY_FAILURE,
30
34
  PROCESSOR_SNAPSHOT_FORMAT_VERSION,
31
35
  createProcessorArtifactFiles,
32
36
  loadProcessorArtifactFiles,
@@ -46,7 +50,10 @@ export class OndaCompilerError extends Error {
46
50
  }
47
51
 
48
52
  export class OndaCompileError extends OndaCompilerError {
49
- constructor(diagnostics, { cause } = {}) {
53
+ constructor(
54
+ diagnostics,
55
+ { cause, sourceFiles = [], unresolvedSourceFiles = [] } = {},
56
+ ) {
50
57
  const normalized = normalizeDiagnostics(diagnostics);
51
58
  const first = normalized[0];
52
59
  const message = first
@@ -55,6 +62,8 @@ export class OndaCompileError extends OndaCompilerError {
55
62
  super(message, { cause });
56
63
  this.name = "OndaCompileError";
57
64
  this.diagnostics = normalized;
65
+ this.sourceFiles = normalizeSourceFiles(sourceFiles);
66
+ this.unresolvedSourceFiles = normalizeSourceFiles(unresolvedSourceFiles);
58
67
  }
59
68
  }
60
69
 
@@ -72,9 +81,9 @@ class OndaCompiler {
72
81
  throw configurationError("source must be a string");
73
82
  }
74
83
  const compile = normalizeCompileOptions(options);
75
- let mir;
84
+ let frontendCompilation;
76
85
  try {
77
- mir = this.frontend.compile_to_mir_messagepack(
86
+ frontendCompilation = this.frontend.compile_to_mir_messagepack(
78
87
  source,
79
88
  compile.sampleRate,
80
89
  compile.blockSize,
@@ -82,38 +91,204 @@ class OndaCompiler {
82
91
  } catch (error) {
83
92
  throw diagnosticsFromFrontend(error);
84
93
  }
85
- return compileMirTransport(mir, compile.codegen, this.compileTrustedMir);
94
+ const { mir, sourceFiles, sourceGraph } = consumeFrontendCompilation(frontendCompilation);
95
+ const artifact = compileMirTransport(
96
+ mir,
97
+ compile.codegen,
98
+ this.compileTrustedMir,
99
+ sourceFiles,
100
+ );
101
+ return { artifact, sourceFiles, sourceGraph };
86
102
  }
87
103
 
88
- async compileProject(project, options = {}) {
89
- if (!project || typeof project !== "object" || Array.isArray(project)) {
90
- throw configurationError("project must contain an entry and source map");
104
+ async compileWorkspace(workspace, options = {}) {
105
+ if (!workspace || typeof workspace !== "object" || Array.isArray(workspace)) {
106
+ throw configurationError("workspace must contain an entry and source map");
91
107
  }
92
- if (typeof project.entry !== "string" || project.entry.length === 0) {
93
- throw configurationError("project.entry must be a non-empty string");
108
+ if (typeof workspace.entry !== "string" || workspace.entry.length === 0) {
109
+ throw configurationError("workspace.entry must be a non-empty string");
94
110
  }
95
- if (!project.sources || typeof project.sources !== "object" || Array.isArray(project.sources)) {
96
- throw configurationError("project.sources must be an object of paths to source strings");
111
+ if (!workspace.sources || typeof workspace.sources !== "object" || Array.isArray(workspace.sources)) {
112
+ throw configurationError("workspace.sources must be an object of paths to source strings");
97
113
  }
98
- for (const [path, source] of Object.entries(project.sources)) {
114
+ for (const [path, source] of Object.entries(workspace.sources)) {
99
115
  if (typeof source !== "string") {
100
- throw configurationError(`project source '${path}' must be a string`);
116
+ throw configurationError(`workspace source '${path}' must be a string`);
101
117
  }
102
118
  }
103
119
 
104
120
  const compile = normalizeCompileOptions(options);
105
- let mir;
121
+ let frontendCompilation;
122
+ try {
123
+ frontendCompilation = this.frontend.compile_source_workspace_to_mir_messagepack(
124
+ workspace.entry,
125
+ JSON.stringify(workspace.sources),
126
+ compile.sampleRate,
127
+ compile.blockSize,
128
+ );
129
+ } catch (error) {
130
+ throw diagnosticsFromFrontend(error);
131
+ }
132
+ const { mir, sourceFiles, sourceGraph } = consumeFrontendCompilation(frontendCompilation);
133
+ const artifact = compileMirTransport(
134
+ mir,
135
+ compile.codegen,
136
+ this.compileTrustedMir,
137
+ sourceFiles,
138
+ );
139
+ return { artifact, sourceFiles, sourceGraph };
140
+ }
141
+
142
+ async compileProjectImage(imageBytes, options = {}) {
143
+ const bytes = normalizeBytes(imageBytes, "project image");
144
+ const compile = normalizeCompileOptions(options);
145
+ let frontendCompilation;
106
146
  try {
107
- mir = this.frontend.compile_project_to_mir_messagepack(
108
- project.entry,
109
- JSON.stringify(project.sources),
147
+ frontendCompilation = this.frontend.compile_project_image_to_mir_messagepack(
148
+ bytes,
110
149
  compile.sampleRate,
111
150
  compile.blockSize,
112
151
  );
113
152
  } catch (error) {
114
153
  throw diagnosticsFromFrontend(error);
115
154
  }
116
- return compileMirTransport(mir, compile.codegen, this.compileTrustedMir);
155
+ const { mir, sourceFiles, sourceGraph } = consumeFrontendCompilation(frontendCompilation);
156
+ const artifact = compileMirTransport(
157
+ mir,
158
+ compile.codegen,
159
+ this.compileTrustedMir,
160
+ sourceFiles,
161
+ );
162
+ return { artifact, sourceFiles, sourceGraph };
163
+ }
164
+
165
+ async createProjectImage(sourceGraph, buffers = new Map()) {
166
+ const graph = normalizeSourceGraph(sourceGraph);
167
+ const builder = new this.frontend.WebProjectImageBuilder(JSON.stringify(graph));
168
+ try {
169
+ for (const [name, bytes] of normalizeBufferAssetEntries(buffers)) {
170
+ builder.add_buffer(name, bytes);
171
+ }
172
+ const bytes = builder.serialize();
173
+ return {
174
+ bytes,
175
+ ...normalizeProjectImageInfo(JSON.parse(this.frontend.inspect_project_image(bytes))),
176
+ };
177
+ } catch (cause) {
178
+ throw new OndaCompilerError("failed to create Onda project image", { cause });
179
+ } finally {
180
+ builder.free();
181
+ }
182
+ }
183
+
184
+ async inspectProjectImage(imageBytes) {
185
+ try {
186
+ return normalizeProjectImageInfo(JSON.parse(this.frontend.inspect_project_image(
187
+ normalizeBytes(imageBytes, "project image"),
188
+ )));
189
+ } catch (cause) {
190
+ throw new OndaCompilerError("failed to inspect Onda project image", { cause });
191
+ }
192
+ }
193
+
194
+ async loadProjectFiles(files, projectFilePath = null) {
195
+ const builder = new this.frontend.WebMaterializedProjectBuilder();
196
+ try {
197
+ if (projectFilePath !== null) {
198
+ builder.select_project(normalizeProjectFilePath(projectFilePath));
199
+ }
200
+ for (const [path, bytes] of normalizeProjectFileEntries(files)) {
201
+ builder.add_file(path, bytes);
202
+ }
203
+ const bytes = builder.serialize();
204
+ return {
205
+ bytes,
206
+ ...normalizeProjectImageInfo(JSON.parse(this.frontend.inspect_project_image(bytes))),
207
+ };
208
+ } catch (cause) {
209
+ throw new OndaCompilerError("failed to load Onda project files", { cause });
210
+ } finally {
211
+ builder.free();
212
+ }
213
+ }
214
+
215
+ async materializeProjectImage(imageBytes, assetFileNames = new Map()) {
216
+ let plan;
217
+ try {
218
+ plan = this.frontend.materialize_project_image(
219
+ normalizeBytes(imageBytes, "project image"),
220
+ JSON.stringify(Object.fromEntries(normalizeAssetFileNameEntries(assetFileNames))),
221
+ );
222
+ const files = [];
223
+ for (let index = 0; index < plan.file_count(); index += 1) {
224
+ files.push({ path: plan.file_path(index), bytes: plan.file_bytes(index) });
225
+ }
226
+ return { directories: JSON.parse(plan.directories_json()), files };
227
+ } catch (cause) {
228
+ throw new OndaCompilerError("failed to materialize Onda project image", { cause });
229
+ } finally {
230
+ plan?.free();
231
+ }
232
+ }
233
+
234
+ async encodeBufferAsset(binding) {
235
+ const normalized = normalizeBufferBinding(binding);
236
+ try {
237
+ return this.frontend.encode_buffer_asset(
238
+ normalized.element,
239
+ normalized.frames,
240
+ normalized.channels,
241
+ normalized.sampleRate,
242
+ encodeCanonicalPayload(normalized.element, normalized.data),
243
+ );
244
+ } catch (cause) {
245
+ throw new OndaCompilerError("failed to encode Onda buffer asset", { cause });
246
+ }
247
+ }
248
+
249
+ async decodeBufferAsset(bytes) {
250
+ return this.#decodeBuffer(
251
+ () => this.frontend.decode_buffer_asset(normalizeBytes(bytes, "buffer asset")),
252
+ "failed to decode Onda buffer asset",
253
+ );
254
+ }
255
+
256
+ async decodeBufferFile(bytes, path = "buffer") {
257
+ return this.#decodeBuffer(
258
+ () => this.frontend.decode_buffer_file(
259
+ normalizeBytes(bytes, "buffer file"),
260
+ String(path),
261
+ ),
262
+ "failed to decode buffer file",
263
+ );
264
+ }
265
+
266
+ async #decodeBuffer(decode, message) {
267
+ let decoded;
268
+ try {
269
+ decoded = decode();
270
+ const element = decoded.element();
271
+ const payload = decoded.canonical_payload();
272
+ return {
273
+ element,
274
+ frames: decoded.frames(),
275
+ channels: decoded.channels(),
276
+ sampleRate: decoded.sample_rate(),
277
+ data: decodeCanonicalPayload(element, payload),
278
+ };
279
+ } catch (cause) {
280
+ throw new OndaCompilerError(message, { cause });
281
+ } finally {
282
+ decoded?.free();
283
+ }
284
+ }
285
+
286
+ async projectCapabilities() {
287
+ return {
288
+ imageFormatVersion: this.frontend.project_image_format_version(),
289
+ bufferAssetFormatVersion: this.frontend.buffer_asset_format_version(),
290
+ stdlibDigest: this.frontend.current_stdlib_digest(),
291
+ };
117
292
  }
118
293
 
119
294
  async sendLspMessage(message) {
@@ -167,8 +342,44 @@ class WorkerOndaCompiler {
167
342
  return this.request("compileSource", { source, options });
168
343
  }
169
344
 
170
- compileProject(project, options = {}) {
171
- return this.request("compileProject", { project, options });
345
+ compileWorkspace(workspace, options = {}) {
346
+ return this.request("compileWorkspace", { workspace, options });
347
+ }
348
+
349
+ compileProjectImage(imageBytes, options = {}) {
350
+ return this.request("compileProjectImage", { imageBytes, options });
351
+ }
352
+
353
+ createProjectImage(sourceGraph, buffers = new Map()) {
354
+ return this.request("createProjectImage", { sourceGraph, buffers });
355
+ }
356
+
357
+ inspectProjectImage(imageBytes) {
358
+ return this.request("inspectProjectImage", { imageBytes });
359
+ }
360
+
361
+ loadProjectFiles(files, projectFilePath = null) {
362
+ return this.request("loadProjectFiles", { files, projectFilePath });
363
+ }
364
+
365
+ materializeProjectImage(imageBytes, assetFileNames = new Map()) {
366
+ return this.request("materializeProjectImage", { imageBytes, assetFileNames });
367
+ }
368
+
369
+ encodeBufferAsset(binding) {
370
+ return this.request("encodeBufferAsset", { binding });
371
+ }
372
+
373
+ decodeBufferAsset(bytes) {
374
+ return this.request("decodeBufferAsset", { bytes });
375
+ }
376
+
377
+ decodeBufferFile(bytes, path = "buffer") {
378
+ return this.request("decodeBufferFile", { bytes, path });
379
+ }
380
+
381
+ projectCapabilities() {
382
+ return this.request("projectCapabilities");
172
383
  }
173
384
 
174
385
  sendLspMessage(message) {
@@ -212,7 +423,10 @@ class WorkerOndaCompiler {
212
423
  return;
213
424
  }
214
425
  const error = message.error?.diagnostics
215
- ? new OndaCompileError(message.error.diagnostics)
426
+ ? new OndaCompileError(message.error.diagnostics, {
427
+ sourceFiles: message.error.sourceFiles,
428
+ unresolvedSourceFiles: message.error.unresolvedSourceFiles,
429
+ })
216
430
  : new OndaCompilerError(message.error?.message ?? "compiler worker failed");
217
431
  if (message.error?.name) error.name = message.error.name;
218
432
  if (message.error?.stack) error.stack = message.error.stack;
@@ -310,7 +524,20 @@ function normalizeCompileOptions(options) {
310
524
  return { sampleRate, blockSize, codegen: options.codegen ?? {} };
311
525
  }
312
526
 
313
- function compileMirTransport(mir, codegen, compileTrustedMir) {
527
+ function consumeFrontendCompilation(compilation) {
528
+ try {
529
+ const mir = compilation.take_mir();
530
+ const sourceFiles = normalizeSourceFiles(JSON.parse(compilation.source_files_json()));
531
+ const sourceGraph = normalizeReturnedSourceGraph(
532
+ JSON.parse(compilation.source_image_json()),
533
+ );
534
+ return { mir, sourceFiles, sourceGraph };
535
+ } finally {
536
+ compilation.free();
537
+ }
538
+ }
539
+
540
+ function compileMirTransport(mir, codegen, compileTrustedMir, sourceFiles) {
314
541
  try {
315
542
  return compileTrustedMir(mir, codegen);
316
543
  } catch (cause) {
@@ -325,7 +552,7 @@ function compileMirTransport(mir, codegen, compileTrustedMir) {
325
552
  end_line: 0,
326
553
  end_column: 0,
327
554
  trace: [],
328
- }], { cause });
555
+ }], { cause, sourceFiles });
329
556
  }
330
557
  }
331
558
 
@@ -333,9 +560,16 @@ function diagnosticsFromFrontend(error) {
333
560
  const encoded = typeof error === "string" ? error : error?.message;
334
561
  if (typeof encoded === "string") {
335
562
  try {
336
- const diagnostics = JSON.parse(encoded);
337
- if (Array.isArray(diagnostics)) {
338
- return new OndaCompileError(diagnostics, { cause: error });
563
+ const failure = JSON.parse(encoded);
564
+ if (Array.isArray(failure)) {
565
+ return new OndaCompileError(failure, { cause: error });
566
+ }
567
+ if (failure && Array.isArray(failure.diagnostics)) {
568
+ return new OndaCompileError(failure.diagnostics, {
569
+ cause: error,
570
+ sourceFiles: failure.source_files,
571
+ unresolvedSourceFiles: failure.unresolved_source_files,
572
+ });
339
573
  }
340
574
  } catch {}
341
575
  }
@@ -382,3 +616,198 @@ function normalizeDiagnostics(diagnostics) {
382
616
  : [],
383
617
  }));
384
618
  }
619
+
620
+ function normalizeSourceFiles(sourceFiles) {
621
+ if (!Array.isArray(sourceFiles)) return [];
622
+ return sourceFiles.map((path) => String(path));
623
+ }
624
+
625
+ function normalizeBytes(value, context) {
626
+ if (value instanceof Uint8Array) return value;
627
+ if (value instanceof ArrayBuffer) return new Uint8Array(value);
628
+ if (ArrayBuffer.isView(value)) {
629
+ return new Uint8Array(value.buffer, value.byteOffset, value.byteLength);
630
+ }
631
+ throw new OndaCompilerError(`${context} must be an ArrayBuffer or typed-array view`);
632
+ }
633
+
634
+ function normalizeSourceGraph(graph) {
635
+ if (!graph || typeof graph !== "object" || Array.isArray(graph)) {
636
+ throw new OndaCompilerError("source graph must be an object");
637
+ }
638
+ const entry = String(graph.entry ?? "");
639
+ const stdlibDigest = String(graph.stdlibDigest ?? graph.stdlib_digest ?? "");
640
+ if (!entry || !stdlibDigest) {
641
+ throw new OndaCompilerError("source graph requires entry and stdlibDigest");
642
+ }
643
+ const documents = Array.isArray(graph.documents) ? graph.documents.map((document) => ({
644
+ path: String(document?.path ?? ""),
645
+ contents: String(document?.contents ?? ""),
646
+ })) : [];
647
+ const resolutions = Array.isArray(graph.resolutions) ? graph.resolutions.map((resolution) => ({
648
+ source: String(resolution?.source ?? ""),
649
+ kind: String(resolution?.kind ?? ""),
650
+ specifier: String(resolution?.specifier ?? ""),
651
+ target: String(resolution?.target ?? ""),
652
+ })) : [];
653
+ return {
654
+ entry,
655
+ stdlib_digest: stdlibDigest,
656
+ documents,
657
+ resolutions,
658
+ };
659
+ }
660
+
661
+ function normalizeReturnedSourceGraph(graph) {
662
+ if (!graph) return null;
663
+ return {
664
+ entry: String(graph.entry),
665
+ stdlibDigest: String(graph.stdlib_digest),
666
+ documents: graph.documents.map((document) => ({
667
+ path: String(document.path),
668
+ contents: String(document.contents),
669
+ })),
670
+ resolutions: graph.resolutions.map((resolution) => ({
671
+ source: String(resolution.source),
672
+ kind: String(resolution.kind),
673
+ specifier: String(resolution.specifier),
674
+ target: String(resolution.target),
675
+ })),
676
+ };
677
+ }
678
+
679
+ function normalizeProjectImageInfo(info) {
680
+ return {
681
+ formatVersion: Number(info.format_version),
682
+ contentDigest: String(info.content_digest),
683
+ sourceGraph: normalizeReturnedSourceGraph(info.sources),
684
+ buffers: info.buffers.map((buffer) => ({
685
+ name: String(buffer.name),
686
+ assetId: String(buffer.asset_id),
687
+ element: String(buffer.element),
688
+ frames: Number(buffer.frames),
689
+ channels: Number(buffer.channels),
690
+ sampleRate: Number(buffer.sample_rate),
691
+ })),
692
+ };
693
+ }
694
+
695
+ function normalizeBufferAssetEntries(buffers) {
696
+ const entries = buffers instanceof Map
697
+ ? [...buffers]
698
+ : buffers && typeof buffers === "object" && !Array.isArray(buffers)
699
+ ? Object.entries(buffers)
700
+ : null;
701
+ if (!entries) throw new OndaCompilerError("project buffers must be a Map or object");
702
+ return entries.map(([name, bytes]) => {
703
+ if (typeof name !== "string" || !name) {
704
+ throw new OndaCompilerError("project buffer names must be non-empty strings");
705
+ }
706
+ return [name, normalizeBytes(bytes, `project buffer '${name}'`)];
707
+ });
708
+ }
709
+
710
+ function normalizeAssetFileNameEntries(fileNames) {
711
+ const entries = fileNames instanceof Map
712
+ ? [...fileNames]
713
+ : fileNames && typeof fileNames === "object" && !Array.isArray(fileNames)
714
+ ? Object.entries(fileNames)
715
+ : null;
716
+ if (!entries) throw new OndaCompilerError("asset filenames must be a Map or object");
717
+ return entries.map(([name, fileName]) => {
718
+ if (typeof name !== "string" || !name || typeof fileName !== "string" || !fileName) {
719
+ throw new OndaCompilerError("asset filenames require non-empty buffer names and filenames");
720
+ }
721
+ return [name, fileName];
722
+ });
723
+ }
724
+
725
+ function normalizeProjectFilePath(path) {
726
+ if (typeof path !== "string" || !path) {
727
+ throw new OndaCompilerError("selected project manifest must be a non-empty string");
728
+ }
729
+ return path;
730
+ }
731
+
732
+ function normalizeProjectFileEntries(files) {
733
+ const entries = files instanceof Map
734
+ ? [...files]
735
+ : files && typeof files === "object" && !Array.isArray(files)
736
+ ? Object.entries(files)
737
+ : null;
738
+ if (!entries) throw new OndaCompilerError("project files must be a Map or object");
739
+ return entries.map(([path, bytes]) => {
740
+ if (typeof path !== "string" || !path) {
741
+ throw new OndaCompilerError("project file paths must be non-empty strings");
742
+ }
743
+ return [path, normalizeBytes(bytes, `project file '${path}'`)];
744
+ });
745
+ }
746
+
747
+ function normalizeBufferBinding(binding) {
748
+ if (!binding || typeof binding !== "object" || Array.isArray(binding)) {
749
+ throw new OndaCompilerError("buffer binding must be an object");
750
+ }
751
+ const element = String(binding.element ?? binding.scalar ?? "");
752
+ const frames = Number(binding.frames);
753
+ const channels = Number(binding.channels);
754
+ const sampleRate = Number(binding.sampleRate);
755
+ const data = binding.data;
756
+ const expectedConstructor = {
757
+ bool: Uint8Array,
758
+ i32: Int32Array,
759
+ i64: BigInt64Array,
760
+ f32: Float32Array,
761
+ f64: Float64Array,
762
+ }[element];
763
+ if (!expectedConstructor || !(data instanceof expectedConstructor)) {
764
+ throw new OndaCompilerError(`buffer element '${element}' requires ${expectedConstructor?.name ?? "a supported typed array"}`);
765
+ }
766
+ if (
767
+ !Number.isInteger(frames) || frames <= 0
768
+ || !Number.isInteger(channels) || channels <= 0
769
+ || !Number.isFinite(sampleRate) || sampleRate <= 0
770
+ || data.length !== frames * channels
771
+ ) {
772
+ throw new OndaCompilerError("buffer binding has an invalid shape or sample rate");
773
+ }
774
+ return { element, frames, channels, sampleRate, data };
775
+ }
776
+
777
+ function encodeCanonicalPayload(element, data) {
778
+ if (element === "bool") {
779
+ if (data.some((value) => value > 1)) {
780
+ throw new OndaCompilerError("bool buffer values must be 0 or 1");
781
+ }
782
+ return data.slice();
783
+ }
784
+ const bytes = new Uint8Array(data.length * data.BYTES_PER_ELEMENT);
785
+ const view = new DataView(bytes.buffer);
786
+ for (let index = 0; index < data.length; index += 1) {
787
+ const offset = index * data.BYTES_PER_ELEMENT;
788
+ if (element === "i32") view.setInt32(offset, data[index], true);
789
+ else if (element === "i64") view.setBigInt64(offset, data[index], true);
790
+ else if (element === "f32") view.setFloat32(offset, data[index], true);
791
+ else view.setFloat64(offset, data[index], true);
792
+ }
793
+ return bytes;
794
+ }
795
+
796
+ function decodeCanonicalPayload(element, payload) {
797
+ if (element === "bool") return payload.slice();
798
+ const elementBytes = element === "i32" || element === "f32" ? 4 : 8;
799
+ const length = payload.byteLength / elementBytes;
800
+ const output = element === "i32" ? new Int32Array(length)
801
+ : element === "i64" ? new BigInt64Array(length)
802
+ : element === "f32" ? new Float32Array(length)
803
+ : new Float64Array(length);
804
+ const view = new DataView(payload.buffer, payload.byteOffset, payload.byteLength);
805
+ for (let index = 0; index < length; index += 1) {
806
+ const offset = index * elementBytes;
807
+ output[index] = element === "i32" ? view.getInt32(offset, true)
808
+ : element === "i64" ? view.getBigInt64(offset, true)
809
+ : element === "f32" ? view.getFloat32(offset, true)
810
+ : view.getFloat64(offset, true);
811
+ }
812
+ return output;
813
+ }
package/src/worker.js CHANGED
@@ -12,19 +12,74 @@ globalThis.addEventListener("message", async (event) => {
12
12
  return;
13
13
  }
14
14
  if (message.type === "compileSource") {
15
- const artifact = await (await compiler()).compileSource(
15
+ const result = await (await compiler()).compileSource(
16
16
  message.source,
17
17
  message.options,
18
18
  );
19
- respond(requestId, artifact, [artifact.wasm.buffer]);
19
+ respond(requestId, result, [result.artifact.wasm.buffer]);
20
20
  return;
21
21
  }
22
- if (message.type === "compileProject") {
23
- const artifact = await (await compiler()).compileProject(
24
- message.project,
22
+ if (message.type === "compileWorkspace") {
23
+ const result = await (await compiler()).compileWorkspace(
24
+ message.workspace,
25
25
  message.options,
26
26
  );
27
- respond(requestId, artifact, [artifact.wasm.buffer]);
27
+ respond(requestId, result, [result.artifact.wasm.buffer]);
28
+ return;
29
+ }
30
+ if (message.type === "compileProjectImage") {
31
+ const result = await (await compiler()).compileProjectImage(
32
+ message.imageBytes,
33
+ message.options,
34
+ );
35
+ respond(requestId, result, [result.artifact.wasm.buffer]);
36
+ return;
37
+ }
38
+ if (message.type === "createProjectImage") {
39
+ const result = await (await compiler()).createProjectImage(
40
+ message.sourceGraph,
41
+ message.buffers,
42
+ );
43
+ respond(requestId, result, [result.bytes.buffer]);
44
+ return;
45
+ }
46
+ if (message.type === "inspectProjectImage") {
47
+ respond(requestId, await (await compiler()).inspectProjectImage(message.imageBytes));
48
+ return;
49
+ }
50
+ if (message.type === "loadProjectFiles") {
51
+ const result = await (await compiler()).loadProjectFiles(
52
+ message.files,
53
+ message.projectFilePath,
54
+ );
55
+ respond(requestId, result, [result.bytes.buffer]);
56
+ return;
57
+ }
58
+ if (message.type === "materializeProjectImage") {
59
+ const result = await (await compiler()).materializeProjectImage(
60
+ message.imageBytes,
61
+ message.assetFileNames,
62
+ );
63
+ respond(requestId, result, result.files.map((file) => file.bytes.buffer));
64
+ return;
65
+ }
66
+ if (message.type === "encodeBufferAsset") {
67
+ const result = await (await compiler()).encodeBufferAsset(message.binding);
68
+ respond(requestId, result, [result.buffer]);
69
+ return;
70
+ }
71
+ if (message.type === "decodeBufferAsset") {
72
+ const result = await (await compiler()).decodeBufferAsset(message.bytes);
73
+ respond(requestId, result, [result.data.buffer]);
74
+ return;
75
+ }
76
+ if (message.type === "decodeBufferFile") {
77
+ const result = await (await compiler()).decodeBufferFile(message.bytes, message.path);
78
+ respond(requestId, result, [result.data.buffer]);
79
+ return;
80
+ }
81
+ if (message.type === "projectCapabilities") {
82
+ respond(requestId, await (await compiler()).projectCapabilities());
28
83
  return;
29
84
  }
30
85
  if (message.type === "lspMessage") {
@@ -53,6 +108,8 @@ globalThis.addEventListener("message", async (event) => {
53
108
  message: error?.message ?? String(error),
54
109
  stack: error?.stack,
55
110
  diagnostics: error?.diagnostics,
111
+ sourceFiles: error?.sourceFiles,
112
+ unresolvedSourceFiles: error?.unresolvedSourceFiles,
56
113
  },
57
114
  });
58
115
  }