fix: too many connect error (#71)

* add fetch all struct

* add other database implement

* rename method name

* adjust the order of functions

* eslint

* eslint

* eslint

* eslint

* eslint

* fix error end when fetch schema batch
This commit is contained in:
CorrectRoadH
2023-05-04 23:36:48 +08:00
committed by GitHub
parent 498bf156c0
commit 40e86fbdaf
5 changed files with 138 additions and 8 deletions

View File

@ -16,6 +16,11 @@ export interface Connector {
tableName: string,
structureFetched: (tableName: string, structure: string) => void
) => Promise<void>;
getTableStructureBatch: (
databaseName: string,
tableNameList: string[],
structureFetched: (tableName: string, structure: string) => void
) => Promise<void>;
}
export const newConnector = (connection: Connection): Connector => {

View File

@ -117,6 +117,39 @@ const getTableStructure = async (
);
};
const getTableStructureBatch = async (
connection: Connection,
databaseName: string,
tableNameList: string[],
structureFetched: (tableName: string, structure: string) => void
): Promise<void> => {
const pool = await getMSSQLConnection(connection);
const request = pool.request();
await Promise.all(
tableNameList.map(async (tableName) => {
const { recordset } = await request.query(
`SELECT COLUMN_NAME, DATA_TYPE, IS_NULLABLE FROM ${databaseName}.INFORMATION_SCHEMA.COLUMNS WHERE TABLE_SCHEMA='dbo' AND TABLE_NAME='${tableName}';`
);
const columnList = [];
// Transform to standard schema string.
for (const row of recordset) {
columnList.push(
`${row["COLUMN_NAME"]} ${row["DATA_TYPE"].toUpperCase()} ${
String(row["IS_NULLABLE"]).toUpperCase() === "NO" ? "NOT NULL" : ""
}`
);
}
structureFetched(
tableName,
`CREATE TABLE [${tableName}] (
${columnList.join(",\n")}
);`
);
})
);
};
const newConnector = (connection: Connection): Connector => {
return {
testConnection: () => testConnection(connection),
@ -130,6 +163,17 @@ const newConnector = (connection: Connection): Connector => {
structureFetched: (tableName: string, structure: string) => void
) =>
getTableStructure(connection, databaseName, tableName, structureFetched),
getTableStructureBatch: (
databaseName: string,
tableNameList: string[],
structureFetched: (tableName: string, structure: string) => void
) =>
getTableStructureBatch(
connection,
databaseName,
tableNameList,
structureFetched
),
};
};

View File

@ -111,6 +111,29 @@ const getTableStructure = async (
structureFetched(tableName, rows[0]["Create Table"] || "");
};
const getTableStructureBatch = async (
connection: Connection,
databaseName: string,
tableNameList: string[],
structureFetched: (tableName: string, structure: string) => void
): Promise<void> => {
const conn = await getMySQLConnection(connection);
await Promise.all(
tableNameList.map(async (tableName) => {
const [rows] = await conn.query<RowDataPacket[]>(
`SHOW CREATE TABLE \`${databaseName}\`.\`${tableName}\`;`
);
if (rows.length !== 1) {
throw new Error("Unexpected number of rows.");
}
structureFetched(tableName, rows[0]["Create Table"] || "");
})
).finally(() => {
conn.destroy();
});
};
const newConnector = (connection: Connection): Connector => {
return {
testConnection: () => testConnection(connection),
@ -124,6 +147,17 @@ const newConnector = (connection: Connection): Connector => {
structureFetched: (tableName: string, structure: string) => void
) =>
getTableStructure(connection, databaseName, tableName, structureFetched),
getTableStructureBatch: (
databaseName: string,
tableNameList: string[],
structureFetched: (tableName: string, structure: string) => void
) =>
getTableStructureBatch(
connection,
databaseName,
tableNameList,
structureFetched
),
};
};

View File

@ -121,6 +121,42 @@ const getTableStructure = async (
);
};
const getTableStructureBatch = async (
connection: Connection,
databaseName: string,
tableNameList: string[],
structureFetched: (tableName: string, structure: string) => void
): Promise<void> => {
connection.database = databaseName;
const client = newPostgresClient(connection);
await client.connect();
await Promise.all(
tableNameList.map(async (tableName) => {
const { rows } = await client.query(
`SELECT column_name, data_type, is_nullable FROM information_schema.columns WHERE table_schema='public' AND table_name=$1;`,
[tableName]
);
const columnList = [];
// TODO(steven): transform it to standard schema string.
for (const row of rows) {
columnList.push(
`${row["column_name"]} ${row["data_type"].toUpperCase()} ${
String(row["is_nullable"]).toUpperCase() === "NO" ? "NOT NULL" : ""
}`
);
}
structureFetched(
tableName,
`CREATE TABLE \`${tableName}\` (
${columnList.join(",\n")}
);`
);
})
).finally(async () => {
await client.end();
});
};
const newConnector = (connection: Connection): Connector => {
return {
testConnection: () => testConnection(connection),
@ -134,6 +170,17 @@ const newConnector = (connection: Connection): Connector => {
structureFetched: (tableName: string, structure: string) => void
) =>
getTableStructure(connection, databaseName, tableName, structureFetched),
getTableStructureBatch: (
databaseName: string,
tableNameList: string[],
structureFetched: (tableName: string, structure: string) => void
) =>
getTableStructureBatch(
connection,
databaseName,
tableNameList,
structureFetched
),
};
};

View File

@ -22,14 +22,14 @@ const handler = async (req: NextApiRequest, res: NextApiResponse) => {
structure,
});
};
Promise.all(
rawTableNameList.map(async (tableName) =>
connector.getTableStructure(db, tableName, structureFetched)
)
).then(() => {
res.status(200).json({
data: tableStructures,
});
await connector.getTableStructureBatch(
db,
rawTableNameList,
structureFetched
);
res.status(200).json({
data: tableStructures,
});
} catch (error: any) {
res.status(400).json({