@opengis/fastify-table 2.0.126 → 2.0.127
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/server/plugins/table/funcs/getSelectMeta.d.ts.map +1 -1
- package/dist/server/plugins/table/funcs/getSelectMeta.js +1 -2
- package/dist/server/routes/file/controllers/export.d.ts.map +1 -1
- package/dist/server/routes/file/controllers/export.js +5 -2
- package/dist/server/routes/table/controllers/suggest.d.ts.map +1 -1
- package/dist/server/routes/table/controllers/suggest.js +64 -36
- package/package.json +1 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"getSelectMeta.d.ts","sourceRoot":"","sources":["../../../../../server/plugins/table/funcs/getSelectMeta.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AAWzD,wBAA8B,aAAa,CAAC,EAC1C,IAAI,EACJ,UAAU,EACV,GAAG,EACH,OAAO,EACP,MAAM,EACN,EAAqB,GACtB,EAAE;IACD,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,OAAO,CAAC,EAAE,GAAG,CAAC;IACd,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,EAAE,CAAC,EAAE,UAAU,CAAC;CACjB,
|
|
1
|
+
{"version":3,"file":"getSelectMeta.d.ts","sourceRoot":"","sources":["../../../../../server/plugins/table/funcs/getSelectMeta.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AAWzD,wBAA8B,aAAa,CAAC,EAC1C,IAAI,EACJ,UAAU,EACV,GAAG,EACH,OAAO,EACP,MAAM,EACN,EAAqB,GACtB,EAAE;IACD,IAAI,EAAE,MAAM,CAAC;IACb,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,GAAG,CAAC,EAAE,MAAM,CAAC;IACb,OAAO,CAAC,EAAE,GAAG,CAAC;IACd,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,EAAE,CAAC,EAAE,UAAU,CAAC;CACjB,gBA6GA"}
|
|
@@ -16,9 +16,8 @@ export default async function getSelectMeta({ name, startsWith, key, nocache, pa
|
|
|
16
16
|
return { ...selectMeta[name], searchQuery };
|
|
17
17
|
}
|
|
18
18
|
const cls = await getSelect(name, pg, nocache);
|
|
19
|
-
const db = typeof cls?.db === "string" ? { database: cls.db } : cls?.db;
|
|
20
19
|
const pg1 = cls?.db
|
|
21
|
-
? await getPGAsync({ database: db, port: cls?.port })
|
|
20
|
+
? await getPGAsync({ database: cls.db, port: cls?.port })
|
|
22
21
|
: pg;
|
|
23
22
|
if (!cls)
|
|
24
23
|
return null;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"export.d.ts","sourceRoot":"","sources":["../../../../../server/routes/file/controllers/export.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AAC5C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AAgCzD;;;;;;;;;;;;;;;;;;;;GAoBG;AAEH,wBAA8B,WAAW,CACvC,EACE,EAAqB,EACrB,OAAO,EACP,IAAI,EACJ,OAAO,EAAE,QAAQ,EACjB,GAAG,EACH,KAAU,EACV,IAAkB,EAClB,QAAQ,EACR,UAAU,GACX,EAAE;IACD,EAAE,EAAE,UAAU,CAAC;IACf,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;IAC9B,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;IAC3B,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,GAAG,CAAC,EAAE,GAAG,CAAC;IACV,KAAK,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;IAC5B,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB,EACD,KAAK,EAAE,YAAY,
|
|
1
|
+
{"version":3,"file":"export.d.ts","sourceRoot":"","sources":["../../../../../server/routes/file/controllers/export.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,YAAY,EAAE,MAAM,SAAS,CAAC;AAC5C,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,wBAAwB,CAAC;AAgCzD;;;;;;;;;;;;;;;;;;;;GAoBG;AAEH,wBAA8B,WAAW,CACvC,EACE,EAAqB,EACrB,OAAO,EACP,IAAI,EACJ,OAAO,EAAE,QAAQ,EACjB,GAAG,EACH,KAAU,EACV,IAAkB,EAClB,QAAQ,EACR,UAAU,GACX,EAAE;IACD,EAAE,EAAE,UAAU,CAAC;IACf,OAAO,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;IAC9B,IAAI,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;IAC3B,OAAO,CAAC,EAAE,MAAM,CAAC;IACjB,GAAG,CAAC,EAAE,GAAG,CAAC;IACV,KAAK,CAAC,EAAE,MAAM,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;IAC5B,IAAI,CAAC,EAAE,MAAM,CAAC;IACd,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB,EACD,KAAK,EAAE,YAAY,gBA0YpB"}
|
|
@@ -187,7 +187,8 @@ export default async function exportTable({ pg = pgClients.client, headers, user
|
|
|
187
187
|
let page = 1;
|
|
188
188
|
let seq = 0;
|
|
189
189
|
send(`Всього в реєстрі: ${result.total} (${filtered} з урахуванням фільтрів)`);
|
|
190
|
-
|
|
190
|
+
const writeNewJsonl = !cacheFileJSON || nocache || config.disableCache;
|
|
191
|
+
if (writeNewJsonl) {
|
|
191
192
|
// delete old json line file, prevent append
|
|
192
193
|
if (existsSync(filePathJSON.replace(/.json$/, ".jsonl"))) {
|
|
193
194
|
await rm(filePathJSON.replace(/.json$/, ".jsonl"), {
|
|
@@ -250,7 +251,9 @@ export default async function exportTable({ pg = pgClients.client, headers, user
|
|
|
250
251
|
}
|
|
251
252
|
}
|
|
252
253
|
// convert json line to json array
|
|
253
|
-
|
|
254
|
+
if (writeNewJsonl) {
|
|
255
|
+
await jsonlToJsonFile(filePathJSON.replace(/.json$/, ".jsonl"));
|
|
256
|
+
}
|
|
254
257
|
clearInterval(interval);
|
|
255
258
|
if (res.error) {
|
|
256
259
|
send("finish");
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"suggest.d.ts","sourceRoot":"","sources":["../../../../../server/routes/table/controllers/suggest.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"suggest.d.ts","sourceRoot":"","sources":["../../../../../server/routes/table/controllers/suggest.ts"],"names":[],"mappings":"AAiHA,wBAA8B,OAAO,CAAC,GAAG,EAAE,GAAG,EAAE,KAAK,EAAE,GAAG,gBA6WzD"}
|
|
@@ -1,21 +1,46 @@
|
|
|
1
1
|
import path from "node:path";
|
|
2
2
|
import { existsSync, readFileSync } from "node:fs";
|
|
3
|
-
import { config, getPGAsync, getTemplate, getSelectMeta, getMeta, applyHook, getSelectVal, logger, getSelect, metaFormat, getColumnCLS, pgClients, } from "../../../../utils.js";
|
|
3
|
+
import { config, getPGAsync, getTemplate, getSelectMeta, getMeta, applyHook, getSelectVal, logger, getSelect, metaFormat, getColumnCLS, pgClients, getFilter, } from "../../../../utils.js";
|
|
4
4
|
const defaultLimit = 50;
|
|
5
5
|
async function getTableColumnMeta({ table, template, column, selectName, filtered, startsWith, key, pg = pgClients.client, }) {
|
|
6
6
|
if (!table || !column) {
|
|
7
7
|
return null;
|
|
8
8
|
}
|
|
9
|
-
const
|
|
10
|
-
|
|
11
|
-
|
|
9
|
+
const metaColumns = await getMeta({
|
|
10
|
+
pg,
|
|
11
|
+
table,
|
|
12
|
+
}).then((el) => el?.columns || []);
|
|
13
|
+
const { dataTypeID } = (metaColumns || []).find((col) => col?.name === column) || {};
|
|
14
|
+
const { columns, table: tableName, sql, } = template ? await getTemplate("table", template) : { table, columns: [] };
|
|
15
|
+
const filters = template
|
|
16
|
+
? await getFilter({ pg, table: template }).then((el) => el.list)
|
|
17
|
+
: null;
|
|
12
18
|
const { data: clsName } = selectName
|
|
13
19
|
? { data: selectName }
|
|
14
|
-
: columns.find((el) => el.name === column) ||
|
|
15
|
-
|
|
20
|
+
: (columns || []).find((el) => el.name === column) ||
|
|
21
|
+
(filters || []).find((el) => el.name === column) ||
|
|
22
|
+
{};
|
|
23
|
+
const { arr, sql: select } = (await getSelect(clsName || column, pg)) || {};
|
|
24
|
+
const sqlTable = (sql || [])
|
|
25
|
+
.filter((el) => !el.disabled && el.sql && el.sql.includes(column) && false)
|
|
26
|
+
.map((el, i) => ` left join lateral (${el.sql}) ${el.name || `t${i}`} on 1=1 `)
|
|
27
|
+
?.join("") || "";
|
|
28
|
+
if (pg.pgType?.[dataTypeID]?.includes("[]")) {
|
|
29
|
+
const original = filtered
|
|
30
|
+
? `with c(id,text) as (select id, id as text from (select unnest(${column}) as id from ${tableName} t ${sqlTable})q group by id) select id, text from c`
|
|
31
|
+
: `with c(id,text) as (select id, id as text, count(*) from (select unnest(${column}) as id from ${tableName} t ${sqlTable})q group by id limit ${defaultLimit}) select * from c`;
|
|
32
|
+
return {
|
|
33
|
+
arr,
|
|
34
|
+
original,
|
|
35
|
+
searchQuery: startsWith && key
|
|
36
|
+
? `(left(lower("text"::text),${key.length}) = $1 )`
|
|
37
|
+
: '(lower("text"::text) ~ $1 )',
|
|
38
|
+
pk: "id",
|
|
39
|
+
};
|
|
40
|
+
}
|
|
16
41
|
const original = filtered
|
|
17
|
-
? `with c(id,text) as (select ${column} as id, ${column} as text from ${tableName} group by ${column}) select id, text from c`
|
|
18
|
-
: `with c(id,text) as (select ${column} as id, ${column} as text, count(*) from ${tableName} group by ${column} limit ${defaultLimit}) select * from c`;
|
|
42
|
+
? `with c(id,text) as (select ${column} as id, ${column} as text from ${tableName} t ${sqlTable} group by ${column}) select id, text from c`
|
|
43
|
+
: `with c(id,text) as (select ${column} as id, ${column} as text, count(*) from ${tableName} t ${sqlTable} group by ${column} limit ${defaultLimit}) select * from c`;
|
|
19
44
|
return {
|
|
20
45
|
arr,
|
|
21
46
|
original,
|
|
@@ -43,15 +68,8 @@ export default async function suggest(req, reply) {
|
|
|
43
68
|
const [table1, column1] = params.data?.includes(":")
|
|
44
69
|
? params.data.split(":")
|
|
45
70
|
: [query.token, query.column];
|
|
46
|
-
const selectName = query.sel || params.data;
|
|
47
71
|
const table = table1 || query.token;
|
|
48
72
|
const column = column1 || query.column;
|
|
49
|
-
if (!selectName) {
|
|
50
|
-
return reply.status(400).send({
|
|
51
|
-
error: "name is required",
|
|
52
|
-
code: 400,
|
|
53
|
-
});
|
|
54
|
-
}
|
|
55
73
|
const { body: hookBody } = table
|
|
56
74
|
? (await applyHook("preSuggest", {
|
|
57
75
|
pg: pg1,
|
|
@@ -66,6 +84,12 @@ export default async function suggest(req, reply) {
|
|
|
66
84
|
code: 400,
|
|
67
85
|
});
|
|
68
86
|
}
|
|
87
|
+
const selectName = query.sel ||
|
|
88
|
+
(tableName && column && body
|
|
89
|
+
? body.columns?.find((el) => el.name === column)?.data ||
|
|
90
|
+
body.meta?.cls?.[column]
|
|
91
|
+
: null) ||
|
|
92
|
+
params.data;
|
|
69
93
|
const meta = tableName && column
|
|
70
94
|
? await getTableColumnMeta({
|
|
71
95
|
table: tableName,
|
|
@@ -103,13 +127,18 @@ export default async function suggest(req, reply) {
|
|
|
103
127
|
code: 400,
|
|
104
128
|
});
|
|
105
129
|
}
|
|
106
|
-
const columns = hookBody?.columns || body?.columns
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
130
|
+
const columns = hookBody?.columns || body?.columns;
|
|
131
|
+
const metaColumns = await getMeta({
|
|
132
|
+
pg,
|
|
133
|
+
table: tableName,
|
|
134
|
+
}).then((el) => el?.columns || []);
|
|
135
|
+
const { name: columnName } = (columns || []).find((col) => col?.name === column) ||
|
|
136
|
+
(metaColumns || []).find((col) => col?.name === column) ||
|
|
137
|
+
{};
|
|
138
|
+
const { dataTypeID } = (metaColumns || []).find((col) => col?.name === column) || {};
|
|
139
|
+
// const filters =
|
|
140
|
+
// hookBody?.filters ||
|
|
141
|
+
// (body ? await getFilter({ pg, table }).then((el) => el.list) : null);
|
|
113
142
|
if (table && (!column || !columnName)) {
|
|
114
143
|
return reply.status(400).send({
|
|
115
144
|
error: "param name is invalid: 2",
|
|
@@ -126,7 +155,8 @@ export default async function suggest(req, reply) {
|
|
|
126
155
|
return meta;
|
|
127
156
|
}
|
|
128
157
|
const { arr, searchQuery } = meta;
|
|
129
|
-
|
|
158
|
+
// table:column + cls
|
|
159
|
+
if (arr && tableName && column) {
|
|
130
160
|
const sqlCls = query.count
|
|
131
161
|
? `select value, count(*) from (select ${pg.pgType?.[dataTypeID]?.includes("[]")
|
|
132
162
|
? `unnest(${columnName})`
|
|
@@ -181,6 +211,7 @@ export default async function suggest(req, reply) {
|
|
|
181
211
|
};
|
|
182
212
|
}
|
|
183
213
|
}
|
|
214
|
+
// cls
|
|
184
215
|
if (arr) {
|
|
185
216
|
const lower = query.key?.toLowerCase();
|
|
186
217
|
const data1 = query.key || query.val
|
|
@@ -207,32 +238,30 @@ export default async function suggest(req, reply) {
|
|
|
207
238
|
data,
|
|
208
239
|
};
|
|
209
240
|
}
|
|
210
|
-
// search
|
|
241
|
+
// select, with search by text support
|
|
211
242
|
const search = query.key ? searchQuery : null;
|
|
212
|
-
//
|
|
213
|
-
// const pk = meta.originalCols.split(',')[0];
|
|
214
|
-
// return meta;
|
|
243
|
+
// filter by value
|
|
215
244
|
const val = query.val
|
|
216
|
-
?
|
|
245
|
+
? `${meta.pk}=any('{${query.val.replace(/'/g, "''")}}')`
|
|
217
246
|
: "";
|
|
218
|
-
const
|
|
219
|
-
.filter(Boolean)
|
|
220
|
-
.join(" and ") || "true";
|
|
221
|
-
const filter = table && pg.pk?.[table] && columnName && dataTypeID
|
|
247
|
+
const filter = tableName && pg.pk?.[tableName] && columnName && dataTypeID
|
|
222
248
|
? `id in (select ${pg.pgType[dataTypeID]?.includes("[]")
|
|
223
249
|
? `unnest(${columnName})`
|
|
224
|
-
: columnName} from ${
|
|
250
|
+
: columnName} from ${tableName.replace(/'/g, "''")})`
|
|
225
251
|
: "true";
|
|
252
|
+
const where = [search, val, filter, meta.pk ? `${meta.pk} is not null` : null]
|
|
253
|
+
.filter(Boolean)
|
|
254
|
+
.join(" and ") || "true";
|
|
226
255
|
const sqlSuggest = `with c(id,text) as ( ${meta.original.replace(/{{parent}}/gi, parent)} where ${where} ${meta.original.includes("order by") ? "" : "order by 2"}) select * from c where ${filter} limit ${Math.min(query.limit || meta.limit || limit, limit)}`.replace(/{{uid}}/g, user?.uid || "0");
|
|
227
256
|
if (query.sql && debugMode) {
|
|
228
257
|
return sqlSuggest;
|
|
229
258
|
}
|
|
230
|
-
// query
|
|
231
259
|
const { rows: dataNew } = await pg.query(sqlSuggest, query.key ? [query.key.toLowerCase()] : []);
|
|
232
260
|
// in case id / text = Boolean
|
|
233
261
|
const data = dataNew.filter((el) => Object.hasOwn(el, "id") && Object.hasOwn(el, "text"));
|
|
262
|
+
// table:column + select
|
|
234
263
|
if (tableName && column) {
|
|
235
|
-
const { name =
|
|
264
|
+
const { name = selectName || column, type = "select" } = getColumnCLS(tableName, column) || {};
|
|
236
265
|
await metaFormat({
|
|
237
266
|
rows: data,
|
|
238
267
|
table: tableName,
|
|
@@ -270,7 +299,6 @@ export default async function suggest(req, reply) {
|
|
|
270
299
|
data,
|
|
271
300
|
dataNew,
|
|
272
301
|
sqlSuggest,
|
|
273
|
-
// ids,
|
|
274
302
|
});
|
|
275
303
|
}
|
|
276
304
|
const message = {
|