supastash 0.1.62 → 0.2.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.
Files changed (151) hide show
  1. package/README.md +17 -5
  2. package/dist/core/config/index.d.ts.map +1 -1
  3. package/dist/core/config/index.js +5 -1
  4. package/dist/db/adapters/expo_sqlite.d.ts.map +1 -1
  5. package/dist/db/adapters/expo_sqlite.js +11 -0
  6. package/dist/db/adapters/rn_nitro.d.ts.map +1 -1
  7. package/dist/db/adapters/rn_nitro.js +20 -0
  8. package/dist/db/adapters/rn_sqlite_storage.d.ts.map +1 -1
  9. package/dist/db/adapters/rn_sqlite_storage.js +27 -0
  10. package/dist/hooks/supastashData/fetchCalls.d.ts.map +1 -1
  11. package/dist/hooks/supastashData/index.d.ts.map +1 -1
  12. package/dist/hooks/supastashData/index.js +12 -4
  13. package/dist/hooks/supastashData/realtimeSubscription.js +4 -4
  14. package/dist/hooks/supastashData/registerSub.d.ts +3 -3
  15. package/dist/hooks/supastashData/registerSub.d.ts.map +1 -1
  16. package/dist/hooks/supastashData/registerSub.js +3 -3
  17. package/dist/hooks/supastashFilters/index.d.ts +2 -2
  18. package/dist/hooks/supastashFilters/index.d.ts.map +1 -1
  19. package/dist/hooks/supastashFilters/index.js +6 -4
  20. package/dist/hooks/supastashLiteQuery/index.d.ts.map +1 -1
  21. package/dist/hooks/supastashLiteQuery/index.js +12 -2
  22. package/dist/hooks/syncEngine/pushLocal/index.js +1 -1
  23. package/dist/index.d.ts +3 -1
  24. package/dist/index.d.ts.map +1 -1
  25. package/dist/index.js +1 -0
  26. package/dist/store/tableFilters.d.ts +3 -3
  27. package/dist/store/tableFilters.d.ts.map +1 -1
  28. package/dist/store/tx.d.ts +3 -0
  29. package/dist/store/tx.d.ts.map +1 -0
  30. package/dist/store/tx.js +1 -0
  31. package/dist/types/expoSqlite.types.d.ts +3 -13
  32. package/dist/types/index.d.ts +1 -1
  33. package/dist/types/index.d.ts.map +1 -1
  34. package/dist/types/liteQuery.types.d.ts +2 -2
  35. package/dist/types/query.types.d.ts +24 -1
  36. package/dist/types/realtimeData.types.d.ts +8 -4
  37. package/dist/types/supastashConfig.types.d.ts +83 -6
  38. package/dist/types/syncEngine.types.d.ts +49 -7
  39. package/dist/utils/errorHandler.d.ts +6 -0
  40. package/dist/utils/errorHandler.d.ts.map +1 -0
  41. package/dist/utils/errorHandler.js +8 -0
  42. package/dist/utils/fetchData/buildFilter.d.ts +8 -4
  43. package/dist/utils/fetchData/buildFilter.d.ts.map +1 -1
  44. package/dist/utils/fetchData/createTable.d.ts.map +1 -1
  45. package/dist/utils/fetchData/createTable.js +3 -46
  46. package/dist/utils/fetchData/deleteData.d.ts.map +1 -1
  47. package/dist/utils/fetchData/deleteData.js +6 -3
  48. package/dist/utils/fetchData/fetchLocalData.d.ts +2 -2
  49. package/dist/utils/fetchData/fetchLocalData.d.ts.map +1 -1
  50. package/dist/utils/fetchData/initialFetch.d.ts +2 -2
  51. package/dist/utils/fetchData/initialFetch.d.ts.map +1 -1
  52. package/dist/utils/fetchData/liteHelpers.d.ts +2 -2
  53. package/dist/utils/fetchData/liteHelpers.d.ts.map +1 -1
  54. package/dist/utils/fetchData/liteHelpers.js +14 -119
  55. package/dist/utils/fetchData/realTimeCall.js +2 -2
  56. package/dist/utils/fetchData/receiveData.js +1 -1
  57. package/dist/utils/query/builder/crud.d.ts +5 -5
  58. package/dist/utils/query/builder/crud.d.ts.map +1 -1
  59. package/dist/utils/query/builder/filters.d.ts +36 -12
  60. package/dist/utils/query/builder/filters.d.ts.map +1 -1
  61. package/dist/utils/query/builder/filters.js +32 -0
  62. package/dist/utils/query/builder/index.d.ts +29 -1
  63. package/dist/utils/query/builder/index.d.ts.map +1 -1
  64. package/dist/utils/query/builder/index.js +77 -1
  65. package/dist/utils/query/builder/mainQuery.d.ts.map +1 -1
  66. package/dist/utils/query/builder/mainQuery.js +17 -2
  67. package/dist/utils/query/helpers/localDb/getLocalMethod.d.ts +2 -2
  68. package/dist/utils/query/helpers/localDb/getLocalMethod.d.ts.map +1 -1
  69. package/dist/utils/query/helpers/localDb/getLocalMethod.js +7 -6
  70. package/dist/utils/query/helpers/localDb/insertMany.d.ts +3 -0
  71. package/dist/utils/query/helpers/localDb/insertMany.d.ts.map +1 -1
  72. package/dist/utils/query/helpers/localDb/insertMany.js +10 -3
  73. package/dist/utils/query/helpers/localDb/localQueryBuilder.d.ts +6 -6
  74. package/dist/utils/query/helpers/localDb/localQueryBuilder.d.ts.map +1 -1
  75. package/dist/utils/query/helpers/localDb/localQueryBuilder.js +17 -10
  76. package/dist/utils/query/helpers/localDb/upsertMany.d.ts +3 -0
  77. package/dist/utils/query/helpers/localDb/upsertMany.d.ts.map +1 -1
  78. package/dist/utils/query/helpers/localDb/upsertMany.js +9 -2
  79. package/dist/utils/query/helpers/mainQueryHelpers.d.ts.map +1 -1
  80. package/dist/utils/query/helpers/mainQueryHelpers.js +38 -8
  81. package/dist/utils/query/helpers/queueRemote.d.ts.map +1 -1
  82. package/dist/utils/query/helpers/queueRemote.js +33 -24
  83. package/dist/utils/query/localDbQuery/delete.d.ts +9 -3
  84. package/dist/utils/query/localDbQuery/delete.d.ts.map +1 -1
  85. package/dist/utils/query/localDbQuery/delete.js +16 -5
  86. package/dist/utils/query/localDbQuery/index.d.ts.map +1 -1
  87. package/dist/utils/query/localDbQuery/index.js +3 -3
  88. package/dist/utils/query/localDbQuery/insert.d.ts +2 -2
  89. package/dist/utils/query/localDbQuery/insert.d.ts.map +1 -1
  90. package/dist/utils/query/localDbQuery/insert.js +8 -5
  91. package/dist/utils/query/localDbQuery/select.d.ts +2 -2
  92. package/dist/utils/query/localDbQuery/select.d.ts.map +1 -1
  93. package/dist/utils/query/localDbQuery/select.js +5 -2
  94. package/dist/utils/query/localDbQuery/update.d.ts +2 -2
  95. package/dist/utils/query/localDbQuery/update.d.ts.map +1 -1
  96. package/dist/utils/query/localDbQuery/update.js +5 -2
  97. package/dist/utils/query/localDbQuery/upsert.d.ts +2 -2
  98. package/dist/utils/query/localDbQuery/upsert.d.ts.map +1 -1
  99. package/dist/utils/query/localDbQuery/upsert.js +8 -3
  100. package/dist/utils/query/remoteQuery/supabaseQuery.d.ts.map +1 -1
  101. package/dist/utils/query/remoteQuery/supabaseQuery.js +4 -1
  102. package/dist/utils/reusedHelpers.d.ts +8 -0
  103. package/dist/utils/reusedHelpers.d.ts.map +1 -0
  104. package/dist/utils/reusedHelpers.js +162 -0
  105. package/dist/utils/schema/createSyncStatus.d.ts +3 -1
  106. package/dist/utils/schema/createSyncStatus.d.ts.map +1 -1
  107. package/dist/utils/schema/createSyncStatus.js +30 -3
  108. package/dist/utils/sync/pullFromRemote/fetchOlder.d.ts +44 -0
  109. package/dist/utils/sync/pullFromRemote/fetchOlder.d.ts.map +1 -0
  110. package/dist/utils/sync/pullFromRemote/fetchOlder.js +55 -0
  111. package/dist/utils/sync/pullFromRemote/fetchOlderHelpers.d.ts +33 -0
  112. package/dist/utils/sync/pullFromRemote/fetchOlderHelpers.d.ts.map +1 -0
  113. package/dist/utils/sync/pullFromRemote/fetchOlderHelpers.js +110 -0
  114. package/dist/utils/sync/pullFromRemote/helpers.d.ts +10 -7
  115. package/dist/utils/sync/pullFromRemote/helpers.d.ts.map +1 -1
  116. package/dist/utils/sync/pullFromRemote/helpers.js +20 -14
  117. package/dist/utils/sync/pullFromRemote/pullData.d.ts +2 -3
  118. package/dist/utils/sync/pullFromRemote/pullData.d.ts.map +1 -1
  119. package/dist/utils/sync/pullFromRemote/pullData.js +4 -9
  120. package/dist/utils/sync/pullFromRemote/pullDeletedData.d.ts +8 -5
  121. package/dist/utils/sync/pullFromRemote/updateFilter.d.ts +1 -1
  122. package/dist/utils/sync/pullFromRemote/updateFilter.d.ts.map +1 -1
  123. package/dist/utils/sync/pullFromRemote/updateFilter.js +5 -3
  124. package/dist/utils/sync/pullFromRemote/updateLocalDb.d.ts +4 -3
  125. package/dist/utils/sync/pullFromRemote/updateLocalDb.d.ts.map +1 -1
  126. package/dist/utils/sync/pullFromRemote/updateLocalDb.js +51 -46
  127. package/dist/utils/sync/pullFromRemote/validateFilters.d.ts +2 -4
  128. package/dist/utils/sync/pullFromRemote/validateFilters.d.ts.map +1 -1
  129. package/dist/utils/sync/pullFromRemote/validateFilters.js +9 -63
  130. package/dist/utils/sync/pushLocal/deleteChunks.d.ts.map +1 -1
  131. package/dist/utils/sync/pushLocal/deleteChunks.js +7 -5
  132. package/dist/utils/sync/pushLocal/getAllUnsyncedData.d.ts.map +1 -1
  133. package/dist/utils/sync/pushLocal/getAllUnsyncedData.js +12 -44
  134. package/dist/utils/sync/pushLocal/uploadHelpers.js +1 -1
  135. package/dist/utils/sync/status/filterKey.d.ts +3 -3
  136. package/dist/utils/sync/status/filterKey.d.ts.map +1 -1
  137. package/dist/utils/sync/status/filterKey.js +5 -2
  138. package/dist/utils/sync/status/remoteSchema.d.ts +4 -0
  139. package/dist/utils/sync/status/remoteSchema.d.ts.map +1 -0
  140. package/dist/utils/sync/status/remoteSchema.js +140 -0
  141. package/dist/utils/sync/status/repo.d.ts +5 -5
  142. package/dist/utils/sync/status/repo.d.ts.map +1 -1
  143. package/dist/utils/sync/status/repo.js +29 -23
  144. package/dist/utils/sync/status/services.d.ts +5 -6
  145. package/dist/utils/sync/status/services.d.ts.map +1 -1
  146. package/dist/utils/sync/status/services.js +1 -6
  147. package/dist/utils/sync/status/syncStatus.d.ts +5 -7
  148. package/dist/utils/sync/status/syncStatus.d.ts.map +1 -1
  149. package/dist/utils/sync/status/syncStatus.js +11 -3
  150. package/package.json +2 -2
  151. package/dist/types/supastashFilters.types.d.ts +0 -3
