datapeek 0.1.7 → 0.1.8
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/cli/dev.js +61 -6
- package/dist/cli/index.js +61 -6
- package/dist/client/assets/index-C32MC3if.js +239 -0
- package/dist/client/assets/index-piPKidzx.css +1 -0
- package/dist/client/index.html +2 -2
- package/dist/server/dev.js +61 -6
- package/dist/server/index.js +61 -6
- package/package.json +1 -1
- package/dist/client/assets/index-Bz4cddDl.css +0 -1
- package/dist/client/assets/index-DDmcmxkb.js +0 -234
package/dist/cli/dev.js
CHANGED
|
@@ -191,12 +191,63 @@ tableRoutes.get("/:schema/:table/data", async (req, res) => {
|
|
|
191
191
|
const sortColumn = req.query.sortColumn;
|
|
192
192
|
const sortDirection = req.query.sortDirection || "asc";
|
|
193
193
|
const offset = (page - 1) * pageSize;
|
|
194
|
+
const filters = {};
|
|
195
|
+
Object.keys(req.query).forEach((key) => {
|
|
196
|
+
const match = key.match(/^filter\[(.+)\]$/);
|
|
197
|
+
if (match && req.query[key] && String(req.query[key]).trim()) {
|
|
198
|
+
filters[match[1]] = String(req.query[key]).trim();
|
|
199
|
+
}
|
|
200
|
+
});
|
|
201
|
+
console.log("Received filters from query:", filters);
|
|
202
|
+
console.log("All query params:", req.query);
|
|
194
203
|
const pool = getConnection();
|
|
195
204
|
if (!pool || !pool.connected) {
|
|
196
205
|
return res.status(400).json({ error: "Not connected to database" });
|
|
197
206
|
}
|
|
198
|
-
const
|
|
199
|
-
|
|
207
|
+
const filterColumns = [];
|
|
208
|
+
if (Object.keys(filters).length > 0) {
|
|
209
|
+
try {
|
|
210
|
+
const columnNames = Object.keys(filters);
|
|
211
|
+
const placeholders = columnNames.map((_, i) => `@col${i}`).join(", ");
|
|
212
|
+
const validateQuery = `
|
|
213
|
+
SELECT COLUMN_NAME
|
|
214
|
+
FROM INFORMATION_SCHEMA.COLUMNS
|
|
215
|
+
WHERE TABLE_SCHEMA = @schema AND TABLE_NAME = @table AND COLUMN_NAME IN (${placeholders})
|
|
216
|
+
`;
|
|
217
|
+
const validateParams = [
|
|
218
|
+
{ name: "schema", value: schema, type: sql.NVarChar },
|
|
219
|
+
{ name: "table", value: table, type: sql.NVarChar },
|
|
220
|
+
...columnNames.map((col, i) => ({ name: `col${i}`, value: col, type: sql.NVarChar }))
|
|
221
|
+
];
|
|
222
|
+
const validateResult = await executeQuery(validateQuery, validateParams);
|
|
223
|
+
filterColumns.push(...validateResult.map((r) => r.COLUMN_NAME));
|
|
224
|
+
console.log("Validated filter columns:", filterColumns, "from filters:", filters);
|
|
225
|
+
} catch (e) {
|
|
226
|
+
console.error("Error validating filter columns:", e);
|
|
227
|
+
console.error("Filters that failed validation:", filters);
|
|
228
|
+
}
|
|
229
|
+
}
|
|
230
|
+
let whereClause = "";
|
|
231
|
+
const filterParams = [];
|
|
232
|
+
if (filterColumns.length > 0) {
|
|
233
|
+
const validFilters = filterColumns.filter((col) => {
|
|
234
|
+
const filterValue = filters[col];
|
|
235
|
+
return filterValue && filterValue.trim() !== "";
|
|
236
|
+
});
|
|
237
|
+
if (validFilters.length > 0) {
|
|
238
|
+
const whereConditions = validFilters.map((col, index) => {
|
|
239
|
+
const filterValue = filters[col];
|
|
240
|
+
filterParams.push({ name: `filter${index}`, value: `%${filterValue.trim()}%`, type: sql.NVarChar });
|
|
241
|
+
return `[${col}] LIKE @filter${index}`;
|
|
242
|
+
});
|
|
243
|
+
whereClause = `WHERE ${whereConditions.join(" AND ")}`;
|
|
244
|
+
console.log("Applying WHERE clause:", whereClause);
|
|
245
|
+
console.log("Filter params:", filterParams);
|
|
246
|
+
console.log("Valid filters:", validFilters);
|
|
247
|
+
}
|
|
248
|
+
}
|
|
249
|
+
const countQuery = `SELECT COUNT(*) as total FROM [${schema}].[${table}]${whereClause ? " " + whereClause : ""}`;
|
|
250
|
+
const countResult = await executeQuery(countQuery, filterParams.length > 0 ? filterParams : []);
|
|
200
251
|
const total = countResult[0]?.total || 0;
|
|
201
252
|
let orderByColumn = sortColumn || "";
|
|
202
253
|
let orderByDirection = sortDirection?.toUpperCase() === "DESC" ? "DESC" : "ASC";
|
|
@@ -240,24 +291,26 @@ tableRoutes.get("/:schema/:table/data", async (req, res) => {
|
|
|
240
291
|
let data;
|
|
241
292
|
let generatedQuery = "";
|
|
242
293
|
if (orderByColumn) {
|
|
243
|
-
generatedQuery = `SELECT * FROM [${schema}].[${table}]
|
|
294
|
+
generatedQuery = `SELECT * FROM [${schema}].[${table}]${whereClause ? "\n" + whereClause : ""}
|
|
244
295
|
ORDER BY [${orderByColumn}] ${orderByDirection}
|
|
245
296
|
OFFSET ${offset} ROWS
|
|
246
297
|
FETCH NEXT ${pageSize} ROWS ONLY`;
|
|
247
298
|
const dataQuery = `
|
|
248
299
|
SELECT * FROM [${schema}].[${table}]
|
|
300
|
+
${whereClause}
|
|
249
301
|
ORDER BY [${orderByColumn}] ${orderByDirection}
|
|
250
302
|
OFFSET @offset ROWS
|
|
251
303
|
FETCH NEXT @pageSize ROWS ONLY
|
|
252
304
|
`;
|
|
253
305
|
data = await executeQuery(dataQuery, [
|
|
254
306
|
{ name: "offset", value: offset, type: sql.Int },
|
|
255
|
-
{ name: "pageSize", value: pageSize, type: sql.Int }
|
|
307
|
+
{ name: "pageSize", value: pageSize, type: sql.Int },
|
|
308
|
+
...filterParams
|
|
256
309
|
]);
|
|
257
310
|
} else {
|
|
258
311
|
generatedQuery = `SELECT * FROM (
|
|
259
312
|
SELECT *, ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) as rn
|
|
260
|
-
FROM [${schema}].[${table}]
|
|
313
|
+
FROM [${schema}].[${table}]${whereClause ? "\n " + whereClause : ""}
|
|
261
314
|
) t
|
|
262
315
|
WHERE rn > ${offset} AND rn <= ${offset + pageSize}
|
|
263
316
|
ORDER BY rn`;
|
|
@@ -265,13 +318,15 @@ ORDER BY rn`;
|
|
|
265
318
|
SELECT * FROM (
|
|
266
319
|
SELECT *, ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) as rn
|
|
267
320
|
FROM [${schema}].[${table}]
|
|
321
|
+
${whereClause}
|
|
268
322
|
) t
|
|
269
323
|
WHERE rn > @offset AND rn <= @offset + @pageSize
|
|
270
324
|
ORDER BY rn
|
|
271
325
|
`;
|
|
272
326
|
data = await executeQuery(dataQuery, [
|
|
273
327
|
{ name: "offset", value: offset, type: sql.Int },
|
|
274
|
-
{ name: "pageSize", value: pageSize, type: sql.Int }
|
|
328
|
+
{ name: "pageSize", value: pageSize, type: sql.Int },
|
|
329
|
+
...filterParams
|
|
275
330
|
]);
|
|
276
331
|
data = data.map((row) => {
|
|
277
332
|
const { rn, ...rest } = row;
|
package/dist/cli/index.js
CHANGED
|
@@ -194,12 +194,63 @@ tableRoutes.get("/:schema/:table/data", async (req, res) => {
|
|
|
194
194
|
const sortColumn = req.query.sortColumn;
|
|
195
195
|
const sortDirection = req.query.sortDirection || "asc";
|
|
196
196
|
const offset = (page - 1) * pageSize;
|
|
197
|
+
const filters = {};
|
|
198
|
+
Object.keys(req.query).forEach((key) => {
|
|
199
|
+
const match = key.match(/^filter\[(.+)\]$/);
|
|
200
|
+
if (match && req.query[key] && String(req.query[key]).trim()) {
|
|
201
|
+
filters[match[1]] = String(req.query[key]).trim();
|
|
202
|
+
}
|
|
203
|
+
});
|
|
204
|
+
console.log("Received filters from query:", filters);
|
|
205
|
+
console.log("All query params:", req.query);
|
|
197
206
|
const pool = getConnection();
|
|
198
207
|
if (!pool || !pool.connected) {
|
|
199
208
|
return res.status(400).json({ error: "Not connected to database" });
|
|
200
209
|
}
|
|
201
|
-
const
|
|
202
|
-
|
|
210
|
+
const filterColumns = [];
|
|
211
|
+
if (Object.keys(filters).length > 0) {
|
|
212
|
+
try {
|
|
213
|
+
const columnNames = Object.keys(filters);
|
|
214
|
+
const placeholders = columnNames.map((_, i) => `@col${i}`).join(", ");
|
|
215
|
+
const validateQuery = `
|
|
216
|
+
SELECT COLUMN_NAME
|
|
217
|
+
FROM INFORMATION_SCHEMA.COLUMNS
|
|
218
|
+
WHERE TABLE_SCHEMA = @schema AND TABLE_NAME = @table AND COLUMN_NAME IN (${placeholders})
|
|
219
|
+
`;
|
|
220
|
+
const validateParams = [
|
|
221
|
+
{ name: "schema", value: schema, type: sql.NVarChar },
|
|
222
|
+
{ name: "table", value: table, type: sql.NVarChar },
|
|
223
|
+
...columnNames.map((col, i) => ({ name: `col${i}`, value: col, type: sql.NVarChar }))
|
|
224
|
+
];
|
|
225
|
+
const validateResult = await executeQuery(validateQuery, validateParams);
|
|
226
|
+
filterColumns.push(...validateResult.map((r) => r.COLUMN_NAME));
|
|
227
|
+
console.log("Validated filter columns:", filterColumns, "from filters:", filters);
|
|
228
|
+
} catch (e) {
|
|
229
|
+
console.error("Error validating filter columns:", e);
|
|
230
|
+
console.error("Filters that failed validation:", filters);
|
|
231
|
+
}
|
|
232
|
+
}
|
|
233
|
+
let whereClause = "";
|
|
234
|
+
const filterParams = [];
|
|
235
|
+
if (filterColumns.length > 0) {
|
|
236
|
+
const validFilters = filterColumns.filter((col) => {
|
|
237
|
+
const filterValue = filters[col];
|
|
238
|
+
return filterValue && filterValue.trim() !== "";
|
|
239
|
+
});
|
|
240
|
+
if (validFilters.length > 0) {
|
|
241
|
+
const whereConditions = validFilters.map((col, index) => {
|
|
242
|
+
const filterValue = filters[col];
|
|
243
|
+
filterParams.push({ name: `filter${index}`, value: `%${filterValue.trim()}%`, type: sql.NVarChar });
|
|
244
|
+
return `[${col}] LIKE @filter${index}`;
|
|
245
|
+
});
|
|
246
|
+
whereClause = `WHERE ${whereConditions.join(" AND ")}`;
|
|
247
|
+
console.log("Applying WHERE clause:", whereClause);
|
|
248
|
+
console.log("Filter params:", filterParams);
|
|
249
|
+
console.log("Valid filters:", validFilters);
|
|
250
|
+
}
|
|
251
|
+
}
|
|
252
|
+
const countQuery = `SELECT COUNT(*) as total FROM [${schema}].[${table}]${whereClause ? " " + whereClause : ""}`;
|
|
253
|
+
const countResult = await executeQuery(countQuery, filterParams.length > 0 ? filterParams : []);
|
|
203
254
|
const total = countResult[0]?.total || 0;
|
|
204
255
|
let orderByColumn = sortColumn || "";
|
|
205
256
|
let orderByDirection = sortDirection?.toUpperCase() === "DESC" ? "DESC" : "ASC";
|
|
@@ -243,24 +294,26 @@ tableRoutes.get("/:schema/:table/data", async (req, res) => {
|
|
|
243
294
|
let data;
|
|
244
295
|
let generatedQuery = "";
|
|
245
296
|
if (orderByColumn) {
|
|
246
|
-
generatedQuery = `SELECT * FROM [${schema}].[${table}]
|
|
297
|
+
generatedQuery = `SELECT * FROM [${schema}].[${table}]${whereClause ? "\n" + whereClause : ""}
|
|
247
298
|
ORDER BY [${orderByColumn}] ${orderByDirection}
|
|
248
299
|
OFFSET ${offset} ROWS
|
|
249
300
|
FETCH NEXT ${pageSize} ROWS ONLY`;
|
|
250
301
|
const dataQuery = `
|
|
251
302
|
SELECT * FROM [${schema}].[${table}]
|
|
303
|
+
${whereClause}
|
|
252
304
|
ORDER BY [${orderByColumn}] ${orderByDirection}
|
|
253
305
|
OFFSET @offset ROWS
|
|
254
306
|
FETCH NEXT @pageSize ROWS ONLY
|
|
255
307
|
`;
|
|
256
308
|
data = await executeQuery(dataQuery, [
|
|
257
309
|
{ name: "offset", value: offset, type: sql.Int },
|
|
258
|
-
{ name: "pageSize", value: pageSize, type: sql.Int }
|
|
310
|
+
{ name: "pageSize", value: pageSize, type: sql.Int },
|
|
311
|
+
...filterParams
|
|
259
312
|
]);
|
|
260
313
|
} else {
|
|
261
314
|
generatedQuery = `SELECT * FROM (
|
|
262
315
|
SELECT *, ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) as rn
|
|
263
|
-
FROM [${schema}].[${table}]
|
|
316
|
+
FROM [${schema}].[${table}]${whereClause ? "\n " + whereClause : ""}
|
|
264
317
|
) t
|
|
265
318
|
WHERE rn > ${offset} AND rn <= ${offset + pageSize}
|
|
266
319
|
ORDER BY rn`;
|
|
@@ -268,13 +321,15 @@ ORDER BY rn`;
|
|
|
268
321
|
SELECT * FROM (
|
|
269
322
|
SELECT *, ROW_NUMBER() OVER (ORDER BY (SELECT NULL)) as rn
|
|
270
323
|
FROM [${schema}].[${table}]
|
|
324
|
+
${whereClause}
|
|
271
325
|
) t
|
|
272
326
|
WHERE rn > @offset AND rn <= @offset + @pageSize
|
|
273
327
|
ORDER BY rn
|
|
274
328
|
`;
|
|
275
329
|
data = await executeQuery(dataQuery, [
|
|
276
330
|
{ name: "offset", value: offset, type: sql.Int },
|
|
277
|
-
{ name: "pageSize", value: pageSize, type: sql.Int }
|
|
331
|
+
{ name: "pageSize", value: pageSize, type: sql.Int },
|
|
332
|
+
...filterParams
|
|
278
333
|
]);
|
|
279
334
|
data = data.map((row) => {
|
|
280
335
|
const { rn, ...rest } = row;
|