@quillsql/node 0.5.8 → 0.5.9
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/db/CachedConnection.d.ts +3 -1
- package/dist/db/CachedConnection.js +17 -1
- package/dist/db/Mysql.js +8 -2
- package/dist/index.js +3 -2
- package/package.json +1 -1
- package/src/db/CachedConnection.ts +23 -6
- package/src/db/Mysql.ts +18 -12
- package/src/index.ts +16 -15
|
@@ -2,15 +2,17 @@ import { Mapable, CacheCredentials } from "../models/Cache";
|
|
|
2
2
|
import { DatabaseConnection } from "./DatabaseHelper";
|
|
3
3
|
export declare class CachedConnection {
|
|
4
4
|
databaseType: "postgresql" | "snowflake" | "bigquery" | "mysql";
|
|
5
|
-
pool: DatabaseConnection;
|
|
5
|
+
pool: DatabaseConnection | null;
|
|
6
6
|
orgId: any;
|
|
7
7
|
ttl: number;
|
|
8
8
|
cache: Mapable | null;
|
|
9
|
+
private config;
|
|
9
10
|
constructor(databaseType: "postgresql" | "snowflake" | "bigquery" | "mysql", config: any, cacheConfig?: Partial<CacheCredentials>);
|
|
10
11
|
query(text: string, values?: any[]): Promise<any>;
|
|
11
12
|
/**
|
|
12
13
|
* Configures and returns a cache instance or null if none could be created.
|
|
13
14
|
*/
|
|
14
15
|
private getCache;
|
|
16
|
+
getPool(): DatabaseConnection;
|
|
15
17
|
close(): Promise<void>;
|
|
16
18
|
}
|
|
@@ -29,12 +29,14 @@ class CachedConnection {
|
|
|
29
29
|
var _a;
|
|
30
30
|
this.databaseType = databaseType;
|
|
31
31
|
this.pool = (0, DatabaseHelper_1.connectToDatabase)(databaseType, config);
|
|
32
|
+
this.config = config;
|
|
32
33
|
this.ttl = (_a = cacheConfig === null || cacheConfig === void 0 ? void 0 : cacheConfig.ttl) !== null && _a !== void 0 ? _a : DEFAULT_CACHE_TTL;
|
|
33
34
|
this.cache = this.getCache(cacheConfig);
|
|
34
35
|
}
|
|
35
36
|
query(text, values) {
|
|
36
37
|
return __awaiter(this, void 0, void 0, function* () {
|
|
37
38
|
try {
|
|
39
|
+
this.pool = this.getPool();
|
|
38
40
|
if (!this.cache) {
|
|
39
41
|
return yield (0, DatabaseHelper_1.runQueryByDatabase)(this.databaseType, this.pool, text);
|
|
40
42
|
}
|
|
@@ -58,6 +60,11 @@ class CachedConnection {
|
|
|
58
60
|
throw new Error(err.message);
|
|
59
61
|
}
|
|
60
62
|
}
|
|
63
|
+
finally {
|
|
64
|
+
if (this.databaseType.toLowerCase() === "mysql") {
|
|
65
|
+
this.close();
|
|
66
|
+
}
|
|
67
|
+
}
|
|
61
68
|
});
|
|
62
69
|
}
|
|
63
70
|
/**
|
|
@@ -72,9 +79,18 @@ class CachedConnection {
|
|
|
72
79
|
}
|
|
73
80
|
return null;
|
|
74
81
|
}
|
|
82
|
+
getPool() {
|
|
83
|
+
if (!this.pool) {
|
|
84
|
+
this.pool = (0, DatabaseHelper_1.connectToDatabase)(this.databaseType, this.config);
|
|
85
|
+
}
|
|
86
|
+
return this.pool;
|
|
87
|
+
}
|
|
75
88
|
close() {
|
|
76
89
|
return __awaiter(this, void 0, void 0, function* () {
|
|
77
|
-
|
|
90
|
+
if (this.pool) {
|
|
91
|
+
(0, DatabaseHelper_1.disconnectFromDatabase)(this.databaseType, this.pool);
|
|
92
|
+
this.pool = null;
|
|
93
|
+
}
|
|
78
94
|
});
|
|
79
95
|
}
|
|
80
96
|
}
|
package/dist/db/Mysql.js
CHANGED
|
@@ -29,7 +29,7 @@ function formatMysqlConfig(connectionString) {
|
|
|
29
29
|
}
|
|
30
30
|
exports.formatMysqlConfig = formatMysqlConfig;
|
|
31
31
|
function connectToMysql(config) {
|
|
32
|
-
const pool = mysql2_1.default.createPool(Object.assign(Object.assign({}, config), { waitForConnections: true, connectionLimit:
|
|
32
|
+
const pool = mysql2_1.default.createPool(Object.assign(Object.assign({}, config), { waitForConnections: true, connectionLimit: 128, queueLimit: 0 }));
|
|
33
33
|
return pool;
|
|
34
34
|
}
|
|
35
35
|
exports.connectToMysql = connectToMysql;
|
|
@@ -167,6 +167,10 @@ function mysqlTextDataTypeToPostgresOID(type) {
|
|
|
167
167
|
return 1043;
|
|
168
168
|
case "timestamp": // date
|
|
169
169
|
return 1082;
|
|
170
|
+
case "date": // date
|
|
171
|
+
return 1082;
|
|
172
|
+
case "datetime": // date
|
|
173
|
+
return 1082;
|
|
170
174
|
default: // varchar
|
|
171
175
|
return 1043;
|
|
172
176
|
}
|
|
@@ -185,7 +189,9 @@ function mysqlDataTypeIdToPostgresType(type) {
|
|
|
185
189
|
return 1043;
|
|
186
190
|
case 7: // date
|
|
187
191
|
return 1082;
|
|
188
|
-
case
|
|
192
|
+
case 10: // date
|
|
193
|
+
return 1082;
|
|
194
|
+
case 12: // date
|
|
189
195
|
return 1082;
|
|
190
196
|
default: // varchar
|
|
191
197
|
return 1043;
|
package/dist/index.js
CHANGED
|
@@ -167,8 +167,9 @@ class Quill {
|
|
|
167
167
|
}
|
|
168
168
|
}
|
|
169
169
|
else if (runQueryConfig === null || runQueryConfig === void 0 ? void 0 : runQueryConfig.getTables) {
|
|
170
|
-
const queryResult = yield (0, DatabaseHelper_1.getTablesBySchemaByDatabase)(this.targetConnection.databaseType, this.targetConnection.
|
|
171
|
-
const schemaInfo = yield (0, DatabaseHelper_1.getColumnInfoBySchemaByDatabase)(this.targetConnection.databaseType, this.targetConnection.
|
|
170
|
+
const queryResult = yield (0, DatabaseHelper_1.getTablesBySchemaByDatabase)(this.targetConnection.databaseType, this.targetConnection.getPool(), runQueryConfig.schemaNames || runQueryConfig.schema);
|
|
171
|
+
const schemaInfo = yield (0, DatabaseHelper_1.getColumnInfoBySchemaByDatabase)(this.targetConnection.databaseType, this.targetConnection.getPool(), runQueryConfig.schema, queryResult);
|
|
172
|
+
this.targetConnection.close();
|
|
172
173
|
return schemaInfo;
|
|
173
174
|
}
|
|
174
175
|
else {
|
package/package.json
CHANGED
|
@@ -29,24 +29,27 @@ const DEFAULT_CACHE_TTL = 24 * 60 * 60;
|
|
|
29
29
|
|
|
30
30
|
export class CachedConnection {
|
|
31
31
|
public databaseType: "postgresql" | "snowflake" | "bigquery" | "mysql";
|
|
32
|
-
public pool: DatabaseConnection;
|
|
32
|
+
public pool: DatabaseConnection | null;
|
|
33
33
|
public orgId: any;
|
|
34
34
|
public ttl: number;
|
|
35
35
|
public cache: Mapable | null;
|
|
36
|
+
private config: any;
|
|
36
37
|
|
|
37
38
|
constructor(
|
|
38
39
|
databaseType: "postgresql" | "snowflake" | "bigquery" | "mysql",
|
|
39
40
|
config: any,
|
|
40
|
-
cacheConfig: Partial<CacheCredentials> = {}
|
|
41
|
+
cacheConfig: Partial<CacheCredentials> = {},
|
|
41
42
|
) {
|
|
42
43
|
this.databaseType = databaseType;
|
|
43
44
|
this.pool = connectToDatabase(databaseType, config);
|
|
45
|
+
this.config = config;
|
|
44
46
|
this.ttl = cacheConfig?.ttl ?? DEFAULT_CACHE_TTL;
|
|
45
47
|
this.cache = this.getCache(cacheConfig);
|
|
46
48
|
}
|
|
47
49
|
|
|
48
50
|
public async query(text: string, values?: any[]): Promise<any> {
|
|
49
51
|
try {
|
|
52
|
+
this.pool = this.getPool();
|
|
50
53
|
if (!this.cache) {
|
|
51
54
|
return await runQueryByDatabase(this.databaseType, this.pool, text);
|
|
52
55
|
}
|
|
@@ -58,7 +61,7 @@ export class CachedConnection {
|
|
|
58
61
|
const newResult = await runQueryByDatabase(
|
|
59
62
|
this.databaseType,
|
|
60
63
|
this.pool,
|
|
61
|
-
text
|
|
64
|
+
text,
|
|
62
65
|
);
|
|
63
66
|
const newResultString: string = JSON.stringify(newResult);
|
|
64
67
|
await this.cache.set(key, newResultString, "EX", DEFAULT_CACHE_TTL);
|
|
@@ -69,11 +72,15 @@ export class CachedConnection {
|
|
|
69
72
|
throw new PgError(
|
|
70
73
|
(err as any).detail,
|
|
71
74
|
(err as any).hint,
|
|
72
|
-
(err as any).position
|
|
75
|
+
(err as any).position,
|
|
73
76
|
);
|
|
74
77
|
} else if (err instanceof Error) {
|
|
75
78
|
throw new Error(err.message);
|
|
76
79
|
}
|
|
80
|
+
} finally {
|
|
81
|
+
if (this.databaseType.toLowerCase() === "mysql") {
|
|
82
|
+
this.close();
|
|
83
|
+
}
|
|
77
84
|
}
|
|
78
85
|
}
|
|
79
86
|
|
|
@@ -89,14 +96,24 @@ export class CachedConnection {
|
|
|
89
96
|
}: QuillConfig["cache"]): Mapable | null {
|
|
90
97
|
if (cacheType === "redis" || cacheType === "rediss") {
|
|
91
98
|
const redisURL = `${cacheType}://${username}:${password}@${host}:${port}`;
|
|
92
|
-
const client =
|
|
99
|
+
const client = createClient({ url: redisURL });
|
|
93
100
|
client.connect();
|
|
94
101
|
return client as Mapable;
|
|
95
102
|
}
|
|
96
103
|
return null;
|
|
97
104
|
}
|
|
98
105
|
|
|
106
|
+
public getPool() {
|
|
107
|
+
if (!this.pool) {
|
|
108
|
+
this.pool = connectToDatabase(this.databaseType, this.config);
|
|
109
|
+
}
|
|
110
|
+
return this.pool;
|
|
111
|
+
}
|
|
112
|
+
|
|
99
113
|
async close() {
|
|
100
|
-
|
|
114
|
+
if (this.pool) {
|
|
115
|
+
disconnectFromDatabase(this.databaseType, this.pool);
|
|
116
|
+
this.pool = null;
|
|
117
|
+
}
|
|
101
118
|
}
|
|
102
119
|
}
|
package/src/db/Mysql.ts
CHANGED
|
@@ -14,7 +14,7 @@ export interface MysqlConnectionConfig {
|
|
|
14
14
|
}
|
|
15
15
|
|
|
16
16
|
export function formatMysqlConfig(
|
|
17
|
-
connectionString: string
|
|
17
|
+
connectionString: string,
|
|
18
18
|
): MysqlConnectionConfig {
|
|
19
19
|
const parsedUrl = url.parse(connectionString);
|
|
20
20
|
const [user, password] = (parsedUrl.auth || "").split(":");
|
|
@@ -31,7 +31,7 @@ export function connectToMysql(config: MysqlConnectionConfig): MysqlPool {
|
|
|
31
31
|
const pool = mysql.createPool({
|
|
32
32
|
...config,
|
|
33
33
|
waitForConnections: true,
|
|
34
|
-
connectionLimit:
|
|
34
|
+
connectionLimit: 128,
|
|
35
35
|
queueLimit: 0,
|
|
36
36
|
});
|
|
37
37
|
return pool;
|
|
@@ -43,7 +43,7 @@ export function disconnectFromMysql(connection: MysqlPool) {
|
|
|
43
43
|
|
|
44
44
|
export async function runQueryMysql(
|
|
45
45
|
sql: string,
|
|
46
|
-
connection: MysqlPool
|
|
46
|
+
connection: MysqlPool,
|
|
47
47
|
): Promise<QuillQueryResults> {
|
|
48
48
|
const result: QuillQueryResults = await new Promise((resolve, reject) => {
|
|
49
49
|
connection.query(sql, (error, results, fields) => {
|
|
@@ -72,7 +72,7 @@ export async function runQueryMysql(
|
|
|
72
72
|
}
|
|
73
73
|
|
|
74
74
|
export async function getSchemasMysql(
|
|
75
|
-
connection: MysqlPool
|
|
75
|
+
connection: MysqlPool,
|
|
76
76
|
): Promise<string[]> {
|
|
77
77
|
const sql = `SELECT SCHEMA_NAME FROM INFORMATION_SCHEMA.SCHEMATA
|
|
78
78
|
WHERE schema_name != 'information_schema'
|
|
@@ -84,7 +84,7 @@ export async function getSchemasMysql(
|
|
|
84
84
|
|
|
85
85
|
export async function getTablesBySchemaMysql(
|
|
86
86
|
connection: MysqlPool,
|
|
87
|
-
schemaNames: string[]
|
|
87
|
+
schemaNames: string[],
|
|
88
88
|
): Promise<{ tableName: string; schemaName: string }[]> {
|
|
89
89
|
const allColumns = await Promise.all(
|
|
90
90
|
schemaNames.map(async (schema) => {
|
|
@@ -93,7 +93,7 @@ export async function getTablesBySchemaMysql(
|
|
|
93
93
|
return results.rows.map((row) => {
|
|
94
94
|
return { tableName: row.TABLE_NAME, schemaName: row.TABLE_SCHEMA };
|
|
95
95
|
});
|
|
96
|
-
})
|
|
96
|
+
}),
|
|
97
97
|
);
|
|
98
98
|
return allColumns.flat();
|
|
99
99
|
}
|
|
@@ -101,7 +101,7 @@ export async function getTablesBySchemaMysql(
|
|
|
101
101
|
export async function getColumnsByTableMysql(
|
|
102
102
|
connection: MysqlPool,
|
|
103
103
|
schemaName: string,
|
|
104
|
-
tableName: string
|
|
104
|
+
tableName: string,
|
|
105
105
|
): Promise<string[]> {
|
|
106
106
|
const sql = `SELECT COLUMN_NAME FROM INFORMATION_SCHEMA.COLUMNS WHERE TABLE_SCHEMA = '${schemaName}' AND TABLE_NAME = '${tableName}'`;
|
|
107
107
|
const results = await runQueryMysql(sql, connection);
|
|
@@ -112,7 +112,7 @@ export async function getForeignKeysMysql(
|
|
|
112
112
|
connection: MysqlPool,
|
|
113
113
|
schemaName: string,
|
|
114
114
|
tableName: string,
|
|
115
|
-
primaryKey: string
|
|
115
|
+
primaryKey: string,
|
|
116
116
|
): Promise<string[]> {
|
|
117
117
|
const depluralizedTableName = depluralize(tableName);
|
|
118
118
|
let sql = `SELECT COLUMN_NAME FROM INFORMATION_SCHEMA.COLUMNS
|
|
@@ -127,7 +127,7 @@ export async function getForeignKeysMysql(
|
|
|
127
127
|
});
|
|
128
128
|
// remove any foreignKeyStrings that are just 'id'
|
|
129
129
|
foreignKeysString = foreignKeysString.filter(
|
|
130
|
-
(key) => key !== "id" && key !== "_id_"
|
|
130
|
+
(key) => key !== "id" && key !== "_id_",
|
|
131
131
|
);
|
|
132
132
|
foreignKeysString = [...new Set(foreignKeysString)];
|
|
133
133
|
if (foreignKeysString.length === 0) {
|
|
@@ -151,7 +151,7 @@ export async function getForeignKeysMysql(
|
|
|
151
151
|
export async function getSchemaColumnInfoMysql(
|
|
152
152
|
connection: MysqlPool,
|
|
153
153
|
schemaName: string,
|
|
154
|
-
tableNames: { tableName: string; schemaName: string }[]
|
|
154
|
+
tableNames: { tableName: string; schemaName: string }[],
|
|
155
155
|
): Promise<
|
|
156
156
|
{ tableName: string; columns: { columnName: string; dataTypeID: number }[] }[]
|
|
157
157
|
> {
|
|
@@ -174,7 +174,7 @@ export async function getSchemaColumnInfoMysql(
|
|
|
174
174
|
fieldType: row.dataType,
|
|
175
175
|
})),
|
|
176
176
|
};
|
|
177
|
-
})
|
|
177
|
+
}),
|
|
178
178
|
);
|
|
179
179
|
return allColumns;
|
|
180
180
|
}
|
|
@@ -191,6 +191,10 @@ function mysqlTextDataTypeToPostgresOID(type: string): number {
|
|
|
191
191
|
return 1043;
|
|
192
192
|
case "timestamp": // date
|
|
193
193
|
return 1082;
|
|
194
|
+
case "date": // date
|
|
195
|
+
return 1082;
|
|
196
|
+
case "datetime": // date
|
|
197
|
+
return 1082;
|
|
194
198
|
default: // varchar
|
|
195
199
|
return 1043;
|
|
196
200
|
}
|
|
@@ -210,7 +214,9 @@ function mysqlDataTypeIdToPostgresType(type: number): number {
|
|
|
210
214
|
return 1043;
|
|
211
215
|
case 7: // date
|
|
212
216
|
return 1082;
|
|
213
|
-
case
|
|
217
|
+
case 10: // date
|
|
218
|
+
return 1082;
|
|
219
|
+
case 12: // date
|
|
214
220
|
return 1082;
|
|
215
221
|
default: // varchar
|
|
216
222
|
return 1043;
|
package/src/index.ts
CHANGED
|
@@ -76,13 +76,13 @@ export class Quill {
|
|
|
76
76
|
if (databaseConnectionString) {
|
|
77
77
|
credentials = getDatabaseCredentials(
|
|
78
78
|
databaseType,
|
|
79
|
-
databaseConnectionString
|
|
79
|
+
databaseConnectionString,
|
|
80
80
|
);
|
|
81
81
|
}
|
|
82
82
|
this.targetConnection = new CachedConnection(
|
|
83
83
|
databaseType,
|
|
84
84
|
credentials,
|
|
85
|
-
cache || {}
|
|
85
|
+
cache || {},
|
|
86
86
|
);
|
|
87
87
|
}
|
|
88
88
|
|
|
@@ -98,7 +98,7 @@ export class Quill {
|
|
|
98
98
|
metadata.preQueries,
|
|
99
99
|
this.targetConnection.databaseType,
|
|
100
100
|
metadata.databaseType,
|
|
101
|
-
metadata.runQueryConfig
|
|
101
|
+
metadata.runQueryConfig,
|
|
102
102
|
)
|
|
103
103
|
: {};
|
|
104
104
|
if (metadata.runQueryConfig?.overridePost) {
|
|
@@ -124,7 +124,7 @@ export class Quill {
|
|
|
124
124
|
response.queries,
|
|
125
125
|
this.targetConnection.databaseType,
|
|
126
126
|
metadata.databaseType,
|
|
127
|
-
responseMetadata.runQueryConfig
|
|
127
|
+
responseMetadata.runQueryConfig,
|
|
128
128
|
);
|
|
129
129
|
// QUICK JANKY FIX TO UPDATE METADATA AFTER GETTING MAPPED ARRAYS
|
|
130
130
|
if (results.mappedArray && responseMetadata.runQueryConfig?.arrayToMap) {
|
|
@@ -163,7 +163,7 @@ export class Quill {
|
|
|
163
163
|
queries: any[] | undefined,
|
|
164
164
|
pkDatabaseType: "postgresql" | "snowflake" | "bigquery" | "mysql",
|
|
165
165
|
databaseType?: string,
|
|
166
|
-
runQueryConfig?: AdditionalProcessing
|
|
166
|
+
runQueryConfig?: AdditionalProcessing,
|
|
167
167
|
) {
|
|
168
168
|
let results: any;
|
|
169
169
|
if (!queries) return { ...results, queryResults: [] };
|
|
@@ -182,7 +182,7 @@ export class Quill {
|
|
|
182
182
|
return { ...results, queryResults: [], mappedArray };
|
|
183
183
|
} else if (runQueryConfig?.getColumns) {
|
|
184
184
|
const queryResult = await this.targetConnection.query(
|
|
185
|
-
`${queries[0].replace(/;/, "")} limit 1
|
|
185
|
+
`${queries[0].replace(/;/, "")} limit 1`,
|
|
186
186
|
);
|
|
187
187
|
const columns = queryResult.fields.map((field: any) => {
|
|
188
188
|
return {
|
|
@@ -209,7 +209,7 @@ export class Quill {
|
|
|
209
209
|
}
|
|
210
210
|
try {
|
|
211
211
|
const queryResult = await this.targetConnection.query(
|
|
212
|
-
`${table.viewQuery.replace(/;/, "")} ${limit}
|
|
212
|
+
`${table.viewQuery.replace(/;/, "")} ${limit}`,
|
|
213
213
|
);
|
|
214
214
|
const columns = queryResult.fields.map((field: any) => {
|
|
215
215
|
return {
|
|
@@ -224,7 +224,7 @@ export class Quill {
|
|
|
224
224
|
} catch (err) {
|
|
225
225
|
return { ...table, error: "Error fetching columns" };
|
|
226
226
|
}
|
|
227
|
-
})
|
|
227
|
+
}),
|
|
228
228
|
);
|
|
229
229
|
results = { ...results, queryResults };
|
|
230
230
|
if (runQueryConfig?.fieldsToRemove) {
|
|
@@ -241,15 +241,16 @@ export class Quill {
|
|
|
241
241
|
} else if (runQueryConfig?.getTables) {
|
|
242
242
|
const queryResult = await getTablesBySchemaByDatabase(
|
|
243
243
|
this.targetConnection.databaseType,
|
|
244
|
-
this.targetConnection.
|
|
245
|
-
runQueryConfig.schemaNames! || runQueryConfig.schema
|
|
244
|
+
this.targetConnection.getPool(),
|
|
245
|
+
runQueryConfig.schemaNames! || runQueryConfig.schema,
|
|
246
246
|
);
|
|
247
247
|
const schemaInfo = await getColumnInfoBySchemaByDatabase(
|
|
248
248
|
this.targetConnection.databaseType,
|
|
249
|
-
this.targetConnection.
|
|
249
|
+
this.targetConnection.getPool(),
|
|
250
250
|
runQueryConfig.schema!,
|
|
251
|
-
queryResult
|
|
251
|
+
queryResult!,
|
|
252
252
|
);
|
|
253
|
+
this.targetConnection.close();
|
|
253
254
|
return schemaInfo;
|
|
254
255
|
} else {
|
|
255
256
|
if (runQueryConfig?.limitThousand) {
|
|
@@ -264,7 +265,7 @@ export class Quill {
|
|
|
264
265
|
const queryResults = await Promise.all(
|
|
265
266
|
queries.map(async (query) => {
|
|
266
267
|
return await this.targetConnection.query(query);
|
|
267
|
-
})
|
|
268
|
+
}),
|
|
268
269
|
);
|
|
269
270
|
results = { ...results, queryResults };
|
|
270
271
|
if (runQueryConfig?.fieldsToRemove) {
|
|
@@ -298,12 +299,12 @@ export class Quill {
|
|
|
298
299
|
|
|
299
300
|
private async postQuill(
|
|
300
301
|
path: string,
|
|
301
|
-
payload: any
|
|
302
|
+
payload: any,
|
|
302
303
|
): Promise<QuillClientResponse> {
|
|
303
304
|
const response = await axios.post(
|
|
304
305
|
`${this.baseUrl}/sdk/${path}`,
|
|
305
306
|
payload,
|
|
306
|
-
this.config
|
|
307
|
+
this.config,
|
|
307
308
|
);
|
|
308
309
|
return response.data;
|
|
309
310
|
}
|