@@ -35,7 +35,7 @@ export async function upsertMany(items, opts, state) {
35
35
  }
36
36
  const upserted = [];
37
37
  const remotePayload = [];
38
- const run = async () => {
38
+ const run = async (db) => {
39
39
  for (let i = 0; i < items.length; i++) {
40
40
  const input = items[i] ?? {};
41
41
  const row = { ...input };
@@ -120,7 +120,14 @@ export async function upsertMany(items, opts, state) {
120
120
  }
121
121
  };
122
122
  try {
123
- await run();
123
+ if (opts.withTx) {
124
+ await db.withTransaction(async (tx) => {
125
+ await run(tx);
126
+ });
127
+ }
128
+ else {
129
+ await run(opts.tx ?? db);
130
+ }
124
131
  const newState = { ...state, payload: remotePayload };
125
132
  if (remoteCalls.includes(newState.type)) {
126
133
  queueRemoteCall(newState);
@@ -1 +1 @@
1
- {"version":3,"file":"mainQueryHelpers.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/helpers/mainQueryHelpers.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EACL,WAAW,EACX,mBAAmB,EACnB,mBAAmB,EACnB,cAAc,EACf,MAAM,4BAA4B,CAAC;AAOpC,wBAAgB,8BAA8B,CAC5C,MAAM,EAAE,WAAW,EACnB,QAAQ,EAAE,OAAO,EACjB,OAAO,EAAE,OAAO,EAChB,KAAK,EAAE,MAAM,GACZ,IAAI,CAUN;AAED,wBAAgB,eAAe,CAAC,CAAC,EAC/B,OAAO,EAAE,CAAC,GAAG,CAAC,EAAE,GAAG,IAAI,GACtB,CAAC,GAAG,CAAC,EAAE,GAAG,IAAI,GAAG,SAAS,CAc5B;AAED,wBAAgB,cAAc,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,SAAS,WAAW,EAAE,CAAC,EAAE,CAAC,EAC3E,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,WAAW,EACnB,WAAW,EAAE,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,IAAI,EAChD,YAAY,EAAE,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,GAAG,IAAI,GAC7C,CAAC,KAAK,GAAG;IAAE,aAAa,CAAC,EAAE,cAAc,CAAA;CAAE,CAAC,GAAG,IAAI,CAwBrD;AAED,wBAAsB,eAAe,CACnC,CAAC,SAAS,WAAW,EACrB,CAAC,SAAS,OAAO,EACjB,CAAC,EACD,CAAC,EAED,KAAK,EAAE,cAAc,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,GAC7B,OAAO,CAAC;IACT,WAAW,EAAE,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC;IACjD,YAAY,EAAE,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,GAAG,IAAI,CAAC;CAChD,CAAC,CAkED"}
1
+ {"version":3,"file":"mainQueryHelpers.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/helpers/mainQueryHelpers.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,cAAc,EAAE,MAAM,uBAAuB,CAAC;AACvD,OAAO,EACL,WAAW,EACX,mBAAmB,EACnB,mBAAmB,EACnB,cAAc,EACf,MAAM,4BAA4B,CAAC;AAOpC,wBAAgB,8BAA8B,CAC5C,MAAM,EAAE,WAAW,EACnB,QAAQ,EAAE,OAAO,EACjB,OAAO,EAAE,OAAO,EAChB,KAAK,EAAE,MAAM,GACZ,IAAI,CAUN;AAED,wBAAgB,eAAe,CAAC,CAAC,EAC/B,OAAO,EAAE,CAAC,GAAG,CAAC,EAAE,GAAG,IAAI,GACtB,CAAC,GAAG,CAAC,EAAE,GAAG,IAAI,GAAG,SAAS,CAc5B;AAED,wBAAgB,cAAc,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,SAAS,WAAW,EAAE,CAAC,EAAE,CAAC,EAC3E,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,WAAW,EACnB,WAAW,EAAE,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,IAAI,EAChD,YAAY,EAAE,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,GAAG,IAAI,GAC7C,CAAC,KAAK,GAAG;IAAE,aAAa,CAAC,EAAE,cAAc,CAAA;CAAE,CAAC,GAAG,IAAI,CAwBrD;AAmDD,wBAAsB,eAAe,CACnC,CAAC,SAAS,WAAW,EACrB,CAAC,SAAS,OAAO,EACjB,CAAC,EACD,CAAC,EAED,KAAK,EAAE,cAAc,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,GAC7B,OAAO,CAAC;IACT,WAAW,EAAE,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC;IACjD,YAAY,EAAE,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,GAAG,IAAI,CAAC;CAChD,CAAC,CAiED"}
@@ -46,20 +46,45 @@ export function getCommonError(table, method, localResult, remoteResult) {
46
46
  }
47
47
  return null;
48
48
  }
49
- export async function runSyncStrategy(state) {
50
- const { type } = state;
49
+ async function handleSelect(state) {
51
50
  let localResult = null;
52
51
  let remoteResult = null;
53
- if (state.method === "select") {
54
- if (state.type.includes("remote")) {
52
+ const isEmpty = (result) => result?.error ||
53
+ !result?.data ||
54
+ (Array.isArray(result.data) && result.data.length === 0);
55
+ if (state.fetchPolicy === "localFirst") {
56
+ localResult = await queryLocalDb(state);
57
+ if (isEmpty(localResult)) {
55
58
  remoteResult = await querySupabase(state);
56
- localResult = await queryLocalDb(state);
57
- return { localResult, remoteResult };
58
59
  }
59
- else {
60
+ return { localResult, remoteResult };
61
+ }
62
+ if (state.fetchPolicy === "remoteFirst") {
63
+ remoteResult = await querySupabase(state);
64
+ if (isEmpty(remoteResult)) {
60
65
  localResult = await queryLocalDb(state);
61
- return { localResult, remoteResult };
66
+ return { localResult, remoteResult: null };
62
67
  }
68
+ return { localResult: null, remoteResult };
69
+ }
70
+ if (state.type === "remoteFirst") {
71
+ remoteResult = await querySupabase(state);
72
+ localResult = await queryLocalDb(state);
73
+ return { localResult, remoteResult };
74
+ }
75
+ if (state.type === "remoteOnly") {
76
+ remoteResult = await querySupabase(state);
77
+ return { localResult, remoteResult: null };
78
+ }
79
+ localResult = await queryLocalDb(state);
80
+ return { localResult, remoteResult };
81
+ }
82
+ export async function runSyncStrategy(state) {
83
+ const { type } = state;
84
+ let localResult = null;
85
+ let remoteResult = null;
86
+ if (state.method === "select") {
87
+ return await handleSelect(state);
63
88
  }
64
89
  const isUpsert = state.method === "upsert";
65
90
  switch (type) {
@@ -71,9 +96,14 @@ export async function runSyncStrategy(state) {
71
96
  break;
72
97
  case "localFirst":
73
98
  localResult = await queryLocalDb(state);
99
+ // If we are in a transaction, we don't want to queue a remote call
100
+ // Remote calls are handled write after the transaction is committed
101
+ if (state.txId)
102
+ return { localResult, remoteResult: null };
74
103
  if (state.viewRemoteResult) {
75
104
  if (isUpsert) {
76
105
  logWarn("Cannot view remote result for upserts. Data will still be synced.");
106
+ queueRemoteCall(state);
77
107
  return { localResult, remoteResult: null };
78
108
  }
79
109
  remoteResult = await querySupabase(state);
@@ -1 +1 @@
1
- {"version":3,"file":"queueRemote.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/helpers/queueRemote.ts"],"names":[],"mappings":"AACA,OAAO,EAEL,WAAW,EACX,cAAc,EACf,MAAM,4BAA4B,CAAC;AA0CpC,wBAAgB,eAAe,CAAC,CAAC,SAAS,WAAW,EAAE,CAAC,SAAS,OAAO,EAAE,CAAC,EACzE,KAAK,EAAE,cAAc,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,GAC7B,OAAO,CAAC,OAAO,CAAC,CAYlB"}
1
+ {"version":3,"file":"queueRemote.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/helpers/queueRemote.ts"],"names":[],"mappings":"AACA,OAAO,EAEL,WAAW,EACX,cAAc,EACf,MAAM,4BAA4B,CAAC;AAuCpC,wBAAsB,eAAe,CACnC,CAAC,SAAS,WAAW,EACrB,CAAC,SAAS,OAAO,EACjB,CAAC,EACD,KAAK,EAAE,cAAc,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,GAAG,OAAO,CAAC,OAAO,CAAC,CAalD"}
@@ -1,13 +1,12 @@
1
1
  import { getSupastashConfig } from "../../../core/config";
2
2
  import { isOnline } from "../../../utils/connection";
3
+ import { generateUUIDv4 } from "../../../utils/genUUID";
3
4
  import { log, logWarn } from "../../../utils/logs";
4
5
  import { getQueryStatusFromDb } from "../../../utils/sync/queryStatus";
5
6
  import { supastashEventBus } from "../../events/eventBus";
6
7
  import { querySupabase } from "../remoteQuery/supabaseQuery";
7
8
  let batchQueue = [];
8
9
  let isProcessing = false;
9
- let batchTimer = null;
10
- const BATCH_DELAY = 10;
11
10
  const MAX_RETRIES = 3;
12
11
  const MAX_OFFLINE_RETRIES = 5;
13
12
  const retryCount = new Map();
@@ -24,26 +23,24 @@ function delay(ms) {
24
23
  return new Promise((resolve) => setTimeout(resolve, ms));
25
24
  }
26
25
  function generateOpKey(state) {
27
- return `${state.table}_${state.method}_${state.id}_${JSON.stringify(state.payload)}`;
26
+ return state.id ? state.id : generateUUIDv4();
28
27
  }
29
- export function queueRemoteCall(state) {
30
- return new Promise((resolve, reject) => {
28
+ export async function queueRemoteCall(state) {
29
+ return new Promise(async (resolve, reject) => {
30
+ void reject;
31
31
  const opKey = generateOpKey(state);
32
32
  if (successfulCalls.has(opKey)) {
33
33
  resolve(true);
34
34
  return;
35
35
  }
36
36
  batchQueue.push({ state, opKey, resolve, reject });
37
- scheduleBatch();
37
+ await startWorkerIfNeeded();
38
38
  });
39
39
  }
40
- function scheduleBatch() {
41
- if (batchTimer)
40
+ async function startWorkerIfNeeded() {
41
+ if (isProcessing)
42
42
  return;
43
- batchTimer = setTimeout(() => {
44
- processBatch();
45
- batchTimer = null;
46
- }, BATCH_DELAY);
43
+ await processQueue();
47
44
  }
48
45
  async function executeSupabaseCall(state) {
49
46
  const config = getSupastashConfig();
@@ -51,7 +48,7 @@ async function executeSupabaseCall(state) {
51
48
  if (!Array.isArray(payload)) {
52
49
  return querySupabase(state, true);
53
50
  }
54
- const batchSize = config.supabaseBatchSize ?? 100;
51
+ const batchSize = config.supabaseBatchSize ?? 800;
55
52
  for (let i = 0; i < payload.length; i += batchSize) {
56
53
  const chunk = payload.slice(i, i + batchSize);
57
54
  const result = await querySupabase({
@@ -64,19 +61,21 @@ async function executeSupabaseCall(state) {
64
61
  }
65
62
  return { error: null };
66
63
  }
67
- async function processBatch() {
68
- if (isProcessing || batchQueue.length === 0)
64
+ async function processQueue() {
65
+ if (isProcessing)
69
66
  return;
70
67
  isProcessing = true;
71
- const batch = [...batchQueue];
72
- batchQueue = [];
73
- for (const call of batch) {
74
- const { state, opKey, resolve, reject } = call;
68
+ while (batchQueue.length > 0) {
69
+ const call = batchQueue[0];
70
+ const { state, opKey, resolve } = call;
75
71
  if (successfulCalls.has(opKey)) {
72
+ batchQueue.shift();
76
73
  resolve(true);
77
74
  continue;
78
75
  }
79
76
  try {
77
+ let shouldRemove = false;
78
+ let isSuccess = false;
80
79
  while ((retryCount.get(opKey) ?? 0) <= MAX_RETRIES) {
81
80
  const isConnected = await isOnline();
82
81
  if (!isConnected) {
@@ -85,11 +84,12 @@ async function processBatch() {
85
84
  if (offlineRetries > MAX_OFFLINE_RETRIES) {
86
85
  if (!seenFailureLog.has(opKey)) {
87
86
  seenFailureLog.add(opKey);
88
- log(`[Supastash] Offline — persisted locally, will retry later: ${opKey}`);
87
+ log(`[Supastash] Offline — persisted locally, will retry later: ${state.table} with ${state.method} `);
89
88
  }
90
89
  await getQueryStatusFromDb(state.table);
91
90
  supastashEventBus.emit("updateSyncStatus");
92
- resolve(false);
91
+ shouldRemove = true;
92
+ isSuccess = false;
93
93
  break;
94
94
  }
95
95
  await delay(1000);
@@ -101,7 +101,8 @@ async function processBatch() {
101
101
  successfulCalls.add(opKey);
102
102
  retryCount.delete(opKey);
103
103
  log(`[Supastash] Synced item on ${state.table} with ${state.method} to supabase`);
104
- resolve(true);
104
+ shouldRemove = true;
105
+ isSuccess = true;
105
106
  break;
106
107
  }
107
108
  else {
@@ -112,7 +113,8 @@ async function processBatch() {
112
113
  seenFailureLog.add(opKey);
113
114
  logWarn(`[Supastash] Duplicate key on ${state.table} (op=${state.method}) — seems already synced; will retry on next full sync: id=${state.id ?? "-"}`);
114
115
  }
115
- resolve(true);
116
+ shouldRemove = true;
117
+ isSuccess = true;
116
118
  break;
117
119
  }
118
120
  if (currentRetries >= MAX_RETRIES) {
@@ -120,18 +122,25 @@ async function processBatch() {
120
122
  seenFailureLog.add(opKey);
121
123
  logWarn(`[Supastash] Gave up on ${state.table} with ${state.method} after ${MAX_RETRIES} retries — will retry on next sync \nError message: ${error.message}`);
122
124
  }
123
- resolve(false);
125
+ shouldRemove = true;
126
+ isSuccess = false;
124
127
  break;
125
128
  }
126
129
  await delay(1000 * (currentRetries + 1));
127
130
  }
128
131
  }
132
+ if (shouldRemove) {
133
+ batchQueue.shift();
134
+ resolve(isSuccess);
135
+ }
129
136
  }
130
137
  catch (err) {
131
138
  if (!seenFailureLog.has(opKey)) {
132
139
  seenFailureLog.add(opKey);
133
140
  logWarn(`[Supastash] Unexpected error processing ${opKey} — ${String(err.message ?? err)}`);
134
141
  }
142
+ batchQueue.shift();
143
+ resolve(false);
135
144
  }
136
145
  }
137
146
  isProcessing = false;
@@ -1,16 +1,22 @@
1
- import { FilterCalls, SupatashDeleteResult, SyncMode } from "../../../types/query.types";
1
+ import { CrudMethods, FilterCalls, SupastashQuery, SupatashDeleteResult } from "../../../types/query.types";
2
+ import { SupastashSQLiteExecutor } from "../../../types/supastashConfig.types";
2
3
  /**
3
4
  * Soft delete: Sets `deleted_at` timestamp based on provided filters.
4
5
  * @param table - The name of the table to delete from
5
6
  * @param filters - The filters to apply to the delete query
6
7
  * @returns The result of the delete query
7
8
  */
8
- export declare function deleteData<Z = any>(table: string, filters: FilterCalls[] | null, syncMode?: SyncMode): Promise<SupatashDeleteResult<Z>>;
9
+ export declare function deleteData<Z = any>(state: SupastashQuery<CrudMethods, boolean, Z>): Promise<SupatashDeleteResult<Z>>;
9
10
  /**
10
11
  * Hard delete: Permanently removes a row by its `id`.
11
12
  * @param table - The name of the table to delete from
12
13
  * @param id - The id of the row to delete
13
14
  * @returns The result of the delete query
14
15
  */
15
- export declare function permanentlyDeleteData<R = any>(table: string, filters: FilterCalls[] | null): Promise<SupatashDeleteResult<R>>;
16
+ export declare function permanentlyDeleteData<R = any>({ table, filters, tx, throwOnError, }: {
17
+ table: string;
18
+ filters: FilterCalls[] | null;
19
+ tx: SupastashSQLiteExecutor | null;
20
+ throwOnError?: boolean;
21
+ }): Promise<SupatashDeleteResult<R>>;
16
22
  //# sourceMappingURL=delete.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"delete.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/delete.ts"],"names":[],"mappings":"AACA,OAAO,EACL,WAAW,EACX,oBAAoB,EACpB,QAAQ,EACT,MAAM,4BAA4B,CAAC;AAKpC;;;;;GAKG;AACH,wBAAsB,UAAU,CAAC,CAAC,GAAG,GAAG,EACtC,KAAK,EAAE,MAAM,EACb,OAAO,EAAE,WAAW,EAAE,GAAG,IAAI,EAC7B,QAAQ,CAAC,EAAE,QAAQ,GAClB,OAAO,CAAC,oBAAoB,CAAC,CAAC,CAAC,CAAC,CA+BlC;AAED;;;;;GAKG;AACH,wBAAsB,qBAAqB,CAAC,CAAC,GAAG,GAAG,EACjD,KAAK,EAAE,MAAM,EACb,OAAO,EAAE,WAAW,EAAE,GAAG,IAAI,GAC5B,OAAO,CAAC,oBAAoB,CAAC,CAAC,CAAC,CAAC,CAkBlC"}
1
+ {"version":3,"file":"delete.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/delete.ts"],"names":[],"mappings":"AACA,OAAO,EACL,WAAW,EACX,WAAW,EACX,cAAc,EACd,oBAAoB,EACrB,MAAM,4BAA4B,CAAC;AACpC,OAAO,EAAE,uBAAuB,EAAE,MAAM,sCAAsC,CAAC;AAK/E;;;;;GAKG;AACH,wBAAsB,UAAU,CAAC,CAAC,GAAG,GAAG,EACtC,KAAK,EAAE,cAAc,CAAC,WAAW,EAAE,OAAO,EAAE,CAAC,CAAC,GAC7C,OAAO,CAAC,oBAAoB,CAAC,CAAC,CAAC,CAAC,CAuClC;AAED;;;;;GAKG;AACH,wBAAsB,qBAAqB,CAAC,CAAC,GAAG,GAAG,EAAE,EACnD,KAAK,EACL,OAAO,EACP,EAAE,EACF,YAAmB,GACpB,EAAE;IACD,KAAK,EAAE,MAAM,CAAC;IACd,OAAO,EAAE,WAAW,EAAE,GAAG,IAAI,CAAC;IAC9B,EAAE,EAAE,uBAAuB,GAAG,IAAI,CAAC;IACnC,YAAY,CAAC,EAAE,OAAO,CAAC;CACxB,GAAG,OAAO,CAAC,oBAAoB,CAAC,CAAC,CAAC,CAAC,CAmBnC"}
@@ -8,25 +8,34 @@ import { buildWhereClause } from "../helpers/remoteDb/queryFilterBuilder";
8
8
  * @param filters - The filters to apply to the delete query
9
9
  * @returns The result of the delete query
10
10
  */
11
- export async function deleteData(table, filters, syncMode) {
11
+ export async function deleteData(state) {
12
+ const { table, filters, tx, type: syncMode } = state;
12
13
  await assertTableExists(table);
13
14
  const { clause, values: filterValues } = buildWhereClause(filters ?? []);
14
15
  try {
15
- const db = await getSupastashDb();
16
+ const db = tx ?? (await getSupastashDb());
16
17
  const timeStamp = new Date().toISOString();
17
18
  const itemsToBeDeleted = await db.getAllAsync(`SELECT * FROM ${table} ${clause}`, filterValues);
18
19
  await db.runAsync(`UPDATE ${table} SET deleted_at = ?, updated_at = ?, synced_at = NULL ${clause}`, [timeStamp, timeStamp, ...filterValues]);
19
20
  if (syncMode === "localOnly" || syncMode === "remoteFirst") {
20
- permanentlyDeleteData(table, filters);
21
+ await permanentlyDeleteData({
22
+ table,
23
+ filters,
24
+ tx,
25
+ throwOnError: state.throwOnError,
26
+ });
21
27
  }
22
28
  return { error: null, data: itemsToBeDeleted };
23
29
  }
24
30
  catch (error) {
25
31
  logError(`[Supastash] ${error}`);
32
+ if (state.throwOnError)
33
+ throw error;
26
34
  return {
27
35
  error: {
28
36
  message: error instanceof Error ? error.message : String(error),
29
37
  },
38
+ data: null,
30
39
  };
31
40
  }
32
41
  }
@@ -36,16 +45,18 @@ export async function deleteData(table, filters, syncMode) {
36
45
  * @param id - The id of the row to delete
37
46
  * @returns The result of the delete query
38
47
  */
39
- export async function permanentlyDeleteData(table, filters) {
48
+ export async function permanentlyDeleteData({ table, filters, tx, throwOnError = true, }) {
40
49
  await assertTableExists(table);
41
50
  try {
42
- const db = await getSupastashDb();
51
+ const db = tx ?? (await getSupastashDb());
43
52
  const { clause, values: filterValues } = buildWhereClause(filters ?? []);
44
53
  await db.runAsync(`DELETE FROM ${table} ${clause}`, filterValues);
45
54
  return { error: null };
46
55
  }
47
56
  catch (error) {
48
57
  logError(`[Supastash] ${error}`);
58
+ if (throwOnError)
59
+ throw error;
49
60
  return {
50
61
  error: {
51
62
  message: error instanceof Error ? error.message : String(error),
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,WAAW,EACX,mBAAmB,EACnB,cAAc,EACf,MAAM,4BAA4B,CAAC;AAGpC;;;;GAIG;AACH,wBAAsB,YAAY,CAChC,CAAC,SAAS,WAAW,EACrB,CAAC,SAAS,OAAO,EACjB,CAAC,EACD,CAAC,EACD,KAAK,EAAE,cAAc,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,GAAG,OAAO,CAAC,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAmCvE"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/index.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,WAAW,EACX,mBAAmB,EACnB,cAAc,EACf,MAAM,4BAA4B,CAAC;AAGpC;;;;GAIG;AACH,wBAAsB,YAAY,CAChC,CAAC,SAAS,WAAW,EACrB,CAAC,SAAS,OAAO,EACjB,CAAC,EACD,CAAC,EACD,KAAK,EAAE,cAAc,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC,GAAG,OAAO,CAAC,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAYvE"}
@@ -5,11 +5,11 @@ import getLocalMethod from "../helpers/localDb/getLocalMethod";
5
5
  * @returns The result of the query
6
6
  */
7
7
  export async function queryLocalDb(state) {
8
- const { table, method, payload, filters, limit, select, isSingle, onConflictKeys, preserveTimestamp, type, } = state;
8
+ const { method } = state;
9
9
  if (!method) {
10
- throw new Error("Method is required for local call");
10
+ throw new Error("[Supastash] Method is required for local call");
11
11
  }
12
- const query = getLocalMethod(table, method, select, payload, filters, limit, isSingle, state, onConflictKeys, type, preserveTimestamp);
12
+ const query = getLocalMethod(state);
13
13
  const result = await query();
14
14
  return result;
15
15
  }
@@ -1,4 +1,4 @@
1
- import { PayloadListResult, PayloadResult, SyncMode } from "../../../types/query.types";
1
+ import { CrudMethods, PayloadListResult, PayloadResult, SupastashQuery } from "../../../types/query.types";
2
2
  /**
3
3
  * Inserts data locally, sets synced_at to null pending update to remote server
4
4
  *
@@ -6,5 +6,5 @@ import { PayloadListResult, PayloadResult, SyncMode } from "../../../types/query
6
6
  * @param payload - The payload to insert
7
7
  * @returns a data / error object
8
8
  */
9
- export declare function insertData<T extends boolean, R, Z>(table: string, payload: R[] | null, syncMode?: SyncMode, isSingle?: T): Promise<T extends true ? PayloadResult<Z> : PayloadListResult<Z>>;
9
+ export declare function insertData<T extends boolean, R, Z>(state: SupastashQuery<CrudMethods, boolean, R>): Promise<T extends true ? PayloadResult<Z> : PayloadListResult<Z>>;
10
10
  //# sourceMappingURL=insert.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"insert.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/insert.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,iBAAiB,EACjB,aAAa,EACb,QAAQ,EACT,MAAM,4BAA4B,CAAC;AAKpC;;;;;;GAMG;AACH,wBAAsB,UAAU,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,EAAE,CAAC,EACtD,KAAK,EAAE,MAAM,EACb,OAAO,EAAE,CAAC,EAAE,GAAG,IAAI,EACnB,QAAQ,CAAC,EAAE,QAAQ,EACnB,QAAQ,CAAC,EAAE,CAAC,GACX,OAAO,CAAC,CAAC,SAAS,IAAI,GAAG,aAAa,CAAC,CAAC,CAAC,GAAG,iBAAiB,CAAC,CAAC,CAAC,CAAC,CA8BnE"}
1
+ {"version":3,"file":"insert.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/insert.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,WAAW,EACX,iBAAiB,EACjB,aAAa,EACb,cAAc,EACf,MAAM,4BAA4B,CAAC;AAKpC;;;;;;GAMG;AACH,wBAAsB,UAAU,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,EAAE,CAAC,EACtD,KAAK,EAAE,cAAc,CAAC,WAAW,EAAE,OAAO,EAAE,CAAC,CAAC,GAC7C,OAAO,CAAC,CAAC,SAAS,IAAI,GAAG,aAAa,CAAC,CAAC,CAAC,GAAG,iBAAiB,CAAC,CAAC,CAAC,CAAC,CAwCnE"}
@@ -8,17 +8,18 @@ import { insertMany } from "../helpers/localDb/insertMany";
8
8
  * @param payload - The payload to insert
9
9
  * @returns a data / error object
10
10
  */
11
- export async function insertData(table, payload, syncMode, isSingle) {
12
- if (!table)
13
- throw new Error("Table name was not provided for an insert call");
14
- if (!payload)
15
- throw new Error(`Payload data was not provided for an insert call on ${table}`);
11
+ export async function insertData(state) {
12
+ const { table, tx, type: syncMode, isSingle, withTx, payload, } = state;
16
13
  try {
14
+ if (!payload)
15
+ throw new Error(`[Supastash] Payload data was not provided for an insert call on ${table}`);
17
16
  await assertTableExists(table);
18
17
  const inserted = await insertMany(payload, {
19
18
  table,
20
19
  syncMode,
21
20
  returnInsertedRows: true,
21
+ withTx: withTx,
22
+ tx,
22
23
  });
23
24
  return {
24
25
  error: null,
@@ -27,6 +28,8 @@ export async function insertData(table, payload, syncMode, isSingle) {
27
28
  }
28
29
  catch (error) {
29
30
  logError(`[Supastash] ${error}`);
31
+ if (state.throwOnError)
32
+ throw error;
30
33
  return {
31
34
  error: {
32
35
  message: error instanceof Error ? error.message : String(error),
@@ -1,4 +1,4 @@
1
- import { FilterCalls, PayloadListResult, PayloadResult } from "../../../types/query.types";
1
+ import { CrudMethods, PayloadListResult, PayloadResult, SupastashQuery } from "../../../types/query.types";
2
2
  /**
3
3
  * Selects one or many rows from the local database.
4
4
  *
@@ -9,5 +9,5 @@ import { FilterCalls, PayloadListResult, PayloadResult } from "../../../types/qu
9
9
  * @param isSingle - Whether to return a single row or multiple rows
10
10
  * @returns a data / error object
11
11
  */
12
- export declare function selectData<T extends boolean, R, Z>(table: string, select: string, filters: FilterCalls[] | null, limit: number | null, isSingle: T): Promise<T extends true ? PayloadResult<Z> : PayloadListResult<Z>>;
12
+ export declare function selectData<T extends boolean, R, Z>(state: SupastashQuery<CrudMethods, boolean, R>): Promise<T extends true ? PayloadResult<Z> : PayloadListResult<Z>>;
13
13
  //# sourceMappingURL=select.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"select.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/select.ts"],"names":[],"mappings":"AACA,OAAO,EACL,WAAW,EACX,iBAAiB,EACjB,aAAa,EACd,MAAM,4BAA4B,CAAC;AAMpC;;;;;;;;;GASG;AACH,wBAAsB,UAAU,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,EAAE,CAAC,EACtD,KAAK,EAAE,MAAM,EACb,MAAM,EAAE,MAAM,EACd,OAAO,EAAE,WAAW,EAAE,GAAG,IAAI,EAC7B,KAAK,EAAE,MAAM,GAAG,IAAI,EACpB,QAAQ,EAAE,CAAC,GACV,OAAO,CAAC,CAAC,SAAS,IAAI,GAAG,aAAa,CAAC,CAAC,CAAC,GAAG,iBAAiB,CAAC,CAAC,CAAC,CAAC,CAoCnE"}
1
+ {"version":3,"file":"select.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/select.ts"],"names":[],"mappings":"AACA,OAAO,EACL,WAAW,EACX,iBAAiB,EACjB,aAAa,EACb,cAAc,EACf,MAAM,4BAA4B,CAAC;AAMpC;;;;;;;;;GASG;AACH,wBAAsB,UAAU,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,EAAE,CAAC,EACtD,KAAK,EAAE,cAAc,CAAC,WAAW,EAAE,OAAO,EAAE,CAAC,CAAC,GAC7C,OAAO,CAAC,CAAC,SAAS,IAAI,GAAG,aAAa,CAAC,CAAC,CAAC,GAAG,iBAAiB,CAAC,CAAC,CAAC,CAAC,CAuCnE"}
@@ -13,7 +13,8 @@ import { buildWhereClause } from "../helpers/remoteDb/queryFilterBuilder";
13
13
  * @param isSingle - Whether to return a single row or multiple rows
14
14
  * @returns a data / error object
15
15
  */
16
- export async function selectData(table, select, filters, limit, isSingle) {
16
+ export async function selectData(state) {
17
+ const { table, filters, limit, isSingle, tx, select } = state;
17
18
  if (!table)
18
19
  throw new Error("Table name was not provided for a select call");
19
20
  await assertTableExists(table);
@@ -21,7 +22,7 @@ export async function selectData(table, select, filters, limit, isSingle) {
21
22
  const limitClause = limit ? `LIMIT ${limit}` : "";
22
23
  const query = `SELECT ${select} FROM ${table} ${clause} ${limitClause}`;
23
24
  try {
24
- const db = await getSupastashDb();
25
+ const db = tx ?? (await getSupastashDb());
25
26
  let data;
26
27
  if (isSingle) {
27
28
  const result = await db.getFirstAsync(query, filterValues);
@@ -35,6 +36,8 @@ export async function selectData(table, select, filters, limit, isSingle) {
35
36
  }
36
37
  catch (error) {
37
38
  logError(`[Supastash] ${error}`);
39
+ if (state.throwOnError)
40
+ throw error;
38
41
  return {
39
42
  error: {
40
43
  message: error instanceof Error ? error.message : String(error),
@@ -1,4 +1,4 @@
1
- import { FilterCalls, PayloadListResult, PayloadResult, SyncMode } from "../../../types/query.types";
1
+ import { CrudMethods, PayloadListResult, PayloadResult, SupastashQuery } from "../../../types/query.types";
2
2
  /**
3
3
  * Updates data locally, sets synced_at to null pending update to remote server
4
4
  *
@@ -7,5 +7,5 @@ import { FilterCalls, PayloadListResult, PayloadResult, SyncMode } from "../../.
7
7
  * @param filters - The filters to apply to the update query
8
8
  * @returns a data / error object
9
9
  */
10
- export declare function updateData<T extends boolean, R, Z>(table: string, payload: R | null, filters: FilterCalls[] | null, syncMode?: SyncMode, isSingle?: T, preserveTimestamp?: boolean): Promise<T extends true ? PayloadResult<Z> : PayloadListResult<Z>>;
10
+ export declare function updateData<T extends boolean, R, Z>(state: SupastashQuery<CrudMethods, boolean, R>): Promise<T extends true ? PayloadResult<Z> : PayloadListResult<Z>>;
11
11
  //# sourceMappingURL=update.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"update.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/update.ts"],"names":[],"mappings":"AAEA,OAAO,EACL,WAAW,EAEX,iBAAiB,EACjB,aAAa,EACb,QAAQ,EACT,MAAM,4BAA4B,CAAC;AASpC;;;;;;;GAOG;AACH,wBAAsB,UAAU,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,EAAE,CAAC,EACtD,KAAK,EAAE,MAAM,EACb,OAAO,EAAE,CAAC,GAAG,IAAI,EACjB,OAAO,EAAE,WAAW,EAAE,GAAG,IAAI,EAC7B,QAAQ,CAAC,EAAE,QAAQ,EACnB,QAAQ,CAAC,EAAE,CAAC,EACZ,iBAAiB,CAAC,EAAE,OAAO,GAC1B,OAAO,CAAC,CAAC,SAAS,IAAI,GAAG,aAAa,CAAC,CAAC,CAAC,GAAG,iBAAiB,CAAC,CAAC,CAAC,CAAC,CA+EnE"}
1
+ {"version":3,"file":"update.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/update.ts"],"names":[],"mappings":"AAEA,OAAO,EACL,WAAW,EAEX,iBAAiB,EACjB,aAAa,EACb,cAAc,EACf,MAAM,4BAA4B,CAAC;AASpC;;;;;;;GAOG;AACH,wBAAsB,UAAU,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,EAAE,CAAC,EACtD,KAAK,EAAE,cAAc,CAAC,WAAW,EAAE,OAAO,EAAE,CAAC,CAAC,GAC7C,OAAO,CAAC,CAAC,SAAS,IAAI,GAAG,aAAa,CAAC,CAAC,CAAC,GAAG,iBAAiB,CAAC,CAAC,CAAC,CAAC,CA0FnE"}
@@ -14,7 +14,8 @@ const warned = new Set();
14
14
  * @param filters - The filters to apply to the update query
15
15
  * @returns a data / error object
16
16
  */
17
- export async function updateData(table, payload, filters, syncMode, isSingle, preserveTimestamp) {
17
+ export async function updateData(state) {
18
+ const { table, payload, filters, type: syncMode, isSingle, preserveTimestamp, tx, } = state;
18
19
  if (!payload)
19
20
  throw new Error(`Payload data was not provided for an update call on ${table}`);
20
21
  if (!table)
@@ -48,7 +49,7 @@ export async function updateData(table, payload, filters, syncMode, isSingle, pr
48
49
  .map((c) => getSafeValue(newPayload[c]));
49
50
  const { clause, values: filterValues } = buildWhereClause(filters ?? []);
50
51
  try {
51
- const db = await getSupastashDb();
52
+ const db = tx ?? (await getSupastashDb());
52
53
  await db.runAsync(`UPDATE ${table} SET ${cols} ${clause}`, [
53
54
  ...values,
54
55
  ...filterValues,
@@ -68,6 +69,8 @@ export async function updateData(table, payload, filters, syncMode, isSingle, pr
68
69
  }
69
70
  catch (error) {
70
71
  logError(`[Supastash] ${error}`);
72
+ if (state.throwOnError)
73
+ throw error;
71
74
  return {
72
75
  error: {
73
76
  message: error instanceof Error ? error.message : String(error),
@@ -1,9 +1,9 @@
1
- import { CrudMethods, PayloadListResult, PayloadResult, SupastashQuery, SyncMode } from "../../../types/query.types";
1
+ import { CrudMethods, PayloadListResult, PayloadResult, SupastashQuery } from "../../../types/query.types";
2
2
  /**
3
3
  * Performs upsert-like logic on local DB:
4
4
  * - If a row with the same ID exists, it is updated.
5
5
  * - Otherwise, it is inserted.
6
6
  * Returns all the rows that were upserted.
7
7
  */
8
- export declare function upsertData<T extends boolean, R, Z>(table: string, payload: R | R[] | null, state: SupastashQuery<CrudMethods, T, R>, syncMode?: SyncMode, isSingle?: T, onConflictKeys?: string[], preserveTimestamp?: boolean): Promise<T extends true ? PayloadResult<Z> : PayloadListResult<Z>>;
8
+ export declare function upsertData<T extends boolean, R, Z>(state: SupastashQuery<CrudMethods, boolean, R>): Promise<T extends true ? PayloadResult<Z> : PayloadListResult<Z>>;
9
9
  //# sourceMappingURL=upsert.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"upsert.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/upsert.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,WAAW,EACX,iBAAiB,EACjB,aAAa,EACb,cAAc,EACd,QAAQ,EACT,MAAM,4BAA4B,CAAC;AAOpC;;;;;GAKG;AACH,wBAAsB,UAAU,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,EAAE,CAAC,EACtD,KAAK,EAAE,MAAM,EACb,OAAO,EAAE,CAAC,GAAG,CAAC,EAAE,GAAG,IAAI,EACvB,KAAK,EAAE,cAAc,CAAC,WAAW,EAAE,CAAC,EAAE,CAAC,CAAC,EACxC,QAAQ,CAAC,EAAE,QAAQ,EACnB,QAAQ,CAAC,EAAE,CAAC,EACZ,cAAc,GAAE,MAAM,EAAW,EACjC,iBAAiB,CAAC,EAAE,OAAO,GAC1B,OAAO,CAAC,CAAC,SAAS,IAAI,GAAG,aAAa,CAAC,CAAC,CAAC,GAAG,iBAAiB,CAAC,CAAC,CAAC,CAAC,CAkCnE"}
1
+ {"version":3,"file":"upsert.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/localDbQuery/upsert.ts"],"names":[],"mappings":"AAAA,OAAO,EACL,WAAW,EACX,iBAAiB,EACjB,aAAa,EACb,cAAc,EACf,MAAM,4BAA4B,CAAC;AAOpC;;;;;GAKG;AACH,wBAAsB,UAAU,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,EAAE,CAAC,EACtD,KAAK,EAAE,cAAc,CAAC,WAAW,EAAE,OAAO,EAAE,CAAC,CAAC,GAC7C,OAAO,CAAC,CAAC,SAAS,IAAI,GAAG,aAAa,CAAC,CAAC,CAAC,GAAG,iBAAiB,CAAC,CAAC,CAAC,CAAC,CA+CnE"}
@@ -8,9 +8,10 @@ const warned = new Set();
8
8
  * - Otherwise, it is inserted.
9
9
  * Returns all the rows that were upserted.
10
10
  */
11
- export async function upsertData(table, payload, state, syncMode, isSingle, onConflictKeys = ["id"], preserveTimestamp) {
12
- if (!payload || !table)
13
- throw new Error("Table and payload are required for upsert.");
11
+ export async function upsertData(state) {
12
+ const { table, payload, type: syncMode, isSingle, onConflictKeys, preserveTimestamp, } = state;
13
+ if (!payload)
14
+ throw new Error(`[Supastash] Payload data was not provided for an upsert call on ${table}`);
14
15
  await assertTableExists(table);
15
16
  const items = Array.isArray(payload) ? payload : [payload];
16
17
  try {
@@ -20,6 +21,8 @@ export async function upsertData(table, payload, state, syncMode, isSingle, onCo
20
21
  returnRows: true,
21
22
  onConflictKeys,
22
23
  preserveTimestamp,
24
+ withTx: state.withTx,
25
+ tx: state.tx,
23
26
  }, state);
24
27
  return {
25
28
  error: null,
@@ -28,6 +31,8 @@ export async function upsertData(table, payload, state, syncMode, isSingle, onCo
28
31
  }
29
32
  catch (error) {
30
33
  logError(`[Supastash] ${error}`);
34
+ if (state.throwOnError)
35
+ throw error;
31
36
  return {
32
37
  error: {
33
38
  message: error instanceof Error ? error.message : String(error),
@@ -1 +1 @@
1
- {"version":3,"file":"supabaseQuery.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/remoteQuery/supabaseQuery.ts"],"names":[],"mappings":"AAEA,OAAO,EACL,WAAW,EACX,mBAAmB,EACnB,cAAc,EACf,MAAM,4BAA4B,CAAC;AAWpC;;;;;GAKG;AACH,wBAAsB,aAAa,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,EAAE,CAAC,EACzD,KAAK,EAAE,cAAc,CAAC,WAAW,EAAE,CAAC,EAAE,CAAC,CAAC,EACxC,SAAS,UAAQ,GAChB,OAAO,CAAC,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CAsNpC"}
1
+ {"version":3,"file":"supabaseQuery.d.ts","sourceRoot":"","sources":["../../../../src/utils/query/remoteQuery/supabaseQuery.ts"],"names":[],"mappings":"AAEA,OAAO,EACL,WAAW,EACX,mBAAmB,EACnB,cAAc,EACf,MAAM,4BAA4B,CAAC;AAWpC;;;;;GAKG;AACH,wBAAsB,aAAa,CAAC,CAAC,SAAS,OAAO,EAAE,CAAC,EAAE,CAAC,EACzD,KAAK,EAAE,cAAc,CAAC,WAAW,EAAE,CAAC,EAAE,CAAC,CAAC,EACxC,SAAS,UAAQ,GAChB,OAAO,CAAC,mBAAmB,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,CA0NpC"}
@@ -125,6 +125,9 @@ export async function querySupabase(state, isBatched = false) {
125
125
  (viewRemoteResult || type === "remoteOnly")) {
126
126
  filterQuery = filterQuery.select();
127
127
  }
128
+ if (state.throwOnError) {
129
+ filterQuery = filterQuery.throwOnError();
130
+ }
128
131
  const result = await filterQuery;
129
132
  const db = await getSupastashDb();
130
133
  if (result.error) {
@@ -162,7 +165,7 @@ export async function querySupabase(state, isBatched = false) {
162
165
  ...filterValues,
163
166
  ]);
164
167
  if (method === "delete") {
165
- await permanentlyDeleteData(table, filters);
168
+ await permanentlyDeleteData({ table, filters, tx: state.tx });
166
169
  }
167
170
  }
168
171
  refreshScreen(table);
@@ -0,0 +1,8 @@
1
+ import { SupastashFilter } from "../types/realtimeData.types";
2
+ export declare const ReusedHelpers: {
3
+ isValidFilter<R = any>(filters: SupastashFilter<R>[]): boolean;
4
+ applyFilters(q: any, filters: SupastashFilter[], table: string): any;
5
+ buildFilterString<R = any>(filter: SupastashFilter<R> | undefined): string | undefined;
6
+ buildFilterForSql<R = any>(filter: SupastashFilter<R> | undefined): string | undefined;
7
+ };
8
+ //# sourceMappingURL=reusedHelpers.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"reusedHelpers.d.ts","sourceRoot":"","sources":["../../src/utils/reusedHelpers.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,eAAe,EAAE,MAAM,6BAA6B,CAAC;AAa9D,eAAO,MAAM,aAAa;kBACV,CAAC,iBAAiB,eAAe,CAAC,CAAC,CAAC,EAAE,GAAG,OAAO;oBA8C9C,GAAG,WAAW,eAAe,EAAE,SAAS,MAAM;sBAoC5C,CAAC,gBACT,eAAe,CAAC,CAAC,CAAC,GAAG,SAAS,GACrC,MAAM,GAAG,SAAS;sBA4CH,CAAC,gBACT,eAAe,CAAC,CAAC,CAAC,GAAG,SAAS,GACrC,MAAM,GAAG,SAAS;CAkDtB,CAAC"}