Java DatabaseMetaData.getSchemas() returns 空结果集,预期非空结果集

Java DatabaseMetaData.getSchemas() returns empty ResultSet, expected non-empty ResultSet

试图了解这里发生了什么。 DatabaseMetaData 返回一个空的结果集,而实际上相同的 SQL 查询却没有。这不是主要问题,因为我正在使用第二个代码示例作为解决方法。

DatabaseMetaData dmd = this.connection.getMetaData();
ResultSet rs = dmd.getSchemas();
while (rs.next()){
  // empty result set
}

应为非空结果集。

ResultSet rs = this.connection.prepareStatement("SELECT SCHEMA_NAME FROM INFORMATION_SCHEMA.SCHEMATA;").executeQuery();
while (rs.next()){
  // non-empty result set with expected results
}

需要一个非空结果集并得到它。

据我所知,MySQL JDBC 驱动程序认为这是一个目录,而不是模式。所以你应该使用 getCatalogs 代替(无论你在哪里使用它,你都需要使用 catalog 参数,而不是 schema 参数)。

getSchemas method in Connector/J总是returns一个空结果集:

public java.sql.ResultSet getSchemas() throws SQLException {
    Field[] fields = new Field[2];
    fields[0] = new Field("", "TABLE_SCHEM", java.sql.Types.CHAR, 0);
    fields[1] = new Field("", "TABLE_CATALOG", java.sql.Types.CHAR, 0);

    ArrayList<ResultSetRow> tuples = new ArrayList<ResultSetRow>();
    java.sql.ResultSet results = buildResultSet(fields, tuples);

    return results;
}

getCatalogs returns the result of SHOW DATABASES. And in DatabaseMetaDataUsingInfoSchema 您会看到别名为 TABLE_CAT(对于目录)的信息架构的 TABLE_SCHEMA 列,并且 catalog 参数作为值传递给TABLE_SCHEMA 查询中的列:

String sql = "SELECT TABLE_SCHEMA AS TABLE_CAT, NULL AS TABLE_SCHEM, TABLE_NAME,"
        + "COLUMN_NAME, NULL AS GRANTOR, GRANTEE, PRIVILEGE_TYPE AS PRIVILEGE, IS_GRANTABLE FROM INFORMATION_SCHEMA.COLUMN_PRIVILEGES WHERE "
        + "TABLE_SCHEMA LIKE ? AND TABLE_NAME =? AND COLUMN_NAME LIKE ? ORDER BY COLUMN_NAME, PRIVILEGE_TYPE";

java.sql.PreparedStatement pStmt = null;

try {
    pStmt = prepareMetaDataSafeStatement(sql);

    if (catalog != null) {
        pStmt.setString(1, catalog);
    } else {
        pStmt.setString(1, "%");
    }

    pStmt.setString(2, table);
    pStmt.setString(3, columnNamePattern);

我知道这是一个旧的 post,但它出现在关于这个主题的 Google 搜索中,这里的答案对我不起作用。

经过更多的挖掘,我找到了正确的方法。

首先,您可以获得所有元数据table类型的列表,方法是

    DatabaseMetaData metaData = connection.getMetaData();
    ResultSet rs = metaData.getTableTypes();
    while (rs.next()) {
        System.out.println(rs.getString(1));
    }

我们感兴趣的table类型简称为TABLE.

并且此代码将提取 SQL 服务器中模式的所有名称,前提是您的凭据有权查看它们。

    DatabaseMetaData metaData = connection.getMetaData();
    ResultSet rs = metaData.getTables(null, null, null, new String[]{"TABLE"});
    while(rs.next())
    {
        System.out.println(rs.getString(1));
    }

无论如何,它对我有用 Java 8 和 mysql-connector-java-8.0.22