feat: implement connection management in DatabasePlugin; add connection check in RedisPlugin; update session ID in runQuery test
This commit is contained in:
@ -14,6 +14,23 @@ export class DatabasePlugin extends Plugin {
|
|||||||
super(name, ["query"]);
|
super(name, ["query"]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static async isConnected(key: string): Promise<boolean> {
|
||||||
|
try {
|
||||||
|
const pool = DatabasePlugin.connectionPool.get(key);
|
||||||
|
if (!pool) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
const connection = await pool.getConnection();
|
||||||
|
await connection.ping();
|
||||||
|
connection.release();
|
||||||
|
|
||||||
|
return true;
|
||||||
|
} catch {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
static async init(
|
static async init(
|
||||||
name: string,
|
name: string,
|
||||||
config: {
|
config: {
|
||||||
@ -28,18 +45,19 @@ export class DatabasePlugin extends Plugin {
|
|||||||
): Promise<DatabasePlugin> {
|
): Promise<DatabasePlugin> {
|
||||||
const connectionKey = `${config.host}:${config.port}:${config.user}:${config.database}`;
|
const connectionKey = `${config.host}:${config.port}:${config.user}:${config.database}`;
|
||||||
|
|
||||||
if (DatabasePlugin.connectionPool.has(connectionKey)) {
|
if (await DatabasePlugin.isConnected(connectionKey)) {
|
||||||
const existingConnection =
|
return new DatabasePlugin(
|
||||||
DatabasePlugin.connectionPool.get(connectionKey);
|
name,
|
||||||
|
await DatabasePlugin.connectionPool.get(connectionKey).getConnection()
|
||||||
if (!(await existingConnection.ping())) {
|
);
|
||||||
DatabasePlugin.connectionPool.delete(connectionKey);
|
|
||||||
} else {
|
|
||||||
return new DatabasePlugin(name, existingConnection);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
const dbConnection = await mysql.createConnection({
|
if (DatabasePlugin.connectionPool.has(connectionKey)) {
|
||||||
|
await DatabasePlugin.connectionPool.get(connectionKey).end();
|
||||||
|
DatabasePlugin.connectionPool.delete(connectionKey);
|
||||||
|
}
|
||||||
|
|
||||||
|
const poolConnections = mysql.createPool({
|
||||||
host: config.host,
|
host: config.host,
|
||||||
user: config.user,
|
user: config.user,
|
||||||
port: config.port,
|
port: config.port,
|
||||||
@ -52,8 +70,8 @@ export class DatabasePlugin extends Plugin {
|
|||||||
connectionLimit: 15,
|
connectionLimit: 15,
|
||||||
});
|
});
|
||||||
|
|
||||||
DatabasePlugin.connectionPool.set(connectionKey, dbConnection);
|
DatabasePlugin.connectionPool.set(connectionKey, poolConnections);
|
||||||
return new DatabasePlugin(name, dbConnection);
|
return new DatabasePlugin(name, await poolConnections.getConnection());
|
||||||
}
|
}
|
||||||
|
|
||||||
async query(query): Promise<any> {
|
async query(query): Promise<any> {
|
||||||
@ -61,6 +79,9 @@ export class DatabasePlugin extends Plugin {
|
|||||||
}
|
}
|
||||||
|
|
||||||
onFinish() {
|
onFinish() {
|
||||||
this.dbConnection.end();
|
const pool = this.dbConnection?.pool;
|
||||||
|
if (pool && typeof pool.releaseConnection === "function") {
|
||||||
|
pool.releaseConnection(this.dbConnection);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -2,6 +2,8 @@ import Redis from "ioredis";
|
|||||||
import { Plugin } from "../plugin.class";
|
import { Plugin } from "../plugin.class";
|
||||||
|
|
||||||
export class RedisPlugin extends Plugin {
|
export class RedisPlugin extends Plugin {
|
||||||
|
private static connectionPool: Map<string, Redis> = new Map();
|
||||||
|
|
||||||
constructor(
|
constructor(
|
||||||
name: string,
|
name: string,
|
||||||
private redisClient: Redis,
|
private redisClient: Redis,
|
||||||
@ -22,16 +24,37 @@ export class RedisPlugin extends Plugin {
|
|||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private static isConnected(key: string): boolean {
|
||||||
|
return (
|
||||||
|
RedisPlugin.connectionPool.has(key) &&
|
||||||
|
RedisPlugin.connectionPool.get(key).status === "ready"
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
static init(
|
static init(
|
||||||
name: string,
|
name: string,
|
||||||
config: { host: string; port: number },
|
config: { host: string; port: number },
|
||||||
prefix: string
|
prefix: string
|
||||||
): RedisPlugin {
|
): RedisPlugin {
|
||||||
|
const key = `${config.host}:${config.port}`;
|
||||||
|
|
||||||
|
if (RedisPlugin.isConnected(key)) {
|
||||||
|
return new RedisPlugin(name, RedisPlugin.connectionPool.get(key), prefix);
|
||||||
|
}
|
||||||
|
|
||||||
|
RedisPlugin.connectionPool.delete(key);
|
||||||
|
|
||||||
const redisClient = new Redis({
|
const redisClient = new Redis({
|
||||||
host: config.host,
|
host: config.host,
|
||||||
port: config.port,
|
port: config.port,
|
||||||
|
commandTimeout: 10000,
|
||||||
|
connectTimeout: 10000,
|
||||||
|
lazyConnect: false,
|
||||||
|
maxRetriesPerRequest: 1,
|
||||||
|
enableReadyCheck: true,
|
||||||
});
|
});
|
||||||
|
|
||||||
|
RedisPlugin.connectionPool.set(key, redisClient);
|
||||||
return new RedisPlugin(name, redisClient, prefix);
|
return new RedisPlugin(name, redisClient, prefix);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@ -130,8 +130,6 @@ export class Vm {
|
|||||||
});
|
});
|
||||||
|
|
||||||
this.setFunction("log", (...args) => {
|
this.setFunction("log", (...args) => {
|
||||||
console.log(...args);
|
|
||||||
|
|
||||||
const logType = args.find(
|
const logType = args.find(
|
||||||
(arg) =>
|
(arg) =>
|
||||||
arg &&
|
arg &&
|
||||||
|
|||||||
@ -9,7 +9,7 @@ export default async (token: string, queryData: Record<string, any>) => {
|
|||||||
{
|
{
|
||||||
headers: {
|
headers: {
|
||||||
"x-api-token": "efbeccd6-dde1-47dc-b3aa-4fbd773d5429",
|
"x-api-token": "efbeccd6-dde1-47dc-b3aa-4fbd773d5429",
|
||||||
Cookie: `x-session-id=gTEd90aRJFmLzJKu_1760193754588`,
|
Cookie: `x-session-id=cqfqc4G3K8JX7JjQ_1760336438448`,
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
);
|
);
|
||||||
|
|||||||
Reference in New Issue
Block a user