@taruvi/refine-providers 1.1.8 → 1.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.
- package/dist/index.cjs +249 -218
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +2 -27
- package/dist/index.d.ts +2 -27
- package/dist/index.js +249 -218
- package/dist/index.js.map +1 -1
- package/package.json +2 -2
package/dist/index.js
CHANGED
|
@@ -1,32 +1,51 @@
|
|
|
1
|
-
import { Graph, Database, Storage, Functions, Analytics, App, User, Auth, Policy } from '@taruvi/sdk';
|
|
2
|
-
import
|
|
1
|
+
import { Graph, Database, Storage, Functions, Analytics, App, Secrets, User, Auth, Policy } from '@taruvi/sdk';
|
|
2
|
+
import DataLoader from 'dataloader';
|
|
3
3
|
|
|
4
4
|
// src/dataProvider.ts
|
|
5
|
-
|
|
6
|
-
|
|
5
|
+
|
|
6
|
+
// src/utils.ts
|
|
7
|
+
var REFINE_OPERATOR_MAP = {
|
|
8
|
+
// Equality
|
|
9
|
+
eq: "",
|
|
10
|
+
// exact match (no suffix)
|
|
7
11
|
ne: "ne",
|
|
12
|
+
// Comparison
|
|
8
13
|
lt: "lt",
|
|
9
14
|
gt: "gt",
|
|
10
15
|
lte: "lte",
|
|
11
16
|
gte: "gte",
|
|
17
|
+
// String operations (case-sensitive)
|
|
12
18
|
contains: "contains",
|
|
13
|
-
|
|
14
|
-
// case-insensitive
|
|
19
|
+
ncontains: "ncontains",
|
|
15
20
|
startswith: "startswith",
|
|
16
|
-
|
|
21
|
+
nstartswith: "nstartswith",
|
|
17
22
|
endswith: "endswith",
|
|
23
|
+
nendswith: "nendswith",
|
|
24
|
+
// String operations (case-insensitive)
|
|
25
|
+
containss: "icontains",
|
|
26
|
+
ncontainss: "nicontains",
|
|
27
|
+
startswiths: "istartswith",
|
|
28
|
+
nstartswiths: "nistartswith",
|
|
18
29
|
endswiths: "iendswith",
|
|
30
|
+
nendswiths: "niendswith",
|
|
31
|
+
// Array operations
|
|
19
32
|
in: "in",
|
|
20
33
|
nin: "nin",
|
|
21
|
-
|
|
34
|
+
// Null checks
|
|
35
|
+
null: "null",
|
|
36
|
+
nnull: "nnull",
|
|
37
|
+
// Range
|
|
38
|
+
between: "between",
|
|
39
|
+
nbetween: "nbetween"
|
|
22
40
|
};
|
|
23
|
-
function
|
|
24
|
-
if (!filters || filters.length === 0) return
|
|
25
|
-
|
|
41
|
+
function convertRefineFilters(filters) {
|
|
42
|
+
if (!filters || filters.length === 0) return {};
|
|
43
|
+
const params = {};
|
|
26
44
|
for (const filter of filters) {
|
|
27
45
|
if ("operator" in filter && (filter.operator === "and" || filter.operator === "or")) {
|
|
28
46
|
if (filter.value && Array.isArray(filter.value)) {
|
|
29
|
-
|
|
47
|
+
const nested = convertRefineFilters(filter.value);
|
|
48
|
+
Object.assign(params, nested);
|
|
30
49
|
}
|
|
31
50
|
continue;
|
|
32
51
|
}
|
|
@@ -35,22 +54,104 @@ function applyFilters(query, filters) {
|
|
|
35
54
|
if (value === void 0 || value === null && operator !== "null") {
|
|
36
55
|
continue;
|
|
37
56
|
}
|
|
38
|
-
const
|
|
39
|
-
if (
|
|
57
|
+
const suffix = REFINE_OPERATOR_MAP[operator];
|
|
58
|
+
if (suffix === void 0) {
|
|
40
59
|
console.warn(`Unknown Refine operator: ${operator}`);
|
|
41
60
|
continue;
|
|
42
61
|
}
|
|
43
|
-
|
|
62
|
+
const paramKey = suffix ? `${field}__${suffix}` : String(field);
|
|
44
63
|
if (operator === "in" || operator === "nin") {
|
|
45
|
-
|
|
64
|
+
params[paramKey] = Array.isArray(value) ? value.join(",") : String(value);
|
|
65
|
+
} else if (operator === "between" || operator === "nbetween") {
|
|
66
|
+
params[paramKey] = Array.isArray(value) ? value.join(",") : String(value);
|
|
46
67
|
} else if (operator === "null" || operator === "nnull") {
|
|
47
|
-
|
|
48
|
-
} else if (typeof value === "boolean" || typeof value === "number") {
|
|
49
|
-
sdkValue = value;
|
|
68
|
+
params[paramKey] = "true";
|
|
50
69
|
} else {
|
|
51
|
-
|
|
70
|
+
params[paramKey] = String(value);
|
|
52
71
|
}
|
|
53
|
-
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
return params;
|
|
75
|
+
}
|
|
76
|
+
function convertRefineSorters(sorters) {
|
|
77
|
+
if (!sorters || sorters.length === 0) return void 0;
|
|
78
|
+
return sorters.map((sort) => sort.order === "desc" ? `-${sort.field}` : sort.field).join(",");
|
|
79
|
+
}
|
|
80
|
+
function convertRefinePagination(pagination) {
|
|
81
|
+
if (!pagination) return {};
|
|
82
|
+
const { currentPage, pageSize, mode } = pagination;
|
|
83
|
+
if (mode === "off") return {};
|
|
84
|
+
return {
|
|
85
|
+
page: currentPage ?? 1,
|
|
86
|
+
// Default to page 1 if currentPage is undefined
|
|
87
|
+
page_size: pageSize
|
|
88
|
+
};
|
|
89
|
+
}
|
|
90
|
+
function buildRefineQueryParams(options) {
|
|
91
|
+
const { filters, sorters, pagination, meta } = options;
|
|
92
|
+
const params = {
|
|
93
|
+
...convertRefineFilters(filters),
|
|
94
|
+
...convertRefinePagination(pagination)
|
|
95
|
+
};
|
|
96
|
+
const ordering = convertRefineSorters(sorters);
|
|
97
|
+
if (ordering) {
|
|
98
|
+
params.ordering = ordering;
|
|
99
|
+
}
|
|
100
|
+
if (meta?.populate) {
|
|
101
|
+
params.populate = Array.isArray(meta.populate) ? meta.populate.join(",") : meta.populate;
|
|
102
|
+
}
|
|
103
|
+
return params;
|
|
104
|
+
}
|
|
105
|
+
function buildQueryString(params) {
|
|
106
|
+
if (!params || Object.keys(params).length === 0) return "";
|
|
107
|
+
const searchParams = new URLSearchParams();
|
|
108
|
+
for (const [key, value] of Object.entries(params)) {
|
|
109
|
+
if (value !== void 0 && value !== null) {
|
|
110
|
+
searchParams.append(key, String(value));
|
|
111
|
+
}
|
|
112
|
+
}
|
|
113
|
+
const queryString = searchParams.toString();
|
|
114
|
+
return queryString ? `?${queryString}` : "";
|
|
115
|
+
}
|
|
116
|
+
function handleError(error) {
|
|
117
|
+
if (error instanceof Error) {
|
|
118
|
+
throw error;
|
|
119
|
+
}
|
|
120
|
+
if (typeof error === "object" && error !== null && "message" in error) {
|
|
121
|
+
throw new Error(String(error.message));
|
|
122
|
+
}
|
|
123
|
+
throw new Error("Unknown error occurred");
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
// src/dataProvider.ts
|
|
127
|
+
function applyFilters(query, filters) {
|
|
128
|
+
if (!filters || filters.length === 0) return query;
|
|
129
|
+
let result = query;
|
|
130
|
+
for (const filter of filters) {
|
|
131
|
+
if ("operator" in filter && (filter.operator === "and" || filter.operator === "or")) {
|
|
132
|
+
if (filter.value && Array.isArray(filter.value)) {
|
|
133
|
+
result = applyFilters(result, filter.value);
|
|
134
|
+
}
|
|
135
|
+
continue;
|
|
136
|
+
}
|
|
137
|
+
if ("field" in filter && filter.field && filter.operator) {
|
|
138
|
+
const { field, operator, value } = filter;
|
|
139
|
+
if (value === void 0 || value === null && operator !== "null") continue;
|
|
140
|
+
const suffix = REFINE_OPERATOR_MAP[operator];
|
|
141
|
+
if (suffix === void 0) {
|
|
142
|
+
console.warn(`Unknown Refine operator: ${operator}`);
|
|
143
|
+
continue;
|
|
144
|
+
}
|
|
145
|
+
const paramKey = suffix ? `${field}__${suffix}` : String(field);
|
|
146
|
+
let paramValue;
|
|
147
|
+
if (operator === "in" || operator === "nin" || operator === "between" || operator === "nbetween") {
|
|
148
|
+
paramValue = Array.isArray(value) ? value.join(",") : String(value);
|
|
149
|
+
} else if (operator === "null" || operator === "nnull") {
|
|
150
|
+
paramValue = "true";
|
|
151
|
+
} else {
|
|
152
|
+
paramValue = String(value);
|
|
153
|
+
}
|
|
154
|
+
result = result.filter(paramKey, "eq", paramValue);
|
|
54
155
|
}
|
|
55
156
|
}
|
|
56
157
|
return result;
|
|
@@ -59,20 +160,15 @@ function applySorters(query, sorters) {
|
|
|
59
160
|
if (!sorters || sorters.length === 0) return query;
|
|
60
161
|
let result = query;
|
|
61
162
|
for (const sorter of sorters) {
|
|
62
|
-
|
|
63
|
-
result = result.sort(sorter.field, order);
|
|
163
|
+
result = result.sort(sorter.field, sorter.order === "desc" ? "desc" : "asc");
|
|
64
164
|
}
|
|
65
165
|
return result;
|
|
66
166
|
}
|
|
67
167
|
function applyPagination(query, pagination) {
|
|
68
168
|
if (!pagination || pagination.mode === "off") return query;
|
|
69
169
|
let result = query;
|
|
70
|
-
if (pagination.currentPage)
|
|
71
|
-
|
|
72
|
-
}
|
|
73
|
-
if (pagination.pageSize) {
|
|
74
|
-
result = result.pageSize(pagination.pageSize);
|
|
75
|
-
}
|
|
170
|
+
if (pagination.currentPage) result = result.page(pagination.currentPage);
|
|
171
|
+
if (pagination.pageSize) result = result.pageSize(pagination.pageSize);
|
|
76
172
|
return result;
|
|
77
173
|
}
|
|
78
174
|
function applyPopulate(query, meta) {
|
|
@@ -94,7 +190,7 @@ function buildGraphQuery(client, tableName, meta, recordId) {
|
|
|
94
190
|
}
|
|
95
191
|
function dataProvider(client) {
|
|
96
192
|
const config = client.getConfig();
|
|
97
|
-
const baseApiUrl = `${config.
|
|
193
|
+
const baseApiUrl = `${config.apiUrl}/api/apps/${config.appSlug}`;
|
|
98
194
|
const getIdColumn = (meta) => meta?.idColumnName ?? "id";
|
|
99
195
|
const getTableName = (resource, meta) => meta?.tableName ?? resource;
|
|
100
196
|
return {
|
|
@@ -125,9 +221,9 @@ function dataProvider(client) {
|
|
|
125
221
|
const data = Array.isArray(response2) ? response2[0] : response2?.data?.[0] ?? response2;
|
|
126
222
|
return { data };
|
|
127
223
|
}
|
|
128
|
-
let query = new Database(client).from(tableName);
|
|
224
|
+
let query = new Database(client).from(tableName).get(String(id));
|
|
129
225
|
query = applyPopulate(query, taruviMeta);
|
|
130
|
-
const response = await query.
|
|
226
|
+
const response = await query.execute();
|
|
131
227
|
return { data: response.data };
|
|
132
228
|
},
|
|
133
229
|
getMany: async (params) => {
|
|
@@ -155,11 +251,11 @@ function dataProvider(client) {
|
|
|
155
251
|
const taruviMeta = meta;
|
|
156
252
|
const tableName = getTableName(resource, taruviMeta);
|
|
157
253
|
if (isGraphQuery(taruviMeta)) {
|
|
158
|
-
const
|
|
159
|
-
return { data:
|
|
254
|
+
const response2 = await new Graph(client).from(tableName).create(variables).execute();
|
|
255
|
+
return { data: response2.data };
|
|
160
256
|
}
|
|
161
|
-
const
|
|
162
|
-
return { data };
|
|
257
|
+
const response = await new Database(client).from(tableName).create(variables).execute();
|
|
258
|
+
return { data: response.data };
|
|
163
259
|
},
|
|
164
260
|
createMany: async (params) => {
|
|
165
261
|
const { resource, variables, meta } = params;
|
|
@@ -167,7 +263,8 @@ function dataProvider(client) {
|
|
|
167
263
|
const tableName = getTableName(resource, taruviMeta);
|
|
168
264
|
const data = await Promise.all(
|
|
169
265
|
variables.map(async (vars) => {
|
|
170
|
-
|
|
266
|
+
const response = await new Database(client).from(tableName).create(vars).execute();
|
|
267
|
+
return response.data;
|
|
171
268
|
})
|
|
172
269
|
);
|
|
173
270
|
return { data };
|
|
@@ -177,11 +274,11 @@ function dataProvider(client) {
|
|
|
177
274
|
const taruviMeta = meta;
|
|
178
275
|
const tableName = getTableName(resource, taruviMeta);
|
|
179
276
|
if (isGraphQuery(taruviMeta)) {
|
|
180
|
-
const
|
|
181
|
-
return { data:
|
|
277
|
+
const response2 = await new Graph(client).from(tableName).update(String(id), variables).execute();
|
|
278
|
+
return { data: response2.data };
|
|
182
279
|
}
|
|
183
|
-
const
|
|
184
|
-
return { data };
|
|
280
|
+
const response = await new Database(client).from(tableName).get(String(id)).update(variables).execute();
|
|
281
|
+
return { data: response.data };
|
|
185
282
|
},
|
|
186
283
|
updateMany: async (params) => {
|
|
187
284
|
const { resource, ids, variables, meta } = params;
|
|
@@ -189,7 +286,8 @@ function dataProvider(client) {
|
|
|
189
286
|
const tableName = getTableName(resource, taruviMeta);
|
|
190
287
|
const data = await Promise.all(
|
|
191
288
|
ids.map(async (id) => {
|
|
192
|
-
|
|
289
|
+
const response = await new Database(client).from(tableName).get(String(id)).update(variables).execute();
|
|
290
|
+
return response.data;
|
|
193
291
|
})
|
|
194
292
|
);
|
|
195
293
|
return { data };
|
|
@@ -199,46 +297,51 @@ function dataProvider(client) {
|
|
|
199
297
|
const taruviMeta = meta;
|
|
200
298
|
const tableName = getTableName(resource, taruviMeta);
|
|
201
299
|
if (isGraphQuery(taruviMeta)) {
|
|
202
|
-
const
|
|
203
|
-
return { data:
|
|
300
|
+
const response = await new Graph(client).from(tableName).delete([Number(id)]).execute();
|
|
301
|
+
return { data: response.data };
|
|
204
302
|
}
|
|
205
|
-
|
|
206
|
-
return { data };
|
|
303
|
+
await new Database(client).from(tableName).delete(String(id)).execute();
|
|
304
|
+
return { data: { id } };
|
|
207
305
|
},
|
|
208
306
|
deleteMany: async (params) => {
|
|
209
307
|
const { resource, ids, meta } = params;
|
|
210
308
|
const taruviMeta = meta;
|
|
211
309
|
const tableName = getTableName(resource, taruviMeta);
|
|
212
310
|
if (isGraphQuery(taruviMeta)) {
|
|
213
|
-
const
|
|
214
|
-
return { data: [
|
|
311
|
+
const response = await new Graph(client).from(tableName).delete(ids.map(Number)).execute();
|
|
312
|
+
return { data: [response.data] };
|
|
215
313
|
}
|
|
216
|
-
|
|
217
|
-
ids.map((id) =>
|
|
314
|
+
await Promise.all(
|
|
315
|
+
ids.map(async (id) => {
|
|
316
|
+
await new Database(client).from(tableName).delete(String(id)).execute();
|
|
317
|
+
})
|
|
218
318
|
);
|
|
219
|
-
return { data };
|
|
319
|
+
return { data: ids.map((id) => ({ id })) };
|
|
220
320
|
},
|
|
221
321
|
custom: async (params) => {
|
|
222
322
|
const { url, method, payload, query } = params;
|
|
223
|
-
let
|
|
323
|
+
let endpoint = `api/apps/${config.appSlug}/datatables/${url}`;
|
|
224
324
|
let data;
|
|
225
325
|
switch (method.toLowerCase()) {
|
|
226
326
|
case "get": {
|
|
227
327
|
if (query && Object.keys(query).length > 0) {
|
|
228
328
|
const queryString = new URLSearchParams(query).toString();
|
|
229
|
-
|
|
329
|
+
endpoint = `${endpoint}${endpoint.includes("?") ? "&" : "?"}${queryString}`;
|
|
230
330
|
}
|
|
231
|
-
data = await client.httpClient.get(
|
|
331
|
+
data = await client.httpClient.get(endpoint);
|
|
232
332
|
break;
|
|
233
333
|
}
|
|
234
334
|
case "post":
|
|
235
|
-
data = await client.httpClient.post(
|
|
335
|
+
data = await client.httpClient.post(endpoint, payload);
|
|
236
336
|
break;
|
|
237
337
|
case "put":
|
|
238
|
-
data = await client.httpClient.put(
|
|
338
|
+
data = await client.httpClient.put(endpoint, payload);
|
|
339
|
+
break;
|
|
340
|
+
case "patch":
|
|
341
|
+
data = await client.httpClient.patch(endpoint, payload);
|
|
239
342
|
break;
|
|
240
343
|
case "delete":
|
|
241
|
-
data = await client.httpClient.delete(
|
|
344
|
+
data = await client.httpClient.delete(endpoint);
|
|
242
345
|
break;
|
|
243
346
|
default:
|
|
244
347
|
throw new Error(`Unsupported HTTP method: ${method}`);
|
|
@@ -248,131 +351,9 @@ function dataProvider(client) {
|
|
|
248
351
|
getApiUrl: () => baseApiUrl
|
|
249
352
|
};
|
|
250
353
|
}
|
|
251
|
-
|
|
252
|
-
// src/utils.ts
|
|
253
|
-
var REFINE_OPERATOR_MAP = {
|
|
254
|
-
// Equality
|
|
255
|
-
eq: "",
|
|
256
|
-
// exact match (no suffix)
|
|
257
|
-
ne: "ne",
|
|
258
|
-
// Comparison
|
|
259
|
-
lt: "lt",
|
|
260
|
-
gt: "gt",
|
|
261
|
-
lte: "lte",
|
|
262
|
-
gte: "gte",
|
|
263
|
-
// String operations (case-sensitive)
|
|
264
|
-
contains: "contains",
|
|
265
|
-
ncontains: "ncontains",
|
|
266
|
-
startswith: "startswith",
|
|
267
|
-
nstartswith: "nstartswith",
|
|
268
|
-
endswith: "endswith",
|
|
269
|
-
nendswith: "nendswith",
|
|
270
|
-
// String operations (case-insensitive)
|
|
271
|
-
containss: "icontains",
|
|
272
|
-
ncontainss: "nicontains",
|
|
273
|
-
startswiths: "istartswith",
|
|
274
|
-
nstartswiths: "nistartswith",
|
|
275
|
-
endswiths: "iendswith",
|
|
276
|
-
nendswiths: "niendswith",
|
|
277
|
-
// Array operations
|
|
278
|
-
in: "in",
|
|
279
|
-
nin: "nin",
|
|
280
|
-
// Null checks
|
|
281
|
-
null: "null",
|
|
282
|
-
nnull: "nnull",
|
|
283
|
-
// Range
|
|
284
|
-
between: "between",
|
|
285
|
-
nbetween: "nbetween"
|
|
286
|
-
};
|
|
287
|
-
function convertRefineFilters(filters) {
|
|
288
|
-
if (!filters || filters.length === 0) return {};
|
|
289
|
-
const params = {};
|
|
290
|
-
for (const filter of filters) {
|
|
291
|
-
if ("operator" in filter && (filter.operator === "and" || filter.operator === "or")) {
|
|
292
|
-
if (filter.value && Array.isArray(filter.value)) {
|
|
293
|
-
const nested = convertRefineFilters(filter.value);
|
|
294
|
-
Object.assign(params, nested);
|
|
295
|
-
}
|
|
296
|
-
continue;
|
|
297
|
-
}
|
|
298
|
-
if ("field" in filter && filter.field && filter.operator) {
|
|
299
|
-
const { field, operator, value } = filter;
|
|
300
|
-
if (value === void 0 || value === null && operator !== "null") {
|
|
301
|
-
continue;
|
|
302
|
-
}
|
|
303
|
-
const suffix = REFINE_OPERATOR_MAP[operator];
|
|
304
|
-
if (suffix === void 0) {
|
|
305
|
-
console.warn(`Unknown Refine operator: ${operator}`);
|
|
306
|
-
continue;
|
|
307
|
-
}
|
|
308
|
-
const paramKey = suffix ? `${field}__${suffix}` : String(field);
|
|
309
|
-
if (operator === "in" || operator === "nin") {
|
|
310
|
-
params[paramKey] = Array.isArray(value) ? value.join(",") : String(value);
|
|
311
|
-
} else if (operator === "between" || operator === "nbetween") {
|
|
312
|
-
params[paramKey] = Array.isArray(value) ? value.join(",") : String(value);
|
|
313
|
-
} else if (operator === "null" || operator === "nnull") {
|
|
314
|
-
params[paramKey] = "true";
|
|
315
|
-
} else {
|
|
316
|
-
params[paramKey] = String(value);
|
|
317
|
-
}
|
|
318
|
-
}
|
|
319
|
-
}
|
|
320
|
-
return params;
|
|
321
|
-
}
|
|
322
|
-
function convertRefineSorters(sorters) {
|
|
323
|
-
if (!sorters || sorters.length === 0) return void 0;
|
|
324
|
-
return sorters.map((sort) => sort.order === "desc" ? `-${sort.field}` : sort.field).join(",");
|
|
325
|
-
}
|
|
326
|
-
function convertRefinePagination(pagination) {
|
|
327
|
-
if (!pagination) return {};
|
|
328
|
-
const { currentPage, pageSize, mode } = pagination;
|
|
329
|
-
if (mode === "off") return {};
|
|
330
|
-
return {
|
|
331
|
-
page: currentPage ?? 1,
|
|
332
|
-
// Default to page 1 if currentPage is undefined
|
|
333
|
-
page_size: pageSize
|
|
334
|
-
};
|
|
335
|
-
}
|
|
336
|
-
function buildRefineQueryParams(options) {
|
|
337
|
-
const { filters, sorters, pagination, meta } = options;
|
|
338
|
-
const params = {
|
|
339
|
-
...convertRefineFilters(filters),
|
|
340
|
-
...convertRefinePagination(pagination)
|
|
341
|
-
};
|
|
342
|
-
const ordering = convertRefineSorters(sorters);
|
|
343
|
-
if (ordering) {
|
|
344
|
-
params.ordering = ordering;
|
|
345
|
-
}
|
|
346
|
-
if (meta?.populate) {
|
|
347
|
-
params.populate = Array.isArray(meta.populate) ? meta.populate.join(",") : meta.populate;
|
|
348
|
-
}
|
|
349
|
-
return params;
|
|
350
|
-
}
|
|
351
|
-
function buildQueryString(params) {
|
|
352
|
-
if (!params || Object.keys(params).length === 0) return "";
|
|
353
|
-
const searchParams = new URLSearchParams();
|
|
354
|
-
for (const [key, value] of Object.entries(params)) {
|
|
355
|
-
if (value !== void 0 && value !== null) {
|
|
356
|
-
searchParams.append(key, String(value));
|
|
357
|
-
}
|
|
358
|
-
}
|
|
359
|
-
const queryString = searchParams.toString();
|
|
360
|
-
return queryString ? `?${queryString}` : "";
|
|
361
|
-
}
|
|
362
|
-
function handleError(error) {
|
|
363
|
-
if (error instanceof Error) {
|
|
364
|
-
throw error;
|
|
365
|
-
}
|
|
366
|
-
if (typeof error === "object" && error !== null && "message" in error) {
|
|
367
|
-
throw new Error(String(error.message));
|
|
368
|
-
}
|
|
369
|
-
throw new Error("Unknown error occurred");
|
|
370
|
-
}
|
|
371
|
-
|
|
372
|
-
// src/storageDataProvider.ts
|
|
373
354
|
function storageDataProvider(client) {
|
|
374
355
|
const config = client.getConfig();
|
|
375
|
-
const baseApiUrl = `${config.
|
|
356
|
+
const baseApiUrl = `${config.apiUrl}/api/apps/${config.appSlug}`;
|
|
376
357
|
const getBucketName = (resource, meta) => meta?.bucketName ?? resource;
|
|
377
358
|
const buildFilters = (params) => {
|
|
378
359
|
const filters = {
|
|
@@ -389,17 +370,15 @@ function storageDataProvider(client) {
|
|
|
389
370
|
const taruviMeta = meta;
|
|
390
371
|
const bucket = getBucketName(resource, taruviMeta);
|
|
391
372
|
const storageFilters = buildFilters({ filters, sorters, pagination});
|
|
392
|
-
const response = await new Storage(client
|
|
373
|
+
const response = await new Storage(client).from(bucket).filter(storageFilters).execute();
|
|
393
374
|
return { data: response.data, total: response.total };
|
|
394
375
|
},
|
|
395
376
|
getOne: async (params) => {
|
|
396
377
|
const { resource, id: path, meta } = params;
|
|
397
378
|
const taruviMeta = meta;
|
|
398
379
|
const bucket = getBucketName(resource, taruviMeta);
|
|
399
|
-
const
|
|
400
|
-
|
|
401
|
-
const data = url;
|
|
402
|
-
return { data };
|
|
380
|
+
const response = await new Storage(client).from(bucket).download(String(path)).execute();
|
|
381
|
+
return { data: response.data };
|
|
403
382
|
},
|
|
404
383
|
create: async (params) => {
|
|
405
384
|
const { resource, variables, meta } = params;
|
|
@@ -408,25 +387,25 @@ function storageDataProvider(client) {
|
|
|
408
387
|
const { files, paths = [], metadatas = [] } = variables;
|
|
409
388
|
const filePaths = files.map((file, i) => paths[i] || file.name);
|
|
410
389
|
const fileMetadatas = files.map((_, i) => metadatas[i] || {});
|
|
411
|
-
const
|
|
412
|
-
|
|
390
|
+
const response = await new Storage(client).from(bucket).upload({ files, paths: filePaths, metadatas: fileMetadatas }).execute();
|
|
391
|
+
const firstUploaded = response.data?.successful?.[0]?.object;
|
|
392
|
+
return { data: firstUploaded ?? response.data };
|
|
413
393
|
},
|
|
414
394
|
update: async (params) => {
|
|
415
395
|
const { resource, id: path, variables, meta } = params;
|
|
416
396
|
const taruviMeta = meta;
|
|
417
397
|
const bucket = getBucketName(resource, taruviMeta);
|
|
418
|
-
const
|
|
419
|
-
return { data };
|
|
398
|
+
const response = await new Storage(client).from(bucket).update(String(path), variables).execute();
|
|
399
|
+
return { data: response.data };
|
|
420
400
|
},
|
|
421
401
|
deleteOne: async (params) => {
|
|
422
402
|
const { resource, id: path, meta } = params;
|
|
423
403
|
const taruviMeta = meta;
|
|
424
404
|
const bucket = getBucketName(resource, taruviMeta);
|
|
425
|
-
|
|
426
|
-
return { data };
|
|
405
|
+
await new Storage(client).from(bucket).delete([String(path)]).execute();
|
|
406
|
+
return { data: { id: path } };
|
|
427
407
|
},
|
|
428
408
|
getApiUrl: () => baseApiUrl,
|
|
429
|
-
// Not applicable for storage - return empty array
|
|
430
409
|
getMany: async () => ({ data: [] }),
|
|
431
410
|
createMany: async (params) => {
|
|
432
411
|
const { resource, variables, meta } = params;
|
|
@@ -435,15 +414,16 @@ function storageDataProvider(client) {
|
|
|
435
414
|
const { files, paths = [], metadatas = [] } = variables;
|
|
436
415
|
const filePaths = files.map((file, i) => paths[i] || file.name);
|
|
437
416
|
const fileMetadatas = files.map((_, i) => metadatas[i] || {});
|
|
438
|
-
const
|
|
439
|
-
|
|
417
|
+
const response = await new Storage(client).from(bucket).upload({ files, paths: filePaths, metadatas: fileMetadatas }).execute();
|
|
418
|
+
const uploaded = response.data?.successful?.map((s) => s.object) ?? [];
|
|
419
|
+
return { data: uploaded.length > 0 ? uploaded[0] : response.data };
|
|
440
420
|
},
|
|
441
421
|
deleteMany: async (params) => {
|
|
442
422
|
const { resource, ids, meta } = params;
|
|
443
423
|
const taruviMeta = meta;
|
|
444
424
|
const bucket = getBucketName(resource, taruviMeta);
|
|
445
|
-
|
|
446
|
-
return { data:
|
|
425
|
+
await new Storage(client).from(bucket).delete(ids.map(String)).execute();
|
|
426
|
+
return { data: ids.map((id) => ({ id })) };
|
|
447
427
|
},
|
|
448
428
|
custom: async (params) => {
|
|
449
429
|
const { url, method, payload, query } = params;
|
|
@@ -464,6 +444,9 @@ function storageDataProvider(client) {
|
|
|
464
444
|
case "put":
|
|
465
445
|
data = await client.httpClient.put(fullUrl, payload);
|
|
466
446
|
break;
|
|
447
|
+
case "patch":
|
|
448
|
+
data = await client.httpClient.patch(fullUrl, payload);
|
|
449
|
+
break;
|
|
467
450
|
case "delete":
|
|
468
451
|
data = await client.httpClient.delete(fullUrl);
|
|
469
452
|
break;
|
|
@@ -478,12 +461,12 @@ function storageDataProvider(client) {
|
|
|
478
461
|
}
|
|
479
462
|
function appDataProvider(client) {
|
|
480
463
|
const config = client.getConfig();
|
|
481
|
-
const baseApiUrl = `${config.
|
|
464
|
+
const baseApiUrl = `${config.apiUrl}/api/apps/${config.appSlug}`;
|
|
482
465
|
const functions = new Functions(client);
|
|
483
466
|
const analytics = new Analytics(client);
|
|
484
467
|
return {
|
|
485
468
|
getList: async (params) => {
|
|
486
|
-
const { resource } = params;
|
|
469
|
+
const { resource, meta } = params;
|
|
487
470
|
if (resource === "roles") {
|
|
488
471
|
const app = new App(client);
|
|
489
472
|
const response = await app.roles().execute();
|
|
@@ -492,18 +475,40 @@ function appDataProvider(client) {
|
|
|
492
475
|
total: response.total ?? (Array.isArray(response) ? response.length : response.data?.length ?? 0)
|
|
493
476
|
};
|
|
494
477
|
}
|
|
495
|
-
|
|
478
|
+
if (resource === "secrets") {
|
|
479
|
+
const keys = meta?.keys;
|
|
480
|
+
if (!keys || keys.length === 0) {
|
|
481
|
+
throw new Error("secrets resource requires meta.keys array");
|
|
482
|
+
}
|
|
483
|
+
const secrets = new Secrets(client);
|
|
484
|
+
const response = await secrets.list(keys, {
|
|
485
|
+
app: meta?.app,
|
|
486
|
+
includeMetadata: meta?.includeMetadata
|
|
487
|
+
});
|
|
488
|
+
const raw = response.data || response;
|
|
489
|
+
const data = Array.isArray(raw) ? raw : Object.entries(raw).map(([key, value]) => ({ key, value }));
|
|
490
|
+
return { data, total: data.length };
|
|
491
|
+
}
|
|
492
|
+
throw new Error(`Unknown app resource: ${resource}. Supported resources: roles, secrets`);
|
|
496
493
|
},
|
|
497
494
|
getOne: async (params) => {
|
|
498
|
-
const { resource } = params;
|
|
495
|
+
const { resource, id, meta } = params;
|
|
499
496
|
if (resource === "settings") {
|
|
500
497
|
const app = new App(client);
|
|
501
498
|
const response = await app.settings().execute();
|
|
502
499
|
return {
|
|
503
|
-
data: response
|
|
500
|
+
data: response.data
|
|
504
501
|
};
|
|
505
502
|
}
|
|
506
|
-
|
|
503
|
+
if (resource === "secrets") {
|
|
504
|
+
const secrets = new Secrets(client);
|
|
505
|
+
const response = await secrets.get(String(id), {
|
|
506
|
+
app: meta?.app,
|
|
507
|
+
tags: meta?.tags
|
|
508
|
+
}).execute();
|
|
509
|
+
return { data: response.data ?? response };
|
|
510
|
+
}
|
|
511
|
+
throw new Error(`Unknown app resource for getOne: ${resource}. Supported resources: settings, secrets`);
|
|
507
512
|
},
|
|
508
513
|
custom: async (params) => {
|
|
509
514
|
const { url: slug, payload, meta } = params;
|
|
@@ -592,7 +597,7 @@ function buildUserListFilters(filters, sorters, pagination) {
|
|
|
592
597
|
}
|
|
593
598
|
function userDataProvider(client) {
|
|
594
599
|
const config = client.getConfig();
|
|
595
|
-
const baseApiUrl = `${config.
|
|
600
|
+
const baseApiUrl = `${config.apiUrl}/api/apps/${config.appSlug}`;
|
|
596
601
|
return {
|
|
597
602
|
getList: async (params) => {
|
|
598
603
|
const { resource, pagination, filters, sorters, meta } = params;
|
|
@@ -612,20 +617,41 @@ function userDataProvider(client) {
|
|
|
612
617
|
}
|
|
613
618
|
const user = new User(client);
|
|
614
619
|
const response = await user.getUser(username);
|
|
615
|
-
const roles = response.roles || [];
|
|
620
|
+
const roles = response.data?.roles || response.roles || [];
|
|
616
621
|
return {
|
|
617
622
|
data: roles,
|
|
618
623
|
total: roles.length
|
|
619
624
|
};
|
|
620
625
|
}
|
|
621
|
-
|
|
626
|
+
if (resource === "apps") {
|
|
627
|
+
const username = meta?.username;
|
|
628
|
+
if (!username) {
|
|
629
|
+
throw new Error("apps resource requires meta.username");
|
|
630
|
+
}
|
|
631
|
+
const user = new User(client);
|
|
632
|
+
const response = await user.getUserApps(username);
|
|
633
|
+
const apps = response.data || response;
|
|
634
|
+
return {
|
|
635
|
+
data: apps,
|
|
636
|
+
total: Array.isArray(apps) ? apps.length : 0
|
|
637
|
+
};
|
|
638
|
+
}
|
|
639
|
+
throw new Error(`Unknown user resource for getList: ${resource}. Supported: users, roles, apps`);
|
|
622
640
|
},
|
|
623
641
|
getOne: async (params) => {
|
|
624
642
|
const { resource, id } = params;
|
|
625
643
|
if (resource === "users") {
|
|
626
644
|
const user = new User(client);
|
|
645
|
+
if (String(id) === "me") {
|
|
646
|
+
const auth = new Auth(client);
|
|
647
|
+
const response2 = await auth.getCurrentUser();
|
|
648
|
+
const data = response2 ? response2.data ?? response2 : null;
|
|
649
|
+
return { data };
|
|
650
|
+
}
|
|
627
651
|
const response = await user.getUser(String(id));
|
|
628
|
-
return {
|
|
652
|
+
return {
|
|
653
|
+
data: response.data
|
|
654
|
+
};
|
|
629
655
|
}
|
|
630
656
|
throw new Error(`Unknown user resource for getOne: ${resource}. Supported: users`);
|
|
631
657
|
},
|
|
@@ -637,7 +663,7 @@ function userDataProvider(client) {
|
|
|
637
663
|
const userData = variables;
|
|
638
664
|
const response = await user.createUser(userData);
|
|
639
665
|
return {
|
|
640
|
-
data: response
|
|
666
|
+
data: response.data
|
|
641
667
|
};
|
|
642
668
|
}
|
|
643
669
|
throw new Error(`Unknown user resource for create: ${resource}. Supported resources: users`);
|
|
@@ -650,7 +676,7 @@ function userDataProvider(client) {
|
|
|
650
676
|
const updateData = variables;
|
|
651
677
|
const response = await user.updateUser(username, updateData);
|
|
652
678
|
return {
|
|
653
|
-
data: response
|
|
679
|
+
data: response.data
|
|
654
680
|
};
|
|
655
681
|
}
|
|
656
682
|
throw new Error(`Unknown user resource for update: ${resource}. Supported resources: users`);
|
|
@@ -687,7 +713,7 @@ function userDataProvider(client) {
|
|
|
687
713
|
}
|
|
688
714
|
function functionsDataProvider(client) {
|
|
689
715
|
const config = client.getConfig();
|
|
690
|
-
const baseApiUrl = `${config.
|
|
716
|
+
const baseApiUrl = `${config.apiUrl}/api/apps/${config.appSlug}`;
|
|
691
717
|
const functions = new Functions(client);
|
|
692
718
|
return {
|
|
693
719
|
/**
|
|
@@ -761,7 +787,7 @@ function functionsDataProvider(client) {
|
|
|
761
787
|
}
|
|
762
788
|
function analyticsDataProvider(client) {
|
|
763
789
|
const config = client.getConfig();
|
|
764
|
-
const baseApiUrl = `${config.
|
|
790
|
+
const baseApiUrl = `${config.apiUrl}/api/apps/${config.appSlug}`;
|
|
765
791
|
const analytics = new Analytics(client);
|
|
766
792
|
return {
|
|
767
793
|
/**
|
|
@@ -856,7 +882,7 @@ function authProvider(client) {
|
|
|
856
882
|
},
|
|
857
883
|
logout: async (params = {}) => {
|
|
858
884
|
const { callbackUrl } = params;
|
|
859
|
-
auth.logout(callbackUrl);
|
|
885
|
+
await auth.logout(callbackUrl);
|
|
860
886
|
return {
|
|
861
887
|
success: true,
|
|
862
888
|
redirectTo: callbackUrl || "/login"
|
|
@@ -926,14 +952,18 @@ function authProvider(client) {
|
|
|
926
952
|
};
|
|
927
953
|
},
|
|
928
954
|
getIdentity: async () => {
|
|
929
|
-
const
|
|
930
|
-
if (!
|
|
955
|
+
const response = await auth.getCurrentUser();
|
|
956
|
+
if (!response) {
|
|
931
957
|
return null;
|
|
932
958
|
}
|
|
933
|
-
return
|
|
959
|
+
return response.data ?? response;
|
|
934
960
|
},
|
|
935
961
|
getPermissions: async () => {
|
|
936
|
-
const
|
|
962
|
+
const response = await auth.getCurrentUser();
|
|
963
|
+
if (!response) {
|
|
964
|
+
return null;
|
|
965
|
+
}
|
|
966
|
+
const user = response.data ?? response;
|
|
937
967
|
if (!user) {
|
|
938
968
|
return null;
|
|
939
969
|
}
|
|
@@ -951,9 +981,10 @@ function accessControlProvider(client, options) {
|
|
|
951
981
|
const policy = new Policy(client);
|
|
952
982
|
const auth = new Auth(client);
|
|
953
983
|
const { batchDelayMs = 50 } = options ?? {};
|
|
954
|
-
const permissionLoader = new
|
|
984
|
+
const permissionLoader = new DataLoader(
|
|
955
985
|
async (checks) => {
|
|
956
|
-
const
|
|
986
|
+
const response = await auth.getCurrentUser();
|
|
987
|
+
const user = response ? response.data ?? response : null;
|
|
957
988
|
if (!user) {
|
|
958
989
|
return checks.map(() => ({
|
|
959
990
|
can: false,
|
|
@@ -1020,7 +1051,7 @@ function accessControlProvider(client, options) {
|
|
|
1020
1051
|
if (!resource) {
|
|
1021
1052
|
return { can: false, reason: "Resource not specified" };
|
|
1022
1053
|
}
|
|
1023
|
-
const entityType = params?.resource?.meta?.entityType;
|
|
1054
|
+
const entityType = params?.entityType ?? params?.resource?.meta?.entityType;
|
|
1024
1055
|
return permissionLoader.load({
|
|
1025
1056
|
resource,
|
|
1026
1057
|
action,
|