@op-engineering/op-sqlite 11.2.5 → 11.2.6

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.
@@ -18,13 +18,13 @@ namespace react = facebook::react;
18
18
 
19
19
  #ifdef OP_SQLITE_USE_LIBSQL
20
20
  void DBHostObject::flush_pending_reactive_queries(
21
- std::shared_ptr<jsi::Value> resolve) {
21
+ const std::shared_ptr<jsi::Value> &resolve) {
22
22
  invoker->invokeAsync(
23
23
  [this, resolve]() { resolve->asObject(rt).asFunction(rt).call(rt, {}); });
24
24
  }
25
25
  #else
26
26
  void DBHostObject::flush_pending_reactive_queries(
27
- std::shared_ptr<jsi::Value> resolve) {
27
+ const std::shared_ptr<jsi::Value> &resolve) {
28
28
  for (const auto &query_ptr : pending_reactive_queries) {
29
29
  auto query = query_ptr.get();
30
30
 
@@ -32,26 +32,15 @@ void DBHostObject::flush_pending_reactive_queries(
32
32
  std::shared_ptr<std::vector<SmartHostObject>> metadata =
33
33
  std::make_shared<std::vector<SmartHostObject>>();
34
34
 
35
- auto status = opsqlite_execute_prepared_statement(db_name, query->stmt,
36
- &results, metadata);
35
+ auto status = opsqlite_execute_prepared_statement(db, query->stmt, &results,
36
+ metadata);
37
37
 
38
- if (status.type == SQLiteError) {
39
- invoker->invokeAsync(
40
- [this, callback = query->callback, status = std::move(status)] {
41
- auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
42
- auto error = errorCtr.callAsConstructor(
43
- rt, jsi::String::createFromUtf8(rt, status.message));
44
- callback->asObject(rt).asFunction(rt).call(rt, error);
45
- });
46
- } else {
47
- invoker->invokeAsync(
48
- [this,
49
- results = std::make_shared<std::vector<DumbHostObject>>(results),
50
- callback = query->callback, metadata, status = std::move(status)] {
51
- auto jsiResult = create_result(rt, status, results.get(), metadata);
52
- callback->asObject(rt).asFunction(rt).call(rt, jsiResult);
53
- });
54
- }
38
+ invoker->invokeAsync(
39
+ [this, results = std::make_shared<std::vector<DumbHostObject>>(results),
40
+ callback = query->callback, metadata, status = std::move(status)] {
41
+ auto jsiResult = create_result(rt, status, results.get(), metadata);
42
+ callback->asObject(rt).asFunction(rt).call(rt, jsiResult);
43
+ });
55
44
  }
56
45
 
57
46
  pending_reactive_queries.clear();
@@ -60,104 +49,111 @@ void DBHostObject::flush_pending_reactive_queries(
60
49
  [this, resolve]() { resolve->asObject(rt).asFunction(rt).call(rt, {}); });
61
50
  }
62
51
 
63
- void DBHostObject::auto_register_update_hook() {
64
- if (update_hook_callback == nullptr && reactive_queries.empty() &&
65
- is_update_hook_registered) {
66
- opsqlite_deregister_update_hook(db_name);
67
- is_update_hook_registered = false;
68
- return;
69
- }
52
+ void DBHostObject::on_commit() {
53
+ invoker->invokeAsync(
54
+ [this] { commit_hook_callback->asObject(rt).asFunction(rt).call(rt); });
55
+ }
70
56
 
71
- if (is_update_hook_registered) {
72
- return;
57
+ void DBHostObject::on_rollback() {
58
+ invoker->invokeAsync(
59
+ [this] { rollback_hook_callback->asObject(rt).asFunction(rt).call(rt); });
60
+ }
61
+
62
+ void DBHostObject::on_update(const std::string &table,
63
+ const std::string &operation, long long row_id) {
64
+ if (update_hook_callback != nullptr) {
65
+ invoker->invokeAsync(
66
+ [this, callback = update_hook_callback, table, operation, row_id] {
67
+ auto res = jsi::Object(rt);
68
+ res.setProperty(rt, "table", jsi::String::createFromUtf8(rt, table));
69
+ res.setProperty(rt, "operation",
70
+ jsi::String::createFromUtf8(rt, operation));
71
+ res.setProperty(rt, "rowId", jsi::Value(static_cast<double>(row_id)));
72
+
73
+ callback->asObject(rt).asFunction(rt).call(rt, res);
74
+ });
73
75
  }
74
76
 
75
- auto hook = [this](std::string name, std::string table_name,
76
- std::string operation, int rowid) {
77
- if (update_hook_callback != nullptr) {
78
- invoker->invokeAsync([this, callback = update_hook_callback, table_name,
79
- operation = std::move(operation), rowid] {
80
- auto res = jsi::Object(rt);
81
- res.setProperty(rt, "table",
82
- jsi::String::createFromUtf8(rt, table_name));
83
- res.setProperty(rt, "operation",
84
- jsi::String::createFromUtf8(rt, operation));
85
- res.setProperty(rt, "rowId", jsi::Value(rowid));
86
-
87
- callback->asObject(rt).asFunction(rt).call(rt, res);
88
- });
77
+ for (const auto &query_ptr : reactive_queries) {
78
+ auto query = query_ptr.get();
79
+ if (query->discriminators.empty()) {
80
+ continue;
89
81
  }
90
82
 
91
- for (const auto &query_ptr : reactive_queries) {
92
- auto query = query_ptr.get();
93
- if (query->discriminators.empty()) {
83
+ bool shouldFire = false;
84
+
85
+ for (const auto &discriminator : query->discriminators) {
86
+ // Tables don't match then skip
87
+ if (discriminator.table != table) {
94
88
  continue;
95
89
  }
96
90
 
97
- bool shouldFire = false;
98
-
99
- for (const auto &discriminator : query->discriminators) {
100
- // Tables don't match then skip
101
- if (discriminator.table != table_name) {
102
- continue;
103
- }
91
+ // If no ids are specified, then we should fire
92
+ if (discriminator.ids.empty()) {
93
+ shouldFire = true;
94
+ break;
95
+ }
104
96
 
105
- // If no ids are specified, then we should fire
106
- if (discriminator.ids.size() == 0) {
97
+ // If ids are specified, then we should check if the rowId matches
98
+ for (const auto &discrimator_id : discriminator.ids) {
99
+ if (row_id == discrimator_id) {
107
100
  shouldFire = true;
108
101
  break;
109
102
  }
110
-
111
- // If ids are specified, then we should check if the rowId matches
112
- for (const auto &discrimator_id : discriminator.ids) {
113
- if (rowid == discrimator_id) {
114
- shouldFire = true;
115
- break;
116
- }
117
- }
118
103
  }
104
+ }
119
105
 
120
- if (shouldFire) {
121
- pending_reactive_queries.insert(query_ptr);
122
- }
106
+ if (shouldFire) {
107
+ pending_reactive_queries.insert(query_ptr);
123
108
  }
124
- };
109
+ }
110
+ }
125
111
 
126
- opsqlite_register_update_hook(db_name, std::move(hook));
112
+ void DBHostObject::auto_register_update_hook() {
113
+ if (update_hook_callback == nullptr && reactive_queries.empty() &&
114
+ is_update_hook_registered) {
115
+ opsqlite_deregister_update_hook(db);
116
+ is_update_hook_registered = false;
117
+ return;
118
+ }
119
+
120
+ if (is_update_hook_registered) {
121
+ return;
122
+ }
123
+
124
+ opsqlite_register_update_hook(db, this);
127
125
  is_update_hook_registered = true;
128
126
  }
129
127
  #endif
130
128
 
129
+ // _____ _ _
130
+ // / ____| | | | |
131
+ // | | ___ _ __ ___| |_ _ __ _ _ ___| |_ ___ _ __
132
+ // | | / _ \| '_ \/ __| __| '__| | | |/ __| __/ _ \| '__|
133
+ // | |___| (_) | | | \__ \ |_| | | |_| | (__| || (_) | |
134
+ // \_____\___/|_| |_|___/\__|_| \__,_|\___|\__\___/|_|
131
135
  #ifdef OP_SQLITE_USE_LIBSQL
132
136
  DBHostObject::DBHostObject(jsi::Runtime &rt, std::string &url,
133
137
  std::string &auth_token,
134
- std::shared_ptr<react::CallInvoker> invoker,
135
- std::shared_ptr<ThreadPool> thread_pool)
138
+ std::shared_ptr<react::CallInvoker> invoker
139
+ )
136
140
  : db_name(url), invoker(std::move(invoker)),
137
- thread_pool(std::move(thread_pool)), rt(rt) {
138
- BridgeResult result = opsqlite_libsql_open_remote(url, auth_token);
139
-
140
- if (result.type == SQLiteError) {
141
- throw std::runtime_error(result.message);
142
- }
141
+ rt(rt) {
142
+ db = opsqlite_libsql_open_remote(url, auth_token);
143
143
 
144
144
  create_jsi_functions();
145
145
  }
146
146
 
147
147
  DBHostObject::DBHostObject(jsi::Runtime &rt,
148
148
  std::shared_ptr<react::CallInvoker> invoker,
149
- std::shared_ptr<ThreadPool> thread_pool,
150
149
  std::string &db_name, std::string &path,
151
150
  std::string &url, std::string &auth_token,
152
151
  int sync_interval)
153
152
  : db_name(db_name), invoker(std::move(invoker)),
154
- thread_pool(std::move(thread_pool)), rt(rt) {
155
- BridgeResult result =
153
+ rt(rt) {
154
+ db =
156
155
  opsqlite_libsql_open_sync(db_name, path, url, auth_token, sync_interval);
157
156
 
158
- if (result.type == SQLiteError) {
159
- throw std::runtime_error(result.message);
160
- }
161
157
 
162
158
  create_jsi_functions();
163
159
  }
@@ -166,114 +162,95 @@ DBHostObject::DBHostObject(jsi::Runtime &rt,
166
162
 
167
163
  DBHostObject::DBHostObject(jsi::Runtime &rt, std::string &base_path,
168
164
  std::shared_ptr<react::CallInvoker> invoker,
169
- std::shared_ptr<ThreadPool> thread_pool,
170
165
  std::string &db_name, std::string &path,
171
166
  std::string &crsqlite_path,
172
167
  std::string &sqlite_vec_path,
173
168
  std::string &encryption_key)
174
- : base_path(base_path), invoker(std::move(invoker)),
175
- thread_pool(std::move(thread_pool)), db_name(db_name), rt(rt) {
169
+ : base_path(base_path), invoker(std::move(invoker)), db_name(db_name),
170
+ rt(rt) {
171
+ _thread_pool = std::make_shared<ThreadPool>();
176
172
 
177
173
  #ifdef OP_SQLITE_USE_SQLCIPHER
178
- BridgeResult result = opsqlite_open(db_name, path, crsqlite_path,
174
+ db = opsqlite_open(db_name, path, crsqlite_path,
179
175
  sqlite_vec_path, encryption_key);
180
176
  #elif OP_SQLITE_USE_LIBSQL
181
- BridgeResult result = opsqlite_libsql_open(db_name, path, crsqlite_path);
177
+ db = opsqlite_libsql_open(db_name, path, crsqlite_path);
182
178
  #else
183
- BridgeResult result =
184
- opsqlite_open(db_name, path, crsqlite_path, sqlite_vec_path);
179
+ db = opsqlite_open(db_name, path, crsqlite_path, sqlite_vec_path);
185
180
  #endif
186
-
187
- if (result.type == SQLiteError) {
188
- throw std::runtime_error(result.message);
189
- }
190
-
191
181
  create_jsi_functions();
192
182
  };
193
183
 
194
184
  void DBHostObject::create_jsi_functions() {
195
- auto attach = HOSTFN("attach") {
185
+ function_map["attach"] = HOSTFN("attach") {
196
186
  if (count < 3) {
197
- throw jsi::JSError(rt,
198
- "[op-sqlite][attach] Incorrect number of arguments");
187
+ throw std::runtime_error(
188
+ "[op-sqlite][attach] Incorrect number of arguments");
199
189
  }
200
190
  if (!args[0].isString() || !args[1].isString() || !args[2].isString()) {
201
- throw jsi::JSError(
202
- rt, "dbName, databaseToAttach and alias must be a strings");
203
- return {};
191
+ throw std::runtime_error(
192
+ "[op-sqlite] name, database to attach and alias must be strings");
204
193
  }
205
194
 
206
- std::string tempDocPath = std::string(base_path);
207
- if (count > 3 && !args[3].isUndefined() && !args[3].isNull()) {
195
+ std::string secondary_db_path = std::string(base_path);
196
+ if (count > 3) {
208
197
  if (!args[3].isString()) {
209
198
  throw std::runtime_error(
210
199
  "[op-sqlite][attach] database location must be a string");
211
200
  }
212
201
 
213
- tempDocPath = tempDocPath + "/" + args[3].asString(rt).utf8(rt);
202
+ secondary_db_path += "/" + args[3].asString(rt).utf8(rt);
214
203
  }
215
204
 
216
- std::string dbName = args[0].asString(rt).utf8(rt);
217
- std::string databaseToAttach = args[1].asString(rt).utf8(rt);
205
+ std::string main_db_name = args[0].asString(rt).utf8(rt);
206
+ std::string secondary_db_name = args[1].asString(rt).utf8(rt);
218
207
  std::string alias = args[2].asString(rt).utf8(rt);
219
208
  #ifdef OP_SQLITE_USE_LIBSQL
220
- BridgeResult result =
221
- opsqlite_libsql_attach(dbName, tempDocPath, databaseToAttach, alias);
209
+ opsqlite_libsql_attach(
210
+ db, secondary_db_path, secondary_db_name, alias);
222
211
  #else
223
- BridgeResult result =
224
- opsqlite_attach(dbName, tempDocPath, databaseToAttach, alias);
212
+ opsqlite_attach(db, main_db_name, secondary_db_path, secondary_db_name,
213
+ alias);
225
214
  #endif
226
- if (result.type == SQLiteError) {
227
- throw std::runtime_error(result.message);
228
- }
229
215
 
230
216
  return {};
231
217
  });
232
218
 
233
- auto detach = HOSTFN("detach") {
219
+ function_map["detach"] = HOSTFN("detach") {
234
220
  if (count < 2) {
235
221
  throw std::runtime_error(
236
222
  "[op-sqlite][detach] Incorrect number of arguments");
237
223
  }
238
224
  if (!args[0].isString() || !args[1].isString()) {
239
225
  throw std::runtime_error(
240
- "dbName, databaseToAttach and alias must be a strings");
241
- return {};
226
+ "[op-sqlite] database name and alias must be a strings");
242
227
  }
243
228
 
244
229
  std::string dbName = args[0].asString(rt).utf8(rt);
245
230
  std::string alias = args[1].asString(rt).utf8(rt);
246
231
  #ifdef OP_SQLITE_USE_LIBSQL
247
- BridgeResult result = opsqlite_libsql_detach(dbName, alias);
232
+ opsqlite_libsql_detach(db, alias);
248
233
  #else
249
- BridgeResult result = opsqlite_detach(dbName, alias);
234
+ opsqlite_detach(db, dbName, alias);
250
235
  #endif
251
236
 
252
- if (result.type == SQLiteError) {
253
- throw jsi::JSError(rt, result.message.c_str());
254
- }
255
-
256
237
  return {};
257
238
  });
258
239
 
259
- auto close = HOSTFN("close") {
240
+ function_map["close"] = HOSTFN("close") {
260
241
  #ifdef OP_SQLITE_USE_LIBSQL
261
- BridgeResult result = opsqlite_libsql_close(db_name);
242
+ opsqlite_libsql_close(db);
262
243
  #else
263
- BridgeResult result = opsqlite_close(db_name);
244
+ opsqlite_close(db);
264
245
  #endif
265
246
 
266
- if (result.type == SQLiteError) {
267
- throw jsi::JSError(rt, result.message.c_str());
268
- }
269
-
270
247
  return {};
271
248
  });
272
249
 
273
- auto remove = HOSTFN("delete") {
250
+ function_map["delete"] = HOSTFN("delete") {
274
251
  std::string path = std::string(base_path);
275
252
 
276
- if (count == 1 && !args[0].isUndefined() && !args[0].isNull()) {
253
+ if (count == 1) {
277
254
  if (!args[1].isString()) {
278
255
  throw std::runtime_error(
279
256
  "[op-sqlite][open] database location must be a string");
@@ -293,41 +270,34 @@ void DBHostObject::create_jsi_functions() {
293
270
  }
294
271
 
295
272
  #ifdef OP_SQLITE_USE_LIBSQL
296
- BridgeResult result = opsqlite_libsql_remove(db_name, path);
273
+ opsqlite_libsql_remove(db, db_name, path);
297
274
  #else
298
- BridgeResult result = opsqlite_remove(db_name, path);
275
+ opsqlite_remove(db, db_name, path);
299
276
  #endif
300
277
 
301
- if (result.type == SQLiteError) {
302
- throw std::runtime_error(result.message);
303
- }
304
-
305
278
  return {};
306
279
  });
307
280
 
308
- auto execute_raw = HOSTFN("executeRaw") {
281
+ function_map["executeRaw"] = HOSTFN("executeRaw") {
309
282
  const std::string query = args[0].asString(rt).utf8(rt);
310
- std::vector<JSVariant> params;
311
-
312
- if (count == 2) {
313
- params = to_variant_vec(rt, args[1]);
314
- }
283
+ std::vector<JSVariant> params = count == 2 && args[1].isObject()
284
+ ? to_variant_vec(rt, args[1])
285
+ : std::vector<JSVariant>();
315
286
 
316
287
  auto promiseCtr = rt.global().getPropertyAsFunction(rt, "Promise");
317
288
  auto promise = promiseCtr.callAsConstructor(rt, HOSTFN("executor") {
318
289
  auto resolve = std::make_shared<jsi::Value>(rt, args[0]);
319
290
  auto reject = std::make_shared<jsi::Value>(rt, args[1]);
320
291
 
321
- auto task = [&rt, this, query, params = std::move(params), resolve,
322
- reject]() {
292
+ auto task = [this, &rt, query, params, resolve, reject]() {
323
293
  try {
324
294
  std::vector<std::vector<JSVariant>> results;
325
295
 
326
296
  #ifdef OP_SQLITE_USE_LIBSQL
327
297
  auto status =
328
- opsqlite_libsql_execute_raw(db_name, query, &params, &results);
298
+ opsqlite_libsql_execute_raw(db, query, &params, &results);
329
299
  #else
330
- auto status = opsqlite_execute_raw(db_name, query, &params, &results);
300
+ auto status = opsqlite_execute_raw(db, query, &params, &results);
331
301
  #endif
332
302
 
333
303
  if (invalidated) {
@@ -336,21 +306,20 @@ void DBHostObject::create_jsi_functions() {
336
306
 
337
307
  invoker->invokeAsync([&rt, results = std::move(results),
338
308
  status = std::move(status), resolve, reject] {
339
- if (status.type == SQLiteOk) {
340
- auto jsiResult = create_raw_result(rt, status, &results);
341
- resolve->asObject(rt).asFunction(rt).call(rt,
342
- std::move(jsiResult));
343
- } else {
344
- auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
345
- auto error = errorCtr.callAsConstructor(
346
- rt, jsi::String::createFromUtf8(rt, status.message));
347
- reject->asObject(rt).asFunction(rt).call(rt, error);
348
- }
309
+ auto jsiResult = create_raw_result(rt, status, &results);
310
+ resolve->asObject(rt).asFunction(rt).call(rt, std::move(jsiResult));
311
+ });
312
+ } catch (std::runtime_error &e) {
313
+ auto what = e.what();
314
+ invoker->invokeAsync([&rt, what, reject] {
315
+ auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
316
+ auto error = errorCtr.callAsConstructor(
317
+ rt, jsi::String::createFromAscii(rt, what));
318
+ reject->asObject(rt).asFunction(rt).call(rt, error);
349
319
  });
350
-
351
320
  } catch (std::exception &exc) {
352
321
  auto what = exc.what();
353
- invoker->invokeAsync([&rt, what = std::move(what), reject] {
322
+ invoker->invokeAsync([&rt, what, reject] {
354
323
  auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
355
324
  auto error = errorCtr.callAsConstructor(
356
325
  rt, jsi::String::createFromAscii(rt, what));
@@ -359,7 +328,7 @@ void DBHostObject::create_jsi_functions() {
359
328
  }
360
329
  };
361
330
 
362
- thread_pool->queueWork(task);
331
+ _thread_pool->queueWork(task);
363
332
 
364
333
  return {};
365
334
  }));
@@ -367,8 +336,7 @@ void DBHostObject::create_jsi_functions() {
367
336
  return promise;
368
337
  });
369
338
 
370
- auto execute_sync = HOSTFN("executeSync") {
371
-
339
+ function_map["executeSync"] = HOSTFN("executeSync") {
372
340
  std::string query = args[0].asString(rt).utf8(rt);
373
341
  std::vector<JSVariant> params;
374
342
 
@@ -376,38 +344,31 @@ void DBHostObject::create_jsi_functions() {
376
344
  params = to_variant_vec(rt, args[1]);
377
345
  }
378
346
  #ifdef OP_SQLITE_USE_LIBSQL
379
- auto status = opsqlite_libsql_execute(db_name, query, &params);
347
+ auto status = opsqlite_libsql_execute(db, query, &params);
380
348
  #else
381
- auto status = opsqlite_execute(db_name, query, &params);
349
+ auto status = opsqlite_execute(db, query, &params);
382
350
  #endif
383
351
 
384
- if (status.type != SQLiteOk) {
385
- throw std::runtime_error(status.message);
386
- }
387
352
  return create_js_rows(rt, status);
388
353
  });
389
354
 
390
- auto execute = HOSTFN("execute") {
391
- std::string query = args[0].asString(rt).utf8(rt);
392
- std::vector<JSVariant> params;
393
-
394
- if (count == 2) {
395
- params = to_variant_vec(rt, args[1]);
396
- }
355
+ function_map["execute"] = HOSTFN("execute") {
356
+ const std::string query = args[0].asString(rt).utf8(rt);
357
+ std::vector<JSVariant> params = count == 2 && args[1].isObject()
358
+ ? to_variant_vec(rt, args[1])
359
+ : std::vector<JSVariant>();
397
360
 
398
361
  auto promiseCtr = rt.global().getPropertyAsFunction(rt, "Promise");
399
- auto promise = promiseCtr.callAsConstructor(rt, HOSTFN("executor") {
400
- auto resolve = std::make_shared<jsi::Value>(rt, args[0]);
401
- auto reject = std::make_shared<jsi::Value>(rt, args[1]);
402
-
403
- auto task = [&rt, this, query = std::move(query),
404
- params = std::move(params), resolve, reject]() {
362
+ auto promise = promiseCtr.callAsConstructor(rt,
363
+ HOSTFN("executor") {
364
+ auto task = [this, &rt, query, params,
365
+ resolve = std::make_shared<jsi::Value>(rt, args[0]),
366
+ reject = std::make_shared<jsi::Value>(rt, args[1])]() {
405
367
  try {
406
-
407
368
  #ifdef OP_SQLITE_USE_LIBSQL
408
- auto status = opsqlite_libsql_execute(db_name, query, &params);
369
+ auto status = opsqlite_libsql_execute(db, query, &params);
409
370
  #else
410
- auto status = opsqlite_execute(db_name, query, &params);
371
+ auto status = opsqlite_execute(db, query, &params);
411
372
  #endif
412
373
 
413
374
  if (invalidated) {
@@ -416,23 +377,24 @@ void DBHostObject::create_jsi_functions() {
416
377
 
417
378
  invoker->invokeAsync([&rt, status = std::move(status), resolve,
418
379
  reject] {
419
- if (status.type == SQLiteOk) {
420
- auto jsiResult = create_js_rows(rt, status);
421
- resolve->asObject(rt).asFunction(rt).call(rt,
422
- std::move(jsiResult));
423
- } else {
424
- auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
425
- auto error = errorCtr.callAsConstructor(
426
- rt, jsi::String::createFromUtf8(rt, status.message));
427
- reject->asObject(rt).asFunction(rt).call(rt, error);
428
- }
380
+ auto jsiResult = create_js_rows(rt, status);
381
+ resolve->asObject(rt).asFunction(rt).call(rt, std::move(jsiResult));
382
+ });
383
+ // On Android RN is broken and does not correctly match runtime_error
384
+ // to the generic exception We have to explicitly catch it
385
+ // https://github.com/facebook/react-native/issues/48027
386
+ } catch (std::runtime_error &e) {
387
+ auto what = e.what();
388
+ invoker->invokeAsync([&rt, what = std::string(what), reject] {
389
+ auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
390
+ auto error = errorCtr.callAsConstructor(
391
+ rt, jsi::String::createFromAscii(rt, what));
392
+ reject->asObject(rt).asFunction(rt).call(rt, error);
429
393
  });
430
-
431
394
  } catch (std::exception &exc) {
432
395
  auto what = exc.what();
433
- invoker->invokeAsync([&rt, what = std::move(what), reject] {
396
+ invoker->invokeAsync([&rt, what = std::string(what), reject] {
434
397
  auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
435
-
436
398
  auto error = errorCtr.callAsConstructor(
437
399
  rt, jsi::String::createFromAscii(rt, what));
438
400
  reject->asObject(rt).asFunction(rt).call(rt, error);
@@ -440,15 +402,15 @@ void DBHostObject::create_jsi_functions() {
440
402
  }
441
403
  };
442
404
 
443
- thread_pool->queueWork(task);
405
+ _thread_pool->queueWork(task);
444
406
 
445
407
  return {};
446
- }));
408
+ }));
447
409
 
448
410
  return promise;
449
411
  });
450
412
 
451
- auto execute_with_host_objects = HOSTFN("executeWithHostObjects") {
413
+ function_map["executeWithHostObjects"] = HOSTFN("executeWithHostObjects") {
452
414
  const std::string query = args[0].asString(rt).utf8(rt);
453
415
  std::vector<JSVariant> params;
454
416
 
@@ -462,17 +424,16 @@ void DBHostObject::create_jsi_functions() {
462
424
  auto resolve = std::make_shared<jsi::Value>(rt, args[0]);
463
425
  auto reject = std::make_shared<jsi::Value>(rt, args[1]);
464
426
 
465
- auto task = [&rt, this, query, params = std::move(params), resolve,
466
- reject, invoker = this->invoker]() {
427
+ auto task = [&rt, this, query, params, resolve, reject]() {
467
428
  try {
468
429
  std::vector<DumbHostObject> results;
469
430
  std::shared_ptr<std::vector<SmartHostObject>> metadata =
470
431
  std::make_shared<std::vector<SmartHostObject>>();
471
432
  #ifdef OP_SQLITE_USE_LIBSQL
472
433
  auto status = opsqlite_libsql_execute_with_host_objects(
473
- db_name, query, &params, &results, metadata);
434
+ db, query, &params, &results, metadata);
474
435
  #else
475
- auto status = opsqlite_execute_host_objects(db_name, query, &params,
436
+ auto status = opsqlite_execute_host_objects(db, query, &params,
476
437
  &results, metadata);
477
438
  #endif
478
439
 
@@ -484,23 +445,22 @@ void DBHostObject::create_jsi_functions() {
484
445
  [&rt,
485
446
  results = std::make_shared<std::vector<DumbHostObject>>(results),
486
447
  metadata, status = std::move(status), resolve, reject] {
487
- if (status.type == SQLiteOk) {
488
- auto jsiResult =
489
- create_result(rt, status, results.get(), metadata);
490
- resolve->asObject(rt).asFunction(rt).call(
491
- rt, std::move(jsiResult));
492
- } else {
493
- auto errorCtr =
494
- rt.global().getPropertyAsFunction(rt, "Error");
495
- auto error = errorCtr.callAsConstructor(
496
- rt, jsi::String::createFromUtf8(rt, status.message));
497
- reject->asObject(rt).asFunction(rt).call(rt, error);
498
- }
448
+ auto jsiResult =
449
+ create_result(rt, status, results.get(), metadata);
450
+ resolve->asObject(rt).asFunction(rt).call(rt,
451
+ std::move(jsiResult));
499
452
  });
500
-
453
+ } catch (std::runtime_error &e) {
454
+ auto what = e.what();
455
+ invoker->invokeAsync([&rt, what = std::string(what), reject] {
456
+ auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
457
+ auto error = errorCtr.callAsConstructor(
458
+ rt, jsi::String::createFromAscii(rt, what));
459
+ reject->asObject(rt).asFunction(rt).call(rt, error);
460
+ });
501
461
  } catch (std::exception &exc) {
502
462
  auto what = exc.what();
503
- invoker->invokeAsync([&rt, what = std::move(what), reject] {
463
+ invoker->invokeAsync([&rt, what, reject] {
504
464
  auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
505
465
  auto error = errorCtr.callAsConstructor(
506
466
  rt, jsi::String::createFromAscii(rt, what));
@@ -509,7 +469,7 @@ void DBHostObject::create_jsi_functions() {
509
469
  }
510
470
  };
511
471
 
512
- thread_pool->queueWork(task);
472
+ _thread_pool->queueWork(task);
513
473
 
514
474
  return {};
515
475
  }));
@@ -517,8 +477,8 @@ void DBHostObject::create_jsi_functions() {
517
477
  return promise;
518
478
  });
519
479
 
520
- auto execute_batch = HOSTFN("executeBatch") {
521
- if (sizeof(args) < 1) {
480
+ function_map["executeBatch"] = HOSTFN("executeBatch") {
481
+ if (count < 1) {
522
482
  throw std::runtime_error(
523
483
  "[op-sqlite][executeAsyncBatch] Incorrect parameter count");
524
484
  return {};
@@ -539,43 +499,44 @@ void DBHostObject::create_jsi_functions() {
539
499
  to_batch_arguments(rt, batchParams, &commands);
540
500
 
541
501
  auto promiseCtr = rt.global().getPropertyAsFunction(rt, "Promise");
542
- auto promise = promiseCtr.callAsConstructor(rt, HOSTFN("executor") {
502
+ auto promise = promiseCtr.callAsConstructor(rt, HOSTFN("executor") {
543
503
  auto resolve = std::make_shared<jsi::Value>(rt, args[0]);
544
504
  auto reject = std::make_shared<jsi::Value>(rt, args[1]);
545
505
 
546
- auto task = [&rt, this,
506
+ auto task = [this, &rt,
547
507
  commands =
548
508
  std::make_shared<std::vector<BatchArguments>>(commands),
549
509
  resolve, reject]() {
550
510
  try {
551
511
  #ifdef OP_SQLITE_USE_LIBSQL
552
512
  auto batchResult =
553
- opsqlite_libsql_execute_batch(db_name, commands.get());
513
+ opsqlite_libsql_execute_batch(db, commands.get());
554
514
  #else
555
- auto batchResult = opsqlite_execute_batch(db_name, commands.get());
515
+ auto batchResult = opsqlite_execute_batch(db, commands.get());
556
516
  #endif
557
517
 
558
518
  if (invalidated) {
559
519
  return;
560
520
  }
561
521
 
562
- invoker->invokeAsync([&rt, batchResult = std::move(batchResult),
563
- resolve, reject] {
564
- if (batchResult.type == SQLiteOk) {
565
- auto res = jsi::Object(rt);
566
- res.setProperty(rt, "rowsAffected",
567
- jsi::Value(batchResult.affectedRows));
568
- resolve->asObject(rt).asFunction(rt).call(rt, std::move(res));
569
- } else {
570
- auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
571
- auto error = errorCtr.callAsConstructor(
572
- rt, jsi::String::createFromUtf8(rt, batchResult.message));
573
- reject->asObject(rt).asFunction(rt).call(rt, error);
574
- }
522
+ invoker->invokeAsync(
523
+ [&rt, batchResult = std::move(batchResult), resolve] {
524
+ auto res = jsi::Object(rt);
525
+ res.setProperty(rt, "rowsAffected",
526
+ jsi::Value(batchResult.affectedRows));
527
+ resolve->asObject(rt).asFunction(rt).call(rt, std::move(res));
528
+ });
529
+ } catch (std::runtime_error &e) {
530
+ auto what = e.what();
531
+ invoker->invokeAsync([&rt, what, reject] {
532
+ auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
533
+ auto error = errorCtr.callAsConstructor(
534
+ rt, jsi::String::createFromAscii(rt, what));
535
+ reject->asObject(rt).asFunction(rt).call(rt, error);
575
536
  });
576
537
  } catch (std::exception &exc) {
577
538
  auto what = exc.what();
578
- invoker->invokeAsync([&rt, what = std::move(what), reject] {
539
+ invoker->invokeAsync([&rt, what, reject] {
579
540
  auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
580
541
  auto error = errorCtr.callAsConstructor(
581
542
  rt, jsi::String::createFromAscii(rt, what));
@@ -583,25 +544,22 @@ void DBHostObject::create_jsi_functions() {
583
544
  });
584
545
  }
585
546
  };
586
- thread_pool->queueWork(task);
547
+ _thread_pool->queueWork(task);
587
548
 
588
549
  return {};
589
- }));
550
+ }));
590
551
 
591
- return promise;
552
+ return promise;
592
553
  });
593
554
 
594
555
  #ifdef OP_SQLITE_USE_LIBSQL
595
- auto sync = HOSTFN("sync") {
596
- BridgeResult result = opsqlite_libsql_sync(db_name);
597
- if (result.type == SQLiteError) {
598
- throw std::runtime_error(result.message);
599
- }
556
+ function_map["sync"] = HOSTFN("sync") {
557
+ opsqlite_libsql_sync(db);
600
558
  return {};
601
559
  });
602
560
  #else
603
- auto load_file = HOSTFN("loadFile") {
604
- if (sizeof(args) < 1) {
561
+ function_map["loadFile"] = HOSTFN("loadFile") {
562
+ if (count < 1) {
605
563
  throw std::runtime_error(
606
564
  "[op-sqlite][loadFile] Incorrect parameter count");
607
565
  return {};
@@ -610,33 +568,32 @@ void DBHostObject::create_jsi_functions() {
610
568
  const std::string sqlFileName = args[0].asString(rt).utf8(rt);
611
569
 
612
570
  auto promiseCtr = rt.global().getPropertyAsFunction(rt, "Promise");
613
- auto promise = promiseCtr.callAsConstructor(rt, HOSTFN("executor")
614
- {
571
+ auto promise = promiseCtr.callAsConstructor(rt, HOSTFN("executor") {
615
572
  auto resolve = std::make_shared<jsi::Value>(rt, args[0]);
616
573
  auto reject = std::make_shared<jsi::Value>(rt, args[1]);
617
574
 
618
575
  auto task = [&rt, this, sqlFileName, resolve, reject]() {
619
576
  try {
620
- const auto result = importSQLFile(db_name, sqlFileName);
621
-
622
- invoker->invokeAsync([&rt, result = std::move(result), resolve,
623
- reject] {
624
- if (result.type == SQLiteOk) {
625
- auto res = jsi::Object(rt);
626
- res.setProperty(rt, "rowsAffected",
627
- jsi::Value(result.affectedRows));
628
- res.setProperty(rt, "commands", jsi::Value(result.commands));
629
- resolve->asObject(rt).asFunction(rt).call(rt, std::move(res));
630
- } else {
631
- auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
632
- auto error = errorCtr.callAsConstructor(
633
- rt, jsi::String::createFromUtf8(rt, result.message));
634
- reject->asObject(rt).asFunction(rt).call(rt, error);
635
- }
577
+ const auto result = import_sql_file(db, sqlFileName);
578
+
579
+ invoker->invokeAsync([&rt, result, resolve] {
580
+ auto res = jsi::Object(rt);
581
+ res.setProperty(rt, "rowsAffected",
582
+ jsi::Value(result.affectedRows));
583
+ res.setProperty(rt, "commands", jsi::Value(result.commands));
584
+ resolve->asObject(rt).asFunction(rt).call(rt, std::move(res));
585
+ });
586
+ } catch (std::runtime_error &e) {
587
+ auto what = e.what();
588
+ invoker->invokeAsync([&rt, what = std::string(what), reject] {
589
+ auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
590
+ auto error = errorCtr.callAsConstructor(
591
+ rt, jsi::String::createFromAscii(rt, what));
592
+ reject->asObject(rt).asFunction(rt).call(rt, error);
636
593
  });
637
594
  } catch (std::exception &exc) {
638
595
  auto what = exc.what();
639
- invoker->invokeAsync([&rt, what = std::move(what), reject] {
596
+ invoker->invokeAsync([&rt, what = std::string(what), reject] {
640
597
  auto errorCtr = rt.global().getPropertyAsFunction(rt, "Error");
641
598
  auto error = errorCtr.callAsConstructor(
642
599
  rt, jsi::String::createFromAscii(rt, what));
@@ -644,14 +601,14 @@ void DBHostObject::create_jsi_functions() {
644
601
  });
645
602
  }
646
603
  };
647
- thread_pool->queueWork(task);
604
+ _thread_pool->queueWork(task);
648
605
  return {};
649
- }));
606
+ }));
650
607
 
651
- return promise;
608
+ return promise;
652
609
  });
653
610
 
654
- auto update_hook = HOSTFN("updateHook") {
611
+ function_map["updateHook"] = HOSTFN("updateHook") {
655
612
  auto callback = std::make_shared<jsi::Value>(rt, args[0]);
656
613
 
657
614
  if (callback->isUndefined() || callback->isNull()) {
@@ -659,81 +616,57 @@ void DBHostObject::create_jsi_functions() {
659
616
  } else {
660
617
  update_hook_callback = callback;
661
618
  }
619
+
662
620
  auto_register_update_hook();
663
621
  return {};
664
622
  });
665
623
 
666
- auto commit_hook = HOSTFN("commitHook") {
667
- if (sizeof(args) < 1) {
624
+ function_map["commitHook"] = HOSTFN("commitHook") {
625
+ if (count < 1) {
668
626
  throw std::runtime_error("[op-sqlite][commitHook] callback needed");
669
- return {};
670
627
  }
671
628
 
672
629
  auto callback = std::make_shared<jsi::Value>(rt, args[0]);
673
630
  if (callback->isUndefined() || callback->isNull()) {
674
- opsqlite_deregister_commit_hook(db_name);
631
+ opsqlite_deregister_commit_hook(db);
675
632
  return {};
676
633
  }
677
634
  commit_hook_callback = callback;
678
-
679
- auto hook = [&rt, this, callback](std::string dbName) {
680
- invoker->invokeAsync(
681
- [&rt, callback] { callback->asObject(rt).asFunction(rt).call(rt); });
682
- };
683
-
684
- opsqlite_register_commit_hook(db_name, std::move(hook));
635
+ opsqlite_register_commit_hook(db, this);
685
636
 
686
637
  return {};
687
638
  });
688
639
 
689
- auto rollback_hook = HOSTFN("rollbackHook") {
690
- if (sizeof(args) < 1) {
640
+ function_map["rollbackHook"] = HOSTFN("rollbackHook") {
641
+ if (count < 1) {
691
642
  throw std::runtime_error("[op-sqlite][rollbackHook] callback needed");
692
- return {};
693
643
  }
694
644
 
695
645
  auto callback = std::make_shared<jsi::Value>(rt, args[0]);
696
646
 
697
647
  if (callback->isUndefined() || callback->isNull()) {
698
- opsqlite_deregister_rollback_hook(db_name);
648
+ opsqlite_deregister_rollback_hook(db);
699
649
  return {};
700
650
  }
701
651
  rollback_hook_callback = callback;
702
652
 
703
- auto hook = [&rt, this, callback](std::string db_name) {
704
- invoker->invokeAsync(
705
- [&rt, callback] { callback->asObject(rt).asFunction(rt).call(rt); });
706
- };
707
-
708
- opsqlite_register_rollback_hook(db_name, std::move(hook));
653
+ opsqlite_register_rollback_hook(db, this);
709
654
  return {};
710
655
  });
711
656
 
712
- auto load_extension = HOSTFN("loadExtension") {
657
+ function_map["loadExtension"] = HOSTFN("loadExtension") {
713
658
  auto path = args[0].asString(rt).utf8(rt);
714
- std::string entry_point = "";
659
+ std::string entry_point;
715
660
  if (count > 1 && args[1].isString()) {
716
661
  entry_point = args[1].asString(rt).utf8(rt);
717
662
  }
718
663
 
719
- auto result = opsqlite_load_extension(db_name, path, entry_point);
720
- if (result.type == SQLiteError) {
721
- throw std::runtime_error(result.message);
722
- }
664
+ opsqlite_load_extension(db, path, entry_point);
723
665
  return {};
724
666
  });
725
667
 
726
- auto reactive_execute = HOSTFN("reactiveExecute") {
668
+ function_map["reactiveExecute"] = HOSTFN("reactiveExecute") {
727
669
  auto query = args[0].asObject(rt);
728
- // if (!query.hasProperty(rt, "query") || !query.hasProperty(rt, "args")
729
- // ||
730
- // !query.hasProperty(rt, "tables") || !query.hasProperty(rt,
731
- // "rowIds")
732
- // || !query.hasProperty(rt, "callback")) {
733
- // throw std::runtime_error(
734
- // "[op-sqlite][reactiveExecute] Query object must have query, args,
735
- // " "tables, rowIds and callback properties");
736
- // }
737
670
 
738
671
  const std::string query_str =
739
672
  query.getProperty(rt, "query").asString(rt).utf8(rt);
@@ -742,20 +675,12 @@ void DBHostObject::create_jsi_functions() {
742
675
  query.getProperty(rt, "fireOn").asObject(rt).asArray(rt);
743
676
  auto variant_args = to_variant_vec(rt, js_args);
744
677
 
745
- sqlite3_stmt *stmt = opsqlite_prepare_statement(db_name, query_str);
678
+ sqlite3_stmt *stmt = opsqlite_prepare_statement(db, query_str);
746
679
  opsqlite_bind_statement(stmt, &variant_args);
747
680
 
748
681
  auto callback =
749
682
  std::make_shared<jsi::Value>(query.getProperty(rt, "callback"));
750
683
 
751
- // std::vector<JSVariant> query_args = to_variant_vec(rt, argsArray);
752
- // std::vector<std::string> tables = to_string_vec(rt, tablesArray);
753
- // std::vector<int> rowIds;
754
- // if (query.hasProperty(rt, "rowIds")) {
755
- // auto rowIdsArray = query.getProperty(rt, "rowIds");
756
- // rowIds = to_int_vec(rt, rowIdsArray);
757
- // }
758
-
759
684
  std::vector<TableRowDiscriminator> discriminators;
760
685
 
761
686
  for (size_t i = 0; i < js_discriminators.length(rt); i++) {
@@ -795,116 +720,103 @@ void DBHostObject::create_jsi_functions() {
795
720
 
796
721
  return unsubscribe;
797
722
  });
798
-
799
723
  #endif
800
724
 
801
- auto prepare_statement = HOSTFN("prepareStatement") {
725
+ function_map["prepareStatement"] = HOSTFN("prepareStatement") {
802
726
  auto query = args[0].asString(rt).utf8(rt);
803
727
  #ifdef OP_SQLITE_USE_LIBSQL
804
- libsql_stmt_t statement = opsqlite_libsql_prepare_statement(db_name, query);
728
+ libsql_stmt_t statement = opsqlite_libsql_prepare_statement(db, query);
805
729
  #else
806
- sqlite3_stmt *statement = opsqlite_prepare_statement(db_name, query);
730
+ sqlite3_stmt *statement = opsqlite_prepare_statement(db, query);
807
731
  #endif
808
732
  auto preparedStatementHostObject =
809
- std::make_shared<PreparedStatementHostObject>(db_name, statement,
810
- invoker, thread_pool);
733
+ std::make_shared<PreparedStatementHostObject>(db, db_name, statement,
734
+ invoker, _thread_pool);
811
735
 
812
736
  return jsi::Object::createFromHostObject(rt, preparedStatementHostObject);
813
737
  });
814
738
 
815
- auto get_db_path = HOSTFN("getDbPath") {
739
+ function_map["getDbPath"] = HOSTFN("getDbPath") {
816
740
  std::string path = std::string(base_path);
817
- if (count == 1 && !args[0].isUndefined() && !args[0].isNull()) {
818
- if (!args[0].isString()) {
819
- throw std::runtime_error(
820
- "[op-sqlite][open] database location must be a string");
821
- }
741
+ if (count == 1 && !args[0].isString()) {
742
+ throw std::runtime_error(
743
+ "[op-sqlite][open] database location must be a string");
744
+ }
822
745
 
823
- std::string lastPath = args[0].asString(rt).utf8(rt);
746
+ std::string last_path = args[0].asString(rt).utf8(rt);
824
747
 
825
- if (lastPath == ":memory:") {
826
- path = ":memory:";
827
- } else if (lastPath.rfind("/", 0) == 0) {
828
- path = lastPath;
829
- } else {
830
- path = path + "/" + lastPath;
831
- }
748
+ if (last_path == ":memory:") {
749
+ path = ":memory:";
750
+ } else if (last_path.rfind('/', 0) == 0) {
751
+ path = last_path;
752
+ } else {
753
+ path = path + "/" + last_path;
832
754
  }
833
755
 
834
756
  auto result = opsqlite_get_db_path(db_name, path);
835
757
  return jsi::String::createFromUtf8(rt, result);
836
758
  });
837
759
 
838
- auto flush_pending_reactive_queries_js =
760
+ function_map["flushPendingReactiveQueries"] =
839
761
  HOSTFN("flushPendingReactiveQueries") {
840
762
  auto promiseCtr = rt.global().getPropertyAsFunction(rt, "Promise");
841
- auto promise = promiseCtr.callAsConstructor(rt, HOSTFN("executor") {
763
+ auto promise = promiseCtr.callAsConstructor(rt, HOSTFN("executor") {
842
764
  auto resolve = std::make_shared<jsi::Value>(rt, args[0]);
843
765
 
844
766
  auto task = [&rt, this, resolve]() {
845
767
  flush_pending_reactive_queries(resolve);
846
768
  };
847
769
 
848
- thread_pool->queueWork(task);
770
+ _thread_pool->queueWork(task);
849
771
 
850
772
  return {};
851
- }));
773
+ }));
852
774
 
853
- return promise;
775
+ return promise;
854
776
  });
855
-
856
- function_map["attach"] = std::move(attach);
857
- function_map["detach"] = std::move(detach);
858
- function_map["close"] = std::move(close);
859
- function_map["execute"] = std::move(execute);
860
- function_map["executeSync"] = std::move(execute_sync);
861
- function_map["executeRaw"] = std::move(execute_raw);
862
- function_map["executeWithHostObjects"] = std::move(execute_with_host_objects);
863
- function_map["delete"] = std::move(remove);
864
- function_map["executeBatch"] = std::move(execute_batch);
865
- function_map["prepareStatement"] = std::move(prepare_statement);
866
- function_map["getDbPath"] = std::move(get_db_path);
867
- function_map["flushPendingReactiveQueries"] =
868
- std::move(flush_pending_reactive_queries_js);
869
- #ifdef OP_SQLITE_USE_LIBSQL
870
- function_map["sync"] = std::move(sync);
871
- #else
872
- function_map["loadFile"] = std::move(load_file);
873
- function_map["updateHook"] = std::move(update_hook);
874
- function_map["commitHook"] = std::move(commit_hook);
875
- function_map["rollbackHook"] = std::move(rollback_hook);
876
- function_map["loadExtension"] = std::move(load_extension);
877
- function_map["reactiveExecute"] = std::move(reactive_execute);
878
- #endif
879
777
  }
880
778
 
881
- std::vector<jsi::PropNameID> DBHostObject::getPropertyNames(jsi::Runtime &rt) {
779
+ std::vector<jsi::PropNameID> DBHostObject::getPropertyNames(jsi::Runtime &_rt) {
882
780
  std::vector<jsi::PropNameID> keys;
883
-
781
+ keys.reserve(function_map.size());
782
+ for (const auto &pair : function_map) {
783
+ keys.emplace_back(jsi::PropNameID::forUtf8(_rt, pair.first));
784
+ }
884
785
  return keys;
885
786
  }
886
787
 
887
- jsi::Value DBHostObject::get(jsi::Runtime &rt,
788
+ jsi::Value DBHostObject::get(jsi::Runtime &_rt,
888
789
  const jsi::PropNameID &propNameID) {
889
790
  auto name = propNameID.utf8(rt);
890
791
  if (function_map.count(name) != 1) {
891
- return HOSTFN(name.c_str()) {
792
+ return HOST_STATIC_FN(name.c_str()) {
892
793
  throw std::runtime_error(
893
794
  "[op-sqlite] Function " + name +
894
795
  " not implemented for current backend (libsql or sqlcipher)");
895
796
  });
896
797
  }
897
798
 
898
- return jsi::Value(rt, function_map[name]);
799
+ return {rt, function_map[name]};
899
800
  }
900
801
 
901
- void DBHostObject::set(jsi::Runtime &rt, const jsi::PropNameID &name,
802
+ void DBHostObject::set(jsi::Runtime &_rt, const jsi::PropNameID &name,
902
803
  const jsi::Value &value) {
903
804
  throw std::runtime_error("You cannot write to this object!");
904
805
  }
905
806
 
906
- void DBHostObject::invalidate() { invalidated = true; }
807
+ void DBHostObject::invalidate() {
808
+ invalidated = true;
809
+ _thread_pool->restartPool();
810
+ #ifdef OP_SQLITE_USE_LIBSQL
811
+ opsqlite_libsql_close(db);
812
+ #else
813
+ if (db != nullptr) {
814
+ opsqlite_close(db);
815
+ db = nullptr;
816
+ }
817
+ #endif
818
+ }
907
819
 
908
- DBHostObject::~DBHostObject() { invalidated = true; }
820
+ DBHostObject::~DBHostObject() { invalidate(); }
909
821
 
910
822
  } // namespace opsqlite