@powersync/react-native 0.0.0-dev-20260525085311 → 0.0.0-dev-20260630141119

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.
Files changed (64) hide show
  1. package/README.md +72 -6
  2. package/android/build.gradle +90 -0
  3. package/android/gradle.properties +4 -0
  4. package/android/src/main/AndroidManifest.xml +3 -0
  5. package/android/src/main/AndroidManifestNew.xml +2 -0
  6. package/android/src/main/java/com/powersync/opsqlite/PowerSyncOpSqlitePackage.kt +46 -0
  7. package/ios/PowerSyncOpSqlite.h +5 -0
  8. package/ios/PowerSyncOpSqlite.mm +6 -0
  9. package/lib/db/PowerSyncDatabase.d.ts +9 -10
  10. package/lib/db/PowerSyncDatabase.js +33 -25
  11. package/lib/db/PowerSyncDatabase.js.map +1 -1
  12. package/lib/db/adapters/op-sqlite/OPSQLiteConnection.d.ts +25 -0
  13. package/lib/db/adapters/op-sqlite/OPSQLiteConnection.js +63 -0
  14. package/lib/db/adapters/op-sqlite/OPSQLiteConnection.js.map +1 -0
  15. package/lib/db/adapters/op-sqlite/OPSqliteAdapter.d.ts +32 -0
  16. package/lib/db/adapters/op-sqlite/OPSqliteAdapter.js +203 -0
  17. package/lib/db/adapters/op-sqlite/OPSqliteAdapter.js.map +1 -0
  18. package/lib/db/adapters/op-sqlite/OPSqliteDBOpenFactory.d.ts +11 -0
  19. package/lib/db/adapters/op-sqlite/OPSqliteDBOpenFactory.js +21 -0
  20. package/lib/db/adapters/op-sqlite/OPSqliteDBOpenFactory.js.map +1 -0
  21. package/lib/db/adapters/op-sqlite/SqliteOptions.d.ts +68 -0
  22. package/lib/db/adapters/op-sqlite/SqliteOptions.js +37 -0
  23. package/lib/db/adapters/op-sqlite/SqliteOptions.js.map +1 -0
  24. package/lib/index.d.ts +1 -3
  25. package/lib/index.js +0 -3
  26. package/lib/index.js.map +1 -1
  27. package/lib/sync/bucket/ReactNativeBucketStorageAdapter.d.ts +1 -1
  28. package/lib/sync/bucket/ReactNativeBucketStorageAdapter.js +1 -1
  29. package/lib/sync/bucket/ReactNativeBucketStorageAdapter.js.map +1 -1
  30. package/lib/sync/stream/ReactNativeRemote.d.ts +11 -11
  31. package/lib/sync/stream/ReactNativeRemote.js +42 -66
  32. package/lib/sync/stream/ReactNativeRemote.js.map +1 -1
  33. package/lib/sync/stream/ReactNativeStreamingSyncImplementation.d.ts +2 -1
  34. package/lib/sync/stream/ReactNativeStreamingSyncImplementation.js +2 -1
  35. package/lib/sync/stream/ReactNativeStreamingSyncImplementation.js.map +1 -1
  36. package/lib/sync/stream/fetch.d.ts +13 -0
  37. package/lib/sync/stream/fetch.js +31 -0
  38. package/lib/sync/stream/fetch.js.map +1 -0
  39. package/package.json +20 -33
  40. package/powersync-react-native.podspec +32 -0
  41. package/src/db/PowerSyncDatabase.ts +58 -31
  42. package/src/db/adapters/op-sqlite/OPSQLiteConnection.ts +95 -0
  43. package/src/db/adapters/op-sqlite/OPSqliteAdapter.ts +245 -0
  44. package/src/db/adapters/op-sqlite/OPSqliteDBOpenFactory.ts +25 -0
  45. package/src/db/adapters/op-sqlite/SqliteOptions.ts +93 -0
  46. package/src/index.ts +1 -3
  47. package/src/sync/bucket/ReactNativeBucketStorageAdapter.ts +1 -1
  48. package/src/sync/stream/ReactNativeRemote.ts +49 -86
  49. package/src/sync/stream/ReactNativeStreamingSyncImplementation.ts +4 -4
  50. package/src/sync/stream/fetch.ts +45 -0
  51. package/dist/index.js +0 -8741
  52. package/dist/index.js.map +0 -1
  53. package/lib/db/adapters/react-native-quick-sqlite/RNQSDBAdapter.d.ts +0 -55
  54. package/lib/db/adapters/react-native-quick-sqlite/RNQSDBAdapter.js +0 -66
  55. package/lib/db/adapters/react-native-quick-sqlite/RNQSDBAdapter.js.map +0 -1
  56. package/lib/db/adapters/react-native-quick-sqlite/RNQSDBOpenFactory.d.ts +0 -19
  57. package/lib/db/adapters/react-native-quick-sqlite/RNQSDBOpenFactory.js +0 -34
  58. package/lib/db/adapters/react-native-quick-sqlite/RNQSDBOpenFactory.js.map +0 -1
  59. package/lib/db/adapters/react-native-quick-sqlite/ReactNativeQuickSQLiteOpenFactory.d.ts +0 -9
  60. package/lib/db/adapters/react-native-quick-sqlite/ReactNativeQuickSQLiteOpenFactory.js +0 -45
  61. package/lib/db/adapters/react-native-quick-sqlite/ReactNativeQuickSQLiteOpenFactory.js.map +0 -1
  62. package/src/db/adapters/react-native-quick-sqlite/RNQSDBAdapter.ts +0 -85
  63. package/src/db/adapters/react-native-quick-sqlite/RNQSDBOpenFactory.ts +0 -44
  64. package/src/db/adapters/react-native-quick-sqlite/ReactNativeQuickSQLiteOpenFactory.ts +0 -43
