From b6cd4350689c18b609d9c591d28fa5c7f5e55abd Mon Sep 17 00:00:00 2001 From: Kacper Kula Date: Sun, 26 Apr 2026 16:06:18 +0100 Subject: [PATCH] fix: wa-sqlite initialisation fix --- esbuild.config.mjs | 14 ++++++++++---- .../database/sqlocal/sqlocalWorkerDatabase.ts | 12 ++---------- .../__tests__/__mocks__/wa-sqlite-wasm-url.ts | 8 ++++---- .../explorer/database/waSqliteMemoryDatabase.ts | 12 ++---------- 4 files changed, 18 insertions(+), 28 deletions(-) diff --git a/esbuild.config.mjs b/esbuild.config.mjs index fb1794d..b58689d 100644 --- a/esbuild.config.mjs +++ b/esbuild.config.mjs @@ -112,10 +112,13 @@ const workerPlugin = { const wasmPath = join(process.cwd(), 'node_modules/wa-sqlite/dist/wa-sqlite-async.wasm'); const wasmContents = readFileSync(wasmPath); const wasmBase64 = wasmContents.toString('base64'); - const wasmDataUrl = `data:application/wasm;base64,${wasmBase64}`; return { - contents: `export default ${JSON.stringify(wasmDataUrl)};`, + contents: ` + const wasmBase64 = "${wasmBase64}"; + const wasmBinary = Uint8Array.from(atob(wasmBase64), c => c.charCodeAt(0)); + export default wasmBinary; + `, loader: 'js', }; }); @@ -158,10 +161,13 @@ const workerPlugin = { const wasmPath = join(process.cwd(), 'node_modules/wa-sqlite/dist/wa-sqlite-async.wasm'); const wasmContents = readFileSync(wasmPath); const wasmBase64 = wasmContents.toString('base64'); - const wasmDataUrl = `data:application/wasm;base64,${wasmBase64}`; return { - contents: `export default ${JSON.stringify(wasmDataUrl)};`, + contents: ` + const wasmBase64 = "${wasmBase64}"; + const wasmBinary = Uint8Array.from(atob(wasmBase64), c => c.charCodeAt(0)); + export default wasmBinary; + `, loader: 'js', }; }); diff --git a/src/modules/database/sqlocal/sqlocalWorkerDatabase.ts b/src/modules/database/sqlocal/sqlocalWorkerDatabase.ts index cc39ec6..f7c1085 100644 --- a/src/modules/database/sqlocal/sqlocalWorkerDatabase.ts +++ b/src/modules/database/sqlocal/sqlocalWorkerDatabase.ts @@ -7,7 +7,7 @@ import { sanitise } from "../../../utils/sanitiseColumn"; // Get the WASM URL from the virtual module // @ts-ignore -import wasmUrl from 'virtual:wa-sqlite-wasm-url'; +import wasmBinary from 'virtual:wa-sqlite-wasm-url'; /** * Retry an async operation with exponential backoff @@ -110,15 +110,7 @@ export class SqlocalWorkerDatabase { } try { - // Initialize the module with bundled WASM - const asyncModule = await SQLiteAsyncESMFactory({ - locateFile: (file: string) => { - if (file.endsWith('.wasm')) { - return wasmUrl; - } - return file; - } - }); + const asyncModule = await SQLiteAsyncESMFactory({ wasmBinary, locateFile: (file: string) => file }); // Use Factory to get the actual sqlite3 API this.sqlite3 = SQLite.Factory(asyncModule); diff --git a/src/modules/explorer/database/__tests__/__mocks__/wa-sqlite-wasm-url.ts b/src/modules/explorer/database/__tests__/__mocks__/wa-sqlite-wasm-url.ts index 7a18853..0368045 100644 --- a/src/modules/explorer/database/__tests__/__mocks__/wa-sqlite-wasm-url.ts +++ b/src/modules/explorer/database/__tests__/__mocks__/wa-sqlite-wasm-url.ts @@ -1,10 +1,10 @@ // Mock for virtual:wa-sqlite-wasm-url used in tests -// Returns a file:// URL that works with the fetch polyfill in jest.setup.mjs +// Returns the WASM binary as Uint8Array (same as production build) import { join } from 'path'; -import { pathToFileURL } from 'url'; +import { readFileSync } from 'fs'; const wasmPath = join(process.cwd(), 'node_modules/wa-sqlite/dist/wa-sqlite-async.wasm'); -const wasmUrl = pathToFileURL(wasmPath).href; +const wasmBinary = new Uint8Array(readFileSync(wasmPath)); -export default wasmUrl; +export default wasmBinary; diff --git a/src/modules/explorer/database/waSqliteMemoryDatabase.ts b/src/modules/explorer/database/waSqliteMemoryDatabase.ts index 5b26577..0777cad 100644 --- a/src/modules/explorer/database/waSqliteMemoryDatabase.ts +++ b/src/modules/explorer/database/waSqliteMemoryDatabase.ts @@ -4,7 +4,7 @@ import SQLiteAsyncESMFactory from 'wa-sqlite/dist/wa-sqlite-async.mjs'; import * as SQLite from 'wa-sqlite'; import { MemoryAsyncVFS } from 'wa-sqlite/src/examples/MemoryAsyncVFS.js'; // @ts-ignore - Virtual module from esbuild -import wasmUrl from 'virtual:wa-sqlite-wasm-url'; +import wasmBinary from 'virtual:wa-sqlite-wasm-url'; type ParamsObject = Record; @@ -33,15 +33,7 @@ export class WaSqliteMemoryDatabase { throw new Error('Invalid SQLite database file format'); } - // Initialize wa-sqlite - const asyncModule = await SQLiteAsyncESMFactory({ - locateFile: (file: string) => { - if (file.endsWith('.wasm')) { - return wasmUrl; - } - return file; - } - }); + const asyncModule = await SQLiteAsyncESMFactory({ wasmBinary, locateFile: (file: string) => file }); this.sqlite3 = SQLite.Factory(asyncModule);