1+ import * as path from 'node:path' ;
12import BetterSQLite3Database , { Database } from '@powersync/better-sqlite3' ;
23import * as Comlink from 'comlink' ;
34import { parentPort , threadId } from 'node:worker_threads' ;
@@ -81,10 +82,16 @@ class BlockingAsyncDatabase implements AsyncDatabase {
8182}
8283
8384class BetterSqliteWorker implements AsyncDatabaseOpener {
85+ options : PowerSyncWorkerOptions ;
86+
87+ constructor ( options : PowerSyncWorkerOptions ) {
88+ this . options = options ;
89+ }
90+
8491 async open ( path : string , isWriter : boolean ) : Promise < AsyncDatabase > {
8592 const baseDB = new BetterSQLite3Database ( path ) ;
8693 baseDB . pragma ( 'journal_mode = WAL' ) ;
87- loadExtension ( baseDB ) ;
94+ baseDB . loadExtension ( this . options . extensionPath ( ) , 'sqlite3_powersync_init' ) ;
8895 if ( ! isWriter ) {
8996 baseDB . pragma ( 'query_only = true' ) ;
9097 }
@@ -96,21 +103,43 @@ class BetterSqliteWorker implements AsyncDatabaseOpener {
96103 }
97104}
98105
99- const loadExtension = ( db : Database ) => {
100- const platform = OS . platform ( ) ;
101- let extensionPath : string ;
102- if ( platform === 'win32' ) {
103- extensionPath = 'powersync.dll' ;
104- } else if ( platform === 'linux' ) {
105- extensionPath = 'libpowersync.so' ;
106- } else if ( platform === 'darwin' ) {
107- extensionPath = 'libpowersync.dylib' ;
108- } else {
109- throw 'Unknown platform, PowerSync for Node.js currently supports Windows, Linux and macOS.' ;
110- }
106+ export interface PowerSyncWorkerOptions {
107+ /**
108+ * A function responsible for finding the powersync DLL/so/dylib file.
109+ *
110+ * @returns The absolute path of the PowerSync SQLite core extensions library.
111+ */
112+ extensionPath : ( ) => string ;
113+ }
111114
112- const resolved = url . fileURLToPath ( new URL ( `../${ extensionPath } ` , import . meta. url ) ) ;
113- db . loadExtension ( resolved , 'sqlite3_powersync_init' ) ;
114- } ;
115+ export function startPowerSyncWorker ( options ?: Partial < PowerSyncWorkerOptions > ) {
116+ const resolvedOptions : PowerSyncWorkerOptions = {
117+ extensionPath ( ) {
118+ const isCommonJsModule = import . meta. isBundlingToCommonJs ?? false ;
119+
120+ const platform = OS . platform ( ) ;
121+ let extensionPath : string ;
122+ if ( platform === 'win32' ) {
123+ extensionPath = 'powersync.dll' ;
124+ } else if ( platform === 'linux' ) {
125+ extensionPath = 'libpowersync.so' ;
126+ } else if ( platform === 'darwin' ) {
127+ extensionPath = 'libpowersync.dylib' ;
128+ } else {
129+ throw 'Unknown platform, PowerSync for Node.js currently supports Windows, Linux and macOS.' ;
130+ }
131+
132+ let resolved : string ;
133+ if ( isCommonJsModule ) {
134+ resolved = path . resolve ( __dirname , '../lib/' , extensionPath ) ;
135+ } else {
136+ resolved = url . fileURLToPath ( new URL ( `../${ extensionPath } ` , import . meta. url ) ) ;
137+ }
115138
116- Comlink . expose ( new BetterSqliteWorker ( ) , parentPort ! as Comlink . Endpoint ) ;
139+ return resolved ;
140+ } ,
141+ ...options ,
142+ } ;
143+
144+ Comlink . expose ( new BetterSqliteWorker ( resolvedOptions ) , parentPort ! as Comlink . Endpoint ) ;
145+ }
0 commit comments