package/README.md CHANGED
@@ -15,17 +15,83 @@ See a summary of features [here](https://docs.powersync.co/client-sdk-references
15
15
  ## Install Package
16
16
 
17
17
  ```bash
18
- npx expo install @powersync/react-native
18
+ npx expo install @powersync/react-native @op-engineering/op-sqlite
19
19
  ```
20
20
 
21
- ## Install Peer Dependency: SQLite
21
+ ## Configuration options
22
22
 
23
- By default, this SDK requires `@journeyapps/react-native-quick-sqlite` as a peer dependency. Alternatively, you can install OP-SQLite from the [PowerSync OP-SQLite package](https://github.com/powersync-ja/powersync-js/tree/main/packages/powersync-op-sqlite) (currently in Beta).
23
+ ### Encryption with SQLCipher
24
24
 
25
- Install it in your app with:
25
+ To enable SQLCipher you need to add the following configuration option to your application's `package.json`. Note that for [monorepos](https://op-engineering.github.io/op-sqlite/docs/installation) you may have to add this configuration to the monorepo root `package.json` instead, this depends on where your package manager tool hoists modules.
26
26
 
27
- ```bash
28
- npx expo install @journeyapps/react-native-quick-sqlite
27
+ ```json
28
+ {
29
+ // your normal package.json
30
+ // ...
31
+ "op-sqlite": {
32
+ "sqlcipher": true
33
+ }
34
+ }
35
+ ```
36
+
37
+ Additionally you will need to add an [encryption key](https://www.zetetic.net/sqlcipher/sqlcipher-api/#key) to the OPSQLite factory constructor
38
+
39
+ ```typescript
40
+ const db = new PowerSyncDatabase({
41
+ schema: new Schema(...),
42
+ database: {
43
+ dbFilename: 'sqlite.db',
44
+ sqliteOptions: {
45
+ encryptionKey: 'your-encryption-key'
46
+ }
47
+ }
48
+ });
49
+ ```
50
+
51
+ ### Full-Text Search
52
+
53
+ To enable the `fts5` extension, configure OP-SQLite in your (or for monorepos, the root) `package.json`:
54
+
55
+ ```json
56
+ {
57
+ // your normal package.json
58
+ // ...
59
+ "op-sqlite": {
60
+ "fts5": true
61
+ }
62
+ }
63
+ ```
64
+
65
+ ### Loading SQLite extensions
66
+
67
+ To load additional SQLite extensions include the `extensions` option in `sqliteOptions` which expects an array of objects with a `path` and an `entryPoint`:
68
+
69
+ ```js
70
+ sqliteOptions: {
71
+ extensions: [{ path: libPath, entryPoint: 'sqlite3_powersync_init' }];
72
+ }
73
+ ```
74
+
75
+ More info can be found in the [OP-SQLite docs](https://op-engineering.github.io/op-sqlite/docs/api/#loading-extensions).
76
+
77
+ Example usage:
78
+
79
+ ```ts
80
+ import { getDylibPath } from '@op-engineering/op-sqlite';
81
+
82
+ let libPath: string;
83
+ if (Platform.OS === 'ios') {
84
+ libPath = getDylibPath('co.powersync.sqlitecore', 'powersync-sqlite-core');
85
+ } else {
86
+ libPath = 'libpowersync';
87
+ }
88
+
89
+ const factory = new OPSqliteOpenFactory({
90
+ dbFilename: 'sqlite.db',
91
+ sqliteOptions: {
92
+ extensions: [{ path: libPath, entryPoint: 'sqlite3_powersync_init' }]
93
+ }
94
+ });
29
95
  ```
30
96
 
31
97
  ## Install Polyfills
@@ -0,0 +1,90 @@
1
+ buildscript {
2
+ // Buildscript is evaluated before everything else so we can't use getExtOrDefault
3
+ def kotlin_version = rootProject.ext.has("kotlinVersion") ? rootProject.ext.get("kotlinVersion") : project.properties["PowerSync_kotlinVersion"]
4
+
5
+ repositories {
6
+ google()
7
+ mavenCentral()
8
+ }
9
+
10
+ dependencies {
11
+ classpath "com.android.tools.build:gradle:8.7.2"
12
+ // noinspection DifferentKotlinGradleVersion
13
+ classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
14
+ }
15
+ }
16
+
17
+ apply plugin: "com.android.library"
18
+ apply plugin: "kotlin-android"
19
+ apply plugin: "com.facebook.react"
20
+
21
+ def getExtOrDefault(name) {
22
+ return rootProject.ext.has(name) ? rootProject.ext.get(name) : project.properties["PowerSync_" + name]
23
+ }
24
+
25
+ def getExtOrIntegerDefault(name) {
26
+ return rootProject.ext.has(name) ? rootProject.ext.get(name) : (project.properties["PowerSync_" + name]).toInteger()
27
+ }
28
+
29
+ def supportsNamespace() {
30
+ def parsed = com.android.Version.ANDROID_GRADLE_PLUGIN_VERSION.tokenize('.')
31
+ def major = parsed[0].toInteger()
32
+ def minor = parsed[1].toInteger()
33
+
34
+ // Namespace support was added in 7.3.0
35
+ return (major == 7 && minor >= 3) || major >= 8
36
+ }
37
+
38
+ android {
39
+ if (supportsNamespace()) {
40
+ namespace "com.powersync.opsqlite"
41
+
42
+ sourceSets {
43
+ main {
44
+ manifest.srcFile "src/main/AndroidManifestNew.xml"
45
+ }
46
+ }
47
+ }
48
+
49
+ compileSdkVersion getExtOrIntegerDefault("compileSdkVersion")
50
+
51
+ defaultConfig {
52
+ minSdkVersion getExtOrIntegerDefault("minSdkVersion")
53
+ targetSdkVersion getExtOrIntegerDefault("targetSdkVersion")
54
+ }
55
+
56
+ buildFeatures {
57
+ buildConfig true
58
+ }
59
+
60
+ buildTypes {
61
+ release {
62
+ minifyEnabled false
63
+ }
64
+ }
65
+
66
+ lintOptions {
67
+ disable "GradleCompatible"
68
+ }
69
+
70
+ compileOptions {
71
+ sourceCompatibility JavaVersion.VERSION_1_8
72
+ targetCompatibility JavaVersion.VERSION_1_8
73
+ }
74
+ }
75
+
76
+ repositories {
77
+ mavenCentral()
78
+ google()
79
+ }
80
+
81
+ def kotlin_version = getExtOrDefault("kotlinVersion")
82
+
83
+ dependencies {
84
+ implementation 'com.powersync:powersync-sqlite-core:0.4.12'
85
+ // For < 0.71, this will be from the local maven repo
86
+ // For > 0.71, this will be replaced by `com.facebook.react:react-android:$version` by react gradle plugin
87
+ //noinspection GradleDynamicVersion
88
+ implementation "com.facebook.react:react-native:+"
89
+ implementation "org.jetbrains.kotlin:kotlin-stdlib:$kotlin_version"
90
+ }
@@ -0,0 +1,4 @@
1
+ PowerSync_kotlinVersion=2.4.0
2
+ PowerSync_minSdkVersion=24
3
+ PowerSync_targetSdkVersion=36
4
+ PowerSync_compileSdkVersion=36
@@ -0,0 +1,3 @@
1
+ <manifest xmlns:android="http://schemas.android.com/apk/res/android"
2
+ package="com.powersync.opsqlite">
3
+ </manifest>
@@ -0,0 +1,2 @@
1
+ <manifest xmlns:android="http://schemas.android.com/apk/res/android">
2
+ </manifest>
@@ -0,0 +1,46 @@
1
+ package com.powersync.opsqlite
2
+
3
+ import java.io.File
4
+ import com.facebook.proguard.annotations.DoNotStrip
5
+ import com.facebook.react.ReactPackage
6
+ import com.facebook.react.bridge.NativeModule
7
+ import com.facebook.react.bridge.ReactApplicationContext
8
+ import com.facebook.react.bridge.ReactMethod
9
+ import com.facebook.react.bridge.ReactContextBaseJavaModule
10
+ import com.facebook.react.uimanager.ViewManager
11
+
12
+ class PowerSyncOpSqlitePackage : ReactPackage {
13
+ override fun createNativeModules(reactContext: ReactApplicationContext): List<NativeModule> {
14
+ return listOf<NativeModule>(NativePowerSyncHelper(reactContext))
15
+ }
16
+
17
+ override fun createViewManagers(
18
+ reactContext: ReactApplicationContext
19
+ ): List<ViewManager<*, *>> {
20
+ return emptyList()
21
+ }
22
+ }
23
+
24
+ private class NativePowerSyncHelper(context: ReactApplicationContext): ReactContextBaseJavaModule(context) {
25
+ @ReactMethod(isBlockingSynchronousMethod = true)
26
+ @DoNotStrip
27
+ fun resolveDefaultDatabaseLocation(dbName: String): String? {
28
+ // OP-sqlite uses context.getDatabasePath() as a default location for databases, but previous
29
+ // versions of the PowerSync React Native SDK used React Native Quick SQLite, which used
30
+ // context.getFileDir() instead. So, check if an old database exists and keep using the existing
31
+ // path for backwards compatibility.
32
+ val context = reactApplicationContext
33
+ val oldDirectory = context.filesDir
34
+ val filesPath = File(oldDirectory, dbName)
35
+ if (filesPath.exists()) {
36
+ return oldDirectory.absolutePath;
37
+ }
38
+ return null;
39
+ }
40
+
41
+ override fun getName(): String = NAME
42
+
43
+ companion object {
44
+ const val NAME: String = "NativePowerSyncHelper"
45
+ }
46
+ }
@@ -0,0 +1,5 @@
1
+ #import <React/RCTBridgeModule.h>
2
+
3
+ @interface PowerSyncOpSqlite : NSObject <RCTBridgeModule>
4
+
5
+ @end
@@ -0,0 +1,6 @@
1
+ #import "PowerSyncOpSqlite.h"
2
+
3
+ @implementation PowerSyncOpSqlite
4
+ RCT_EXPORT_MODULE()
5
+
6
+ @end
@@ -1,4 +1,10 @@
1
- import { AbstractPowerSyncDatabase, AbstractStreamingSyncImplementation, BucketStorageAdapter, DBAdapter, PowerSyncBackendConnector, PowerSyncDatabaseOptionsWithSettings, type RequiredAdditionalConnectionOptions } from '@powersync/common';
1
+ import { BasePowerSyncDatabaseOptions, CommonPowerSyncDatabase, DatabaseSource, PowerSyncDatabaseConstructor } from '@powersync/common';
2
+ import { ReactNativeRemoteOptions } from '../sync/stream/ReactNativeRemote';
3
+ import { OPSQLiteOpenFactoryOptions } from './adapters/op-sqlite/OPSqliteDBOpenFactory';
4
+ export type ReactNativeDatabaseOptions = BasePowerSyncDatabaseOptions & DatabaseSource<OPSQLiteOpenFactoryOptions> & ReactNativeSpecificOptions;
5
+ export interface ReactNativeSpecificOptions {
6
+ remote?: ReactNativeRemoteOptions;
7
+ }
2
8
  /**
3
9
  * A PowerSync database which provides SQLite functionality
4
10
  * which is automatically synced.
@@ -13,13 +19,6 @@ import { AbstractPowerSyncDatabase, AbstractStreamingSyncImplementation, BucketS
13
19
  * });
14
20
  * ```
15
21
  */
16
- export declare class PowerSyncDatabase extends AbstractPowerSyncDatabase {
17
- _initialize(): Promise<void>;
18
- /**
19
- * Opens a DBAdapter using React Native Quick SQLite as the
20
- * default SQLite open factory.
21
- */
22
- protected openDBAdapter(options: PowerSyncDatabaseOptionsWithSettings): DBAdapter;
23
- protected generateBucketStorageAdapter(): BucketStorageAdapter;
24
- protected generateSyncStreamImplementation(connector: PowerSyncBackendConnector, options: RequiredAdditionalConnectionOptions): AbstractStreamingSyncImplementation;
22
+ export declare const PowerSyncDatabase: PowerSyncDatabaseConstructor<ReactNativeDatabaseOptions>;
23
+ export interface PowerSyncDatabase extends CommonPowerSyncDatabase {
25
24
  }
@@ -1,37 +1,26 @@
1
- import { AbstractPowerSyncDatabase } from '@powersync/common';
1
+ import { SyncStreamConnectionMethod } from '@powersync/common';
2
+ import { BasePowerSyncDatabase, openDatabase } from '@powersync/shared-internals';
2
3
  import { ReactNativeRemote } from '../sync/stream/ReactNativeRemote';
3
4
  import { ReactNativeStreamingSyncImplementation } from '../sync/stream/ReactNativeStreamingSyncImplementation';
4
5
  import { ReactNativeBucketStorageAdapter } from './../sync/bucket/ReactNativeBucketStorageAdapter';
5
- import { ReactNativeQuickSqliteOpenFactory } from './adapters/react-native-quick-sqlite/ReactNativeQuickSQLiteOpenFactory';
6
- /**
7
- * A PowerSync database which provides SQLite functionality
8
- * which is automatically synced.
9
- *
10
- * @example
11
- * ```typescript
12
- * export const db = new PowerSyncDatabase({
13
- * schema: AppSchema,
14
- * database: {
15
- * dbFilename: 'example.db'
16
- * }
17
- * });
18
- * ```
19
- */
20
- export class PowerSyncDatabase extends AbstractPowerSyncDatabase {
6
+ import { OPSqliteOpenFactory } from './adapters/op-sqlite/OPSqliteDBOpenFactory';
7
+ import { defaultFetchImplementation } from '../sync/stream/fetch';
8
+ class ReactNativePowerSyncDatabase extends BasePowerSyncDatabase {
9
+ constructor(options) {
10
+ super(options);
11
+ }
21
12
  async _initialize() { }
22
- /**
23
- * Opens a DBAdapter using React Native Quick SQLite as the
24
- * default SQLite open factory.
25
- */
26
- openDBAdapter(options) {
27
- const defaultFactory = new ReactNativeQuickSqliteOpenFactory(options.database);
28
- return defaultFactory.openDB();
13
+ openDBAdapter() {
14
+ return openDatabase(this.options, (database) => {
15
+ const defaultFactory = new OPSqliteOpenFactory(database);
16
+ return defaultFactory.openDB();
17
+ });
29
18
  }
30
19
  generateBucketStorageAdapter() {
31
20
  return new ReactNativeBucketStorageAdapter(this.database, this.logger);
32
21
  }
33
22
  generateSyncStreamImplementation(connector, options) {
34
- const remote = new ReactNativeRemote(connector, this.logger);
23
+ const remote = new ReactNativeRemote(connector, this.logger, this.options.remote);
35
24
  return new ReactNativeStreamingSyncImplementation({
36
25
  ...options,
37
26
  adapter: this.bucketStorageAdapter,
@@ -44,5 +33,24 @@ export class PowerSyncDatabase extends AbstractPowerSyncDatabase {
44
33
  logger: this.logger
45
34
  });
46
35
  }
36
+ get defaultConnectionMethod() {
37
+ const fetch = this.options.remote?.fetchImplementation ?? defaultFetchImplementation(this.logger);
38
+ return fetch.supportsStreams ? SyncStreamConnectionMethod.HTTP : SyncStreamConnectionMethod.WEB_SOCKET;
39
+ }
47
40
  }
41
+ /**
42
+ * A PowerSync database which provides SQLite functionality
43
+ * which is automatically synced.
44
+ *
45
+ * @example
46
+ * ```typescript
47
+ * export const db = new PowerSyncDatabase({
48
+ * schema: AppSchema,
49
+ * database: {
50
+ * dbFilename: 'example.db'
51
+ * }
52
+ * });
53
+ * ```
54
+ */
55
+ export const PowerSyncDatabase = ReactNativePowerSyncDatabase;
48
56
  //# sourceMappingURL=PowerSyncDatabase.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"PowerSyncDatabase.js","sourceRoot":"","sources":["../../src/db/PowerSyncDatabase.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,yBAAyB,EAO1B,MAAM,mBAAmB,CAAC;AAC3B,OAAO,EAAE,iBAAiB,EAAE,MAAM,kCAAkC,CAAC;AACrE,OAAO,EAAE,sCAAsC,EAAE,MAAM,uDAAuD,CAAC;AAC/G,OAAO,EAAE,+BAA+B,EAAE,MAAM,kDAAkD,CAAC;AACnG,OAAO,EAAE,iCAAiC,EAAE,MAAM,wEAAwE,CAAC;AAE3H;;;;;;;;;;;;;GAaG;AACH,MAAM,OAAO,iBAAkB,SAAQ,yBAAyB;IAC9D,KAAK,CAAC,WAAW,KAAmB,CAAC;IAErC;;;OAGG;IACO,aAAa,CAAC,OAA6C;QACnE,MAAM,cAAc,GAAG,IAAI,iCAAiC,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC;QAC/E,OAAO,cAAc,CAAC,MAAM,EAAE,CAAC;IACjC,CAAC;IAES,4BAA4B;QACpC,OAAO,IAAI,+BAA+B,CAAC,IAAI,CAAC,QAAQ,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;IACzE,CAAC;IAES,gCAAgC,CACxC,SAAoC,EACpC,OAA4C;QAE5C,MAAM,MAAM,GAAG,IAAI,iBAAiB,CAAC,SAAS,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;QAE7D,OAAO,IAAI,sCAAsC,CAAC;YAChD,GAAG,OAAO;YACV,OAAO,EAAE,IAAI,CAAC,oBAAoB;YAClC,MAAM;YACN,UAAU,EAAE,KAAK,IAAI,EAAE;gBACrB,MAAM,IAAI,CAAC,YAAY,EAAE,CAAC;gBAC1B,MAAM,SAAS,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC;YACnC,CAAC;YACD,UAAU,EAAE,IAAI,CAAC,QAAQ,CAAC,IAAI;YAC9B,MAAM,EAAE,IAAI,CAAC,MAAM;SACpB,CAAC,CAAC;IACL,CAAC;CACF"}
1
+ {"version":3,"file":"PowerSyncDatabase.js","sourceRoot":"","sources":["../../src/db/PowerSyncDatabase.ts"],"names":[],"mappings":"AAAA,OAAO,EAOL,0BAA0B,EAC3B,MAAM,mBAAmB,CAAC;AAC3B,OAAO,EACL,qBAAqB,EAIrB,YAAY,EACb,MAAM,6BAA6B,CAAC;AACrC,OAAO,EAAE,iBAAiB,EAA4B,MAAM,kCAAkC,CAAC;AAC/F,OAAO,EAAE,sCAAsC,EAAE,MAAM,uDAAuD,CAAC;AAC/G,OAAO,EAAE,+BAA+B,EAAE,MAAM,kDAAkD,CAAC;AACnG,OAAO,EAAE,mBAAmB,EAA8B,MAAM,4CAA4C,CAAC;AAC7G,OAAO,EAAE,0BAA0B,EAAE,MAAM,sBAAsB,CAAC;AAUlE,MAAM,4BAA6B,SAAQ,qBAAiD;IAC1F,YAAY,OAAmC;QAC7C,KAAK,CAAC,OAAO,CAAC,CAAC;IACjB,CAAC;IAED,KAAK,CAAC,WAAW,KAAmB,CAAC;IAElB,aAAa;QAC9B,OAAO,YAAY,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,QAAQ,EAAE,EAAE;YAC7C,MAAM,cAAc,GAAG,IAAI,mBAAmB,CAAC,QAAQ,CAAC,CAAC;YACzD,OAAO,cAAc,CAAC,MAAM,EAAE,CAAC;QACjC,CAAC,CAAC,CAAC;IACL,CAAC;IAES,4BAA4B;QACpC,OAAO,IAAI,+BAA+B,CAAC,IAAI,CAAC,QAAQ,EAAE,IAAI,CAAC,MAAM,CAAC,CAAC;IACzE,CAAC;IAES,gCAAgC,CACxC,SAAoC,EACpC,OAAwC;QAExC,MAAM,MAAM,GAAG,IAAI,iBAAiB,CAAC,SAAS,EAAE,IAAI,CAAC,MAAM,EAAE,IAAI,CAAC,OAAO,CAAC,MAAM,CAAC,CAAC;QAElF,OAAO,IAAI,sCAAsC,CAAC;YAChD,GAAG,OAAO;YACV,OAAO,EAAE,IAAI,CAAC,oBAAoB;YAClC,MAAM;YACN,UAAU,EAAE,KAAK,IAAI,EAAE;gBACrB,MAAM,IAAI,CAAC,YAAY,EAAE,CAAC;gBAC1B,MAAM,SAAS,CAAC,UAAU,CAAC,IAAI,CAAC,CAAC;YACnC,CAAC;YACD,UAAU,EAAE,IAAI,CAAC,QAAQ,CAAC,IAAI;YAC9B,MAAM,EAAE,IAAI,CAAC,MAAM;SACpB,CAAC,CAAC;IACL,CAAC;IAED,IAAc,uBAAuB;QACnC,MAAM,KAAK,GAAG,IAAI,CAAC,OAAO,CAAC,MAAM,EAAE,mBAAmB,IAAI,0BAA0B,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC;QAClG,OAAO,KAAK,CAAC,eAAe,CAAC,CAAC,CAAC,0BAA0B,CAAC,IAAI,CAAC,CAAC,CAAC,0BAA0B,CAAC,UAAU,CAAC;IACzG,CAAC;CACF;AAED;;;;;;;;;;;;;GAaG;AACH,MAAM,CAAC,MAAM,iBAAiB,GAA6D,4BAA4B,CAAC"}
@@ -0,0 +1,25 @@
1
+ import { DB, UpdateHookOperation } from '@op-engineering/op-sqlite';
2
+ import { BaseObserver, LockContext, QueryResult, RawQueryResult } from '@powersync/common';
3
+ export type OPSQLiteConnectionOptions = {
4
+ baseDB: DB;
5
+ };
6
+ export type OPSQLiteUpdateNotification = {
7
+ table: string;
8
+ operation: UpdateHookOperation;
9
+ row?: any;
10
+ rowId: number;
11
+ };
12
+ export declare class OPSQLiteConnection extends LockContext {
13
+ protected options: OPSQLiteConnectionOptions;
14
+ protected DB: DB;
15
+ private updateBuffer;
16
+ readonly tableUpdateDispatcher: BaseObserver<import("@powersync/common").BaseListener>;
17
+ constructor(options: OPSQLiteConnectionOptions);
18
+ addTableUpdate(update: OPSQLiteUpdateNotification): void;
19
+ flushUpdates(): void;
20
+ close(): void;
21
+ execute<T>(query: string, params?: any[]): Promise<QueryResult<T>>;
22
+ executeRaw(query: string, params?: any[]): Promise<RawQueryResult>;
23
+ executeNativeBatch(query: string, params?: any[][]): Promise<QueryResult<never>>;
24
+ refreshSchema(): Promise<void>;
25
+ }
@@ -0,0 +1,63 @@
1
+ import { BaseObserver, LockContext, queryResultFromMapped, queryResultWithoutRows } from '@powersync/common';
2
+ export class OPSQLiteConnection extends LockContext {
3
+ options;
4
+ DB;
5
+ updateBuffer;
6
+ tableUpdateDispatcher = new BaseObserver();
7
+ constructor(options) {
8
+ super();
9
+ this.options = options;
10
+ this.DB = options.baseDB;
11
+ this.updateBuffer = new Set();
12
+ this.DB.rollbackHook(() => {
13
+ this.updateBuffer = new Set();
14
+ });
15
+ this.DB.updateHook((update) => {
16
+ this.addTableUpdate(update);
17
+ });
18
+ }
19
+ addTableUpdate(update) {
20
+ this.updateBuffer.add(update.table);
21
+ }
22
+ flushUpdates() {
23
+ if (!this.updateBuffer.size) {
24
+ return;
25
+ }
26
+ const batchedUpdate = {
27
+ tables: Array.from(this.updateBuffer)
28
+ };
29
+ this.updateBuffer = new Set();
30
+ this.tableUpdateDispatcher.iterateListeners((l) => l.tablesUpdated?.(batchedUpdate));
31
+ }
32
+ close() {
33
+ return this.DB.close();
34
+ }
35
+ async execute(query, params) {
36
+ const res = await this.DB.execute(query, params);
37
+ return queryResultFromMapped(res, res.rows);
38
+ }
39
+ async executeRaw(query, params) {
40
+ const { insertId, rowsAffected, columnNames, rawRows } = await this.DB.executeRaw(query, params);
41
+ return {
42
+ insertId: insertId,
43
+ rowsAffected: rowsAffected,
44
+ columnNames,
45
+ rawRows: (rawRows ?? [])
46
+ };
47
+ }
48
+ // NOTE: Do not override executeBatch here. OP-sqlite starts a transaction in executeBatch, so we can't use it if
49
+ // we're already in a transaction. To be safe, we only call this method from the OPSqliteAdapter class overriding
50
+ // executeBatch when called on the adapter directly (not within readLock / writeLock).
51
+ async executeNativeBatch(query, params = []) {
52
+ const tuple = [[query, params[0]]];
53
+ params.slice(1).forEach((p) => tuple.push([query, p]));
54
+ const result = await this.DB.executeBatch(tuple);
55
+ return queryResultWithoutRows({
56
+ rowsAffected: result.rowsAffected ?? 0
57
+ });
58
+ }
59
+ async refreshSchema() {
60
+ await this.get("PRAGMA table_info('sqlite_master')");
61
+ }
62
+ }
63
+ //# sourceMappingURL=OPSQLiteConnection.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"OPSQLiteConnection.js","sourceRoot":"","sources":["../../../../src/db/adapters/op-sqlite/OPSQLiteConnection.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,32 @@
1
+ import { DBAdapter, DBLockOptions, QueryResult } from '@powersync/common';
2
+ import { Semaphore } from '@powersync/shared-internals';
3
+ import { OPSQLiteConnection } from './OPSQLiteConnection';
4
+ import { SqliteOptions } from './SqliteOptions';
5
+ /**
6
+ * Adapter for React Native Quick SQLite
7
+ */
8
+ export type OPSQLiteAdapterOptions = {
9
+ name: string;
10
+ dbLocation?: string;
11
+ sqliteOptions?: SqliteOptions;
12
+ };
13
+ export declare class OPSQLiteDBAdapter extends DBAdapter {
14
+ protected options: OPSQLiteAdapterOptions;
15
+ name: string;
16
+ protected initialized: Promise<void>;
17
+ protected readConnections: Semaphore<OPSQLiteConnection> | null;
18
+ protected writeConnection: Semaphore<OPSQLiteConnection> | null;
19
+ private abortController;
20
+ constructor(options: OPSQLiteAdapterOptions);
21
+ protected init(): Promise<void>;
22
+ protected openConnection(readOnly: boolean, filenameOverride?: string): Promise<OPSQLiteConnection>;
23
+ private openDatabase;
24
+ private loadAdditionalExtensions;
25
+ private loadPowerSyncExtension;
26
+ close(): Promise<void>;
27
+ private generateNestedAbortSignal;
28
+ readLock<T>(fn: (tx: OPSQLiteConnection) => Promise<T>, options?: DBLockOptions): Promise<T>;
29
+ writeLock<T>(fn: (tx: OPSQLiteConnection) => Promise<T>, options?: DBLockOptions): Promise<T>;
30
+ refreshSchema(): Promise<void>;
31
+ executeBatch(query: string, params?: any[][]): Promise<QueryResult<never>>;
32
+ }