supastash 0.2.15 → 0.2.17
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.
- package/dist/desktop/hooks/syncEngine.d.ts.map +1 -1
- package/dist/desktop/hooks/syncEngine.js +14 -9
- package/dist/desktop/utils/sync/pullFromRemote/pullFromRemoteBatch.d.ts +1 -1
- package/dist/desktop/utils/sync/pullFromRemote/pullFromRemoteBatch.d.ts.map +1 -1
- package/dist/desktop/utils/sync/pullFromRemote/pullFromRemoteBatch.js +2 -2
- package/dist/native/hooks/syncEngine.d.ts.map +1 -1
- package/dist/native/hooks/syncEngine.js +6 -1
- package/dist/native/utils/sync/pullFromRemote/pullFromRemoteBatch.d.ts +1 -1
- package/dist/native/utils/sync/pullFromRemote/pullFromRemoteBatch.d.ts.map +1 -1
- package/dist/native/utils/sync/pullFromRemote/pullFromRemoteBatch.js +31 -12
- package/dist/shared/utils/sync/pushLocal/getAllUnsyncedData.d.ts +9 -0
- package/dist/shared/utils/sync/pushLocal/getAllUnsyncedData.d.ts.map +1 -1
- package/dist/shared/utils/sync/pushLocal/getAllUnsyncedData.js +100 -5
- package/package.json +1 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"syncEngine.d.ts","sourceRoot":"","sources":["../../../src/desktop/hooks/syncEngine.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"syncEngine.d.ts","sourceRoot":"","sources":["../../../src/desktop/hooks/syncEngine.ts"],"names":[],"mappings":"AA8BA;;;;;GAKG;AACH,wBAAsB,OAAO,CAAC,KAAK,GAAE,OAAe,GAAG,OAAO,CAAC,IAAI,CAAC,CAqCnE;AAyDD;;;;;GAKG;AACH,wBAAgB,aAAa;;;EA2D5B;AAMD;;;;GAIG;AACH,wBAAsB,SAAS,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAoC5D;AAED;;GAEG;AACH,wBAAsB,aAAa,IAAI,OAAO,CAAC,IAAI,CAAC,CAEnD"}
|
|
@@ -9,6 +9,7 @@ import { subscribeToAppVisibility } from "../adapters/appstate";
|
|
|
9
9
|
import { pullFromRemote as doPullFromRemote } from "../utils/sync/pullFromRemote";
|
|
10
10
|
import { pullFromRemoteBatch } from "../utils/sync/pullFromRemote/pullFromRemoteBatch";
|
|
11
11
|
import { updateLocalDb } from "../utils/sync/pullFromRemote/updateLocalDb";
|
|
12
|
+
import { pushLocalData as doPushLocalData } from "../utils/sync/pushLocal";
|
|
12
13
|
import { pushLocalDataToRemote } from "../utils/sync/pushLocal/sendUnsyncedToSupabase";
|
|
13
14
|
// -----------------------------
|
|
14
15
|
// Module-scoped state & tunables
|
|
@@ -85,12 +86,7 @@ async function pushLocalDataSafe() {
|
|
|
85
86
|
return;
|
|
86
87
|
isPushing = true;
|
|
87
88
|
try {
|
|
88
|
-
|
|
89
|
-
await pullFromRemoteBatch();
|
|
90
|
-
}
|
|
91
|
-
else {
|
|
92
|
-
await doPullFromRemote();
|
|
93
|
-
}
|
|
89
|
+
await doPushLocalData();
|
|
94
90
|
lastPushAt = Date.now();
|
|
95
91
|
}
|
|
96
92
|
catch (e) {
|
|
@@ -108,7 +104,6 @@ async function pullFromRemoteSafe() {
|
|
|
108
104
|
return;
|
|
109
105
|
if (!(await isOnline()))
|
|
110
106
|
return;
|
|
111
|
-
// If in ghost mode, don't pull
|
|
112
107
|
const cfg = getSupastashConfig();
|
|
113
108
|
if (cfg.supastashMode === "ghost")
|
|
114
109
|
return;
|
|
@@ -116,7 +111,12 @@ async function pullFromRemoteSafe() {
|
|
|
116
111
|
return;
|
|
117
112
|
isPulling = true;
|
|
118
113
|
try {
|
|
119
|
-
|
|
114
|
+
if (cfg.useBatchPullSync) {
|
|
115
|
+
await pullFromRemoteBatch();
|
|
116
|
+
}
|
|
117
|
+
else {
|
|
118
|
+
await doPullFromRemote();
|
|
119
|
+
}
|
|
120
120
|
lastPullAt = Date.now();
|
|
121
121
|
}
|
|
122
122
|
catch (e) {
|
|
@@ -206,7 +206,12 @@ export async function syncTable(table) {
|
|
|
206
206
|
// Pull
|
|
207
207
|
if (cfg.syncEngine?.pull) {
|
|
208
208
|
try {
|
|
209
|
-
|
|
209
|
+
if (cfg.useBatchPullSync) {
|
|
210
|
+
await pullFromRemoteBatch([table]);
|
|
211
|
+
}
|
|
212
|
+
else {
|
|
213
|
+
await updateLocalDb(table, filter, syncCalls.get(table)?.pull);
|
|
214
|
+
}
|
|
210
215
|
}
|
|
211
216
|
catch (e) {
|
|
212
217
|
log("[Supastash] syncTable pull error", {
|
|
@@ -5,5 +5,5 @@
|
|
|
5
5
|
* Requires `useBatchPullSync: true` in config and the
|
|
6
6
|
* `supastash_pull_sync` Postgres function to be deployed.
|
|
7
7
|
*/
|
|
8
|
-
export declare function pullFromRemoteBatch(): Promise<void>;
|
|
8
|
+
export declare function pullFromRemoteBatch(specificTables?: string[]): Promise<void>;
|
|
9
9
|
//# sourceMappingURL=pullFromRemoteBatch.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"pullFromRemoteBatch.d.ts","sourceRoot":"","sources":["../../../../../src/desktop/utils/sync/pullFromRemote/pullFromRemoteBatch.ts"],"names":[],"mappings":"AA+CA;;;;;;GAMG;AACH,wBAAsB,mBAAmB,
|
|
1
|
+
{"version":3,"file":"pullFromRemoteBatch.d.ts","sourceRoot":"","sources":["../../../../../src/desktop/utils/sync/pullFromRemote/pullFromRemoteBatch.ts"],"names":[],"mappings":"AA+CA;;;;;;GAMG;AACH,wBAAsB,mBAAmB,CACvC,cAAc,CAAC,EAAE,MAAM,EAAE,GACxB,OAAO,CAAC,IAAI,CAAC,CA4Mf"}
|
|
@@ -37,14 +37,14 @@ function buildCursorFilter(tsCol, lastSyncedAt, lastPk) {
|
|
|
37
37
|
* Requires `useBatchPullSync: true` in config and the
|
|
38
38
|
* `supastash_pull_sync` Postgres function to be deployed.
|
|
39
39
|
*/
|
|
40
|
-
export async function pullFromRemoteBatch() {
|
|
40
|
+
export async function pullFromRemoteBatch(specificTables) {
|
|
41
41
|
const cfg = getSupastashConfig();
|
|
42
42
|
const supabase = cfg.supabaseClient;
|
|
43
43
|
if (!supabase)
|
|
44
44
|
throw new Error(`No supabase client found: ${supabaseClientErr}`);
|
|
45
45
|
if (cfg.supastashMode === "ghost")
|
|
46
46
|
return;
|
|
47
|
-
const tables = await getAllTables();
|
|
47
|
+
const tables = specificTables ?? (await getAllTables());
|
|
48
48
|
if (!tables) {
|
|
49
49
|
log("[Supastash] Batch pull: no tables found");
|
|
50
50
|
return;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"syncEngine.d.ts","sourceRoot":"","sources":["../../../src/native/hooks/syncEngine.ts"],"names":[],"mappings":"AA8BA;;;;;GAKG;AACH,wBAAsB,OAAO,CAAC,KAAK,GAAE,OAAe,GAAG,OAAO,CAAC,IAAI,CAAC,CAqCnE;AAyDD;;;;;GAKG;AACH,wBAAgB,aAAa;;;EA+D5B;AAMD;;;;GAIG;AACH,wBAAsB,SAAS,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,
|
|
1
|
+
{"version":3,"file":"syncEngine.d.ts","sourceRoot":"","sources":["../../../src/native/hooks/syncEngine.ts"],"names":[],"mappings":"AA8BA;;;;;GAKG;AACH,wBAAsB,OAAO,CAAC,KAAK,GAAE,OAAe,GAAG,OAAO,CAAC,IAAI,CAAC,CAqCnE;AAyDD;;;;;GAKG;AACH,wBAAgB,aAAa;;;EA+D5B;AAMD;;;;GAIG;AACH,wBAAsB,SAAS,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC,CAoC5D;AAED;;GAEG;AACH,wBAAsB,aAAa,IAAI,OAAO,CAAC,IAAI,CAAC,CAEnD"}
|
|
@@ -208,7 +208,12 @@ export async function syncTable(table) {
|
|
|
208
208
|
// Pull
|
|
209
209
|
if (cfg.syncEngine?.pull) {
|
|
210
210
|
try {
|
|
211
|
-
|
|
211
|
+
if (cfg.useBatchPullSync) {
|
|
212
|
+
await pullFromRemoteBatch([table]);
|
|
213
|
+
}
|
|
214
|
+
else {
|
|
215
|
+
await updateLocalDb(table, filter, syncCalls.get(table)?.pull);
|
|
216
|
+
}
|
|
212
217
|
}
|
|
213
218
|
catch (e) {
|
|
214
219
|
log("[Supastash] syncTable pull error", {
|
|
@@ -5,5 +5,5 @@
|
|
|
5
5
|
* Requires `useBatchPullSync: true` in config and the
|
|
6
6
|
* `supastash_pull_sync` Postgres function to be deployed.
|
|
7
7
|
*/
|
|
8
|
-
export declare function pullFromRemoteBatch(): Promise<void>;
|
|
8
|
+
export declare function pullFromRemoteBatch(specificTables?: string[]): Promise<void>;
|
|
9
9
|
//# sourceMappingURL=pullFromRemoteBatch.d.ts.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"pullFromRemoteBatch.d.ts","sourceRoot":"","sources":["../../../../../src/native/utils/sync/pullFromRemote/pullFromRemoteBatch.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"pullFromRemoteBatch.d.ts","sourceRoot":"","sources":["../../../../../src/native/utils/sync/pullFromRemote/pullFromRemoteBatch.ts"],"names":[],"mappings":"AA+CA;;;;;;GAMG;AACH,wBAAsB,mBAAmB,CACvC,cAAc,CAAC,EAAE,MAAM,EAAE,GACxB,OAAO,CAAC,IAAI,CAAC,CA4Mf"}
|
|
@@ -2,16 +2,16 @@ import { getSupastashConfig } from "../../../../shared/core/config";
|
|
|
2
2
|
import { getSupastashDb } from "../../../../shared/db/dbInitializer";
|
|
3
3
|
import { rpcTableFilters } from "../../../../shared/store/rpcTableFilters";
|
|
4
4
|
import { tableFilters } from "../../../../shared/store/tableFilters";
|
|
5
|
-
import {
|
|
5
|
+
import log, { logError, logWarn } from "../../../../shared/utils/logs";
|
|
6
|
+
import { refreshScreen } from "../../../../shared/utils/refreshScreenCalls";
|
|
7
|
+
import { supabaseClientErr } from "../../../../shared/utils/supabaseClientErr";
|
|
6
8
|
import { getAllTables } from "../../../../shared/utils/sync/getAllTables";
|
|
7
9
|
import { getMaxSyncLookBack, logNoUpdates, returnMaxDate, } from "../../../../shared/utils/sync/pullFromRemote/helpers";
|
|
10
|
+
import { postgrestFiltersToRpc } from "../../../../shared/utils/sync/pullFromRemote/postgrestToRpc";
|
|
8
11
|
import { SyncInfoUpdater } from "../../../../shared/utils/sync/queryStatus";
|
|
9
|
-
import { refreshScreen } from "../../../../shared/utils/refreshScreenCalls";
|
|
10
|
-
import log, { logError, logWarn } from "../../../../shared/utils/logs";
|
|
11
|
-
import { supabaseClientErr } from "../../../../shared/utils/supabaseClientErr";
|
|
12
12
|
import { prefetchRemoteTableSchemas } from "../../../../shared/utils/sync/status/remoteSchema";
|
|
13
|
-
import { setSupastashSyncStatus } from "../status/services";
|
|
14
13
|
import { selectSyncStatus } from "../status/repo";
|
|
14
|
+
import { setSupastashSyncStatus } from "../status/services";
|
|
15
15
|
import { upsertChunkData } from "./updateLocalDb";
|
|
16
16
|
const CHUNK_SIZE = 999;
|
|
17
17
|
function buildCursorFilter(tsCol, lastSyncedAt, lastPk) {
|
|
@@ -37,14 +37,14 @@ function buildCursorFilter(tsCol, lastSyncedAt, lastPk) {
|
|
|
37
37
|
* Requires `useBatchPullSync: true` in config and the
|
|
38
38
|
* `supastash_pull_sync` Postgres function to be deployed.
|
|
39
39
|
*/
|
|
40
|
-
export async function pullFromRemoteBatch() {
|
|
40
|
+
export async function pullFromRemoteBatch(specificTables) {
|
|
41
41
|
const cfg = getSupastashConfig();
|
|
42
42
|
const supabase = cfg.supabaseClient;
|
|
43
43
|
if (!supabase)
|
|
44
44
|
throw new Error(`No supabase client found: ${supabaseClientErr}`);
|
|
45
45
|
if (cfg.supastashMode === "ghost")
|
|
46
46
|
return;
|
|
47
|
-
const tables = await getAllTables();
|
|
47
|
+
const tables = specificTables ?? (await getAllTables());
|
|
48
48
|
if (!tables) {
|
|
49
49
|
log("[Supastash] Batch pull: no tables found");
|
|
50
50
|
return;
|
|
@@ -57,7 +57,10 @@ export async function pullFromRemoteBatch() {
|
|
|
57
57
|
const db = await getSupastashDb();
|
|
58
58
|
const completedTables = new Set();
|
|
59
59
|
SyncInfoUpdater.setInProgress({ action: "start", type: "pull" });
|
|
60
|
-
SyncInfoUpdater.setNumberOfTables({
|
|
60
|
+
SyncInfoUpdater.setNumberOfTables({
|
|
61
|
+
amount: tablesToPull.length,
|
|
62
|
+
type: "pull",
|
|
63
|
+
});
|
|
61
64
|
// Warm schema cache for all tables in one call if enabled
|
|
62
65
|
if (cfg.useBatchSchemaFetch) {
|
|
63
66
|
await prefetchRemoteTableSchemas(tablesToPull);
|
|
@@ -112,8 +115,16 @@ export async function pullFromRemoteBatch() {
|
|
|
112
115
|
logWarn(`[Supastash] Batch: skipped row without id from "${table}"`);
|
|
113
116
|
continue;
|
|
114
117
|
}
|
|
115
|
-
prevMaxSyncedAt = returnMaxDate({
|
|
116
|
-
|
|
118
|
+
prevMaxSyncedAt = returnMaxDate({
|
|
119
|
+
row,
|
|
120
|
+
prevMax: prevMaxSyncedAt,
|
|
121
|
+
col: tsCol,
|
|
122
|
+
});
|
|
123
|
+
prevMaxDeletedAt = returnMaxDate({
|
|
124
|
+
row,
|
|
125
|
+
prevMax: prevMaxDeletedAt,
|
|
126
|
+
col: "deleted_at",
|
|
127
|
+
});
|
|
117
128
|
if (row.deleted_at) {
|
|
118
129
|
toDelete.push(row.id);
|
|
119
130
|
}
|
|
@@ -121,8 +132,16 @@ export async function pullFromRemoteBatch() {
|
|
|
121
132
|
toUpsert.push(row);
|
|
122
133
|
}
|
|
123
134
|
}
|
|
124
|
-
SyncInfoUpdater.setUnsyncedDataCount({
|
|
125
|
-
|
|
135
|
+
SyncInfoUpdater.setUnsyncedDataCount({
|
|
136
|
+
amount: toUpsert.length,
|
|
137
|
+
type: "pull",
|
|
138
|
+
table,
|
|
139
|
+
});
|
|
140
|
+
SyncInfoUpdater.setUnsyncedDeletedCount({
|
|
141
|
+
amount: toDelete.length,
|
|
142
|
+
type: "pull",
|
|
143
|
+
table,
|
|
144
|
+
});
|
|
126
145
|
// Delete soft-deleted rows
|
|
127
146
|
if (toDelete.length > 0) {
|
|
128
147
|
for (let i = 0; i < toDelete.length; i += CHUNK_SIZE) {
|
|
@@ -1,4 +1,13 @@
|
|
|
1
1
|
import { PayloadData } from "../../../types/query.types";
|
|
2
|
+
import { SupastashFilter } from "../../../types/realtimeData.types";
|
|
3
|
+
/**
|
|
4
|
+
* Builds a combined " AND (...)" SQL string + params array from a list of filters.
|
|
5
|
+
* Never throws — malformed filters are skipped and logged.
|
|
6
|
+
*/
|
|
7
|
+
export declare function buildFilterSql(filters: SupastashFilter[]): {
|
|
8
|
+
sql: string;
|
|
9
|
+
params: unknown[];
|
|
10
|
+
};
|
|
2
11
|
/**
|
|
3
12
|
* Gets all unsynced data from a table
|
|
4
13
|
* @param table - The table to get the data from
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"getAllUnsyncedData.d.ts","sourceRoot":"","sources":["../../../../../src/shared/utils/sync/pushLocal/getAllUnsyncedData.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"getAllUnsyncedData.d.ts","sourceRoot":"","sources":["../../../../../src/shared/utils/sync/pushLocal/getAllUnsyncedData.ts"],"names":[],"mappings":"AAEA,OAAO,EAAE,WAAW,EAAE,MAAM,4BAA4B,CAAC;AACzD,OAAO,EAAE,eAAe,EAAE,MAAM,mCAAmC,CAAC;AAgGpE;;;GAGG;AACH,wBAAgB,cAAc,CAAC,OAAO,EAAE,eAAe,EAAE,GAAG;IAC1D,GAAG,EAAE,MAAM,CAAC;IACZ,MAAM,EAAE,OAAO,EAAE,CAAC;CACnB,CAYA;AAmCD;;;;GAIG;AACH,wBAAsB,kBAAkB,CACtC,KAAK,EAAE,MAAM,GACZ,OAAO,CAAC,WAAW,EAAE,GAAG,IAAI,CAAC,CAuB/B;AAED;;;;GAIG;AACH,wBAAsB,iBAAiB,CACrC,KAAK,EAAE,MAAM,GACZ,OAAO,CAAC,WAAW,EAAE,GAAG,IAAI,CAAC,CAS/B"}
|
|
@@ -1,8 +1,99 @@
|
|
|
1
1
|
import { getSupastashDb } from "../../../db/dbInitializer";
|
|
2
|
+
import { tableFilters } from "../../../store/tableFilters";
|
|
2
3
|
import { getTableSchema } from "../../getTableSchema";
|
|
3
4
|
import log from "../../logs";
|
|
4
5
|
import { getRemoteTableSchema } from "../status/remoteSchema";
|
|
5
6
|
const sharedKeysCache = new Map();
|
|
7
|
+
const VALID_OPERATORS = new Set([
|
|
8
|
+
"eq",
|
|
9
|
+
"neq",
|
|
10
|
+
"gt",
|
|
11
|
+
"gte",
|
|
12
|
+
"lt",
|
|
13
|
+
"lte",
|
|
14
|
+
"is",
|
|
15
|
+
"in",
|
|
16
|
+
]);
|
|
17
|
+
function escapeColumn(column) {
|
|
18
|
+
// Basic guard against injection via column names (should only ever be internal identifiers)
|
|
19
|
+
return `"${column.replace(/"/g, '""')}"`;
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Builds a single SQL clause + params for one filter condition.
|
|
23
|
+
* Returns null (instead of throwing) if the filter is malformed.
|
|
24
|
+
*/
|
|
25
|
+
function buildSingleClause(f) {
|
|
26
|
+
try {
|
|
27
|
+
// Composite OR filter: { or: SupastashFilter[] }
|
|
28
|
+
if ("or" in f && Array.isArray(f.or)) {
|
|
29
|
+
const orFilters = f.or;
|
|
30
|
+
const built = orFilters
|
|
31
|
+
.map((sub) => buildSingleClause(sub))
|
|
32
|
+
.filter((c) => !!c);
|
|
33
|
+
if (!built.length)
|
|
34
|
+
return null;
|
|
35
|
+
const sql = "(" + built.map((c) => c.sql).join(" OR ") + ")";
|
|
36
|
+
const params = built.flatMap((c) => c.params);
|
|
37
|
+
return { sql, params };
|
|
38
|
+
}
|
|
39
|
+
// Flat filter: { column, operator, value }
|
|
40
|
+
const { column, operator, value } = f;
|
|
41
|
+
if (!column || !operator || !VALID_OPERATORS.has(operator)) {
|
|
42
|
+
log(`[Supastash] Skipping invalid filter: ${JSON.stringify(f)}`);
|
|
43
|
+
return null;
|
|
44
|
+
}
|
|
45
|
+
const col = escapeColumn(column);
|
|
46
|
+
switch (operator) {
|
|
47
|
+
case "is":
|
|
48
|
+
// sqlite uses IS for null comparisons; also support IS TRUE/FALSE-ish via 0/1
|
|
49
|
+
if (value === null) {
|
|
50
|
+
return { sql: `${col} IS NULL`, params: [] };
|
|
51
|
+
}
|
|
52
|
+
return { sql: `${col} IS ?`, params: [value] };
|
|
53
|
+
case "in": {
|
|
54
|
+
const values = Array.isArray(value) ? value : [value];
|
|
55
|
+
if (!values.length)
|
|
56
|
+
return null;
|
|
57
|
+
const placeholders = values.map(() => "?").join(", ");
|
|
58
|
+
return { sql: `${col} IN (${placeholders})`, params: values };
|
|
59
|
+
}
|
|
60
|
+
case "eq":
|
|
61
|
+
return { sql: `${col} = ?`, params: [value] };
|
|
62
|
+
case "neq":
|
|
63
|
+
return { sql: `${col} != ?`, params: [value] };
|
|
64
|
+
case "gt":
|
|
65
|
+
return { sql: `${col} > ?`, params: [value] };
|
|
66
|
+
case "gte":
|
|
67
|
+
return { sql: `${col} >= ?`, params: [value] };
|
|
68
|
+
case "lt":
|
|
69
|
+
return { sql: `${col} < ?`, params: [value] };
|
|
70
|
+
case "lte":
|
|
71
|
+
return { sql: `${col} <= ?`, params: [value] };
|
|
72
|
+
default:
|
|
73
|
+
return null;
|
|
74
|
+
}
|
|
75
|
+
}
|
|
76
|
+
catch (err) {
|
|
77
|
+
log(`[Supastash] Failed to build filter clause: ${String(err)}`);
|
|
78
|
+
return null;
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
/**
|
|
82
|
+
* Builds a combined " AND (...)" SQL string + params array from a list of filters.
|
|
83
|
+
* Never throws — malformed filters are skipped and logged.
|
|
84
|
+
*/
|
|
85
|
+
export function buildFilterSql(filters) {
|
|
86
|
+
if (!filters?.length)
|
|
87
|
+
return { sql: "", params: [] };
|
|
88
|
+
const clauses = filters
|
|
89
|
+
.map((f) => buildSingleClause(f))
|
|
90
|
+
.filter((c) => !!c);
|
|
91
|
+
if (!clauses.length)
|
|
92
|
+
return { sql: "", params: [] };
|
|
93
|
+
const sql = " AND " + clauses.map((c) => c.sql).join(" AND ");
|
|
94
|
+
const params = clauses.flatMap((c) => c.params);
|
|
95
|
+
return { sql, params };
|
|
96
|
+
}
|
|
6
97
|
async function getRemoteKeys(table) {
|
|
7
98
|
if (sharedKeysCache.has(table)) {
|
|
8
99
|
return sharedKeysCache.get(table);
|
|
@@ -30,15 +121,17 @@ async function getRemoteKeys(table) {
|
|
|
30
121
|
*/
|
|
31
122
|
export async function getAllUnsyncedData(table) {
|
|
32
123
|
const db = await getSupastashDb();
|
|
124
|
+
const filters = tableFilters.get(table) ?? [];
|
|
125
|
+
const filterSqlDetails = buildFilterSql(filters);
|
|
33
126
|
const remoteKeys = await getRemoteKeys(table);
|
|
34
127
|
if (!remoteKeys) {
|
|
35
|
-
const query = `SELECT * FROM ${table} WHERE synced_at IS NULL AND deleted_at IS NULL`;
|
|
36
|
-
const data = await db.getAllAsync(query);
|
|
128
|
+
const query = `SELECT * FROM ${table} WHERE synced_at IS NULL AND deleted_at IS NULL${filterSqlDetails.sql}`;
|
|
129
|
+
const data = await db.getAllAsync(query, filterSqlDetails.params);
|
|
37
130
|
return data ?? null;
|
|
38
131
|
}
|
|
39
132
|
const columns = remoteKeys.join(", ");
|
|
40
|
-
const query = `SELECT ${columns} FROM ${table} WHERE synced_at IS NULL AND deleted_at IS NULL`;
|
|
41
|
-
const data = await db.getAllAsync(query);
|
|
133
|
+
const query = `SELECT ${columns} FROM ${table} WHERE synced_at IS NULL AND deleted_at IS NULL${filterSqlDetails.sql}`;
|
|
134
|
+
const data = await db.getAllAsync(query, filterSqlDetails.params);
|
|
42
135
|
return data ?? null;
|
|
43
136
|
}
|
|
44
137
|
/**
|
|
@@ -48,6 +141,8 @@ export async function getAllUnsyncedData(table) {
|
|
|
48
141
|
*/
|
|
49
142
|
export async function getAllDeletedData(table) {
|
|
50
143
|
const db = await getSupastashDb();
|
|
51
|
-
const
|
|
144
|
+
const filters = tableFilters.get(table) ?? [];
|
|
145
|
+
const filterSqlDetails = buildFilterSql(filters);
|
|
146
|
+
const data = await db.getAllAsync(`SELECT deleted_at, id FROM ${table} WHERE deleted_at IS NOT NULL${filterSqlDetails.sql}`, filterSqlDetails.params);
|
|
52
147
|
return data ?? null;
|
|
53
148
|
}
|