【问题标题】:Apache derby in-memory db schema dump with Hibernate 4+Apache derby in-memory db schema dump with Hibernate 4+
【发布时间】:2013-03-06 00:23:20
【问题描述】:

我在单元测试中使用 Apache Derby 10.9.x 和 Hibernate Entitymanager 4.1.9.Final。 Derby db 模式是从 JPA 注释实体生成的。只有一个 persistence.xml 配置文件。我想在单元测试期间/之前/之后转储生成的 Derby db 模式。这样做的程序化方式是什么?

解决方案:

    // should not be required because Hibernate already started Derby:
    //Class.forName("org.apache.derby.jdbc.EmbeddedDriver").newInstance();

    try (Connection conn = DriverManager.getConnection ("jdbc:derby:memory:unit-testing;")) {
        String cat = null;
        String schema = "ROOT";

        DatabaseMetaData md = conn.getMetaData();
        ResultSet rs = md.getTableTypes();
        ResultSetUtils.dump(rs);
        rs = md.getTables(cat, schema, null, new String[]{"TABLE"});
        ResultSetUtils.dump(rs);
        rs = md.getColumns(cat, schema, null, null);
        ResultSetUtils.dump(rs);
    }

公共类 ResultSetUtils {

private static final Logger logger = Logger.getLogger(ResultSetUtils.class.getName());
private static final String COL_SEPARATOR = ";";

public static int getColForLabel(ResultSet rs, String labelname) throws SQLException {
    ResultSetMetaData rsmd = rs.getMetaData();

    for (int i = 1; i <= rsmd.getColumnCount(); i++) {
        if (labelname.equals(rsmd.getColumnLabel(i))) {
            return i;
        }
    }

    throw new SQLException("Invalid label name " + labelname);
}

public static void dump(ResultSet rs) throws SQLException {

    // the order of the rows in a cursor
    // are implementation dependent unless you use the SQL ORDER statement
    ResultSetMetaData meta = rs.getMetaData();
    int colmax = meta.getColumnCount();
    int i;
    Object o;

    StringBuilder sb = new StringBuilder(512);
    for (i = 0; i < colmax; ++i) {
        if(i>0) {
            sb.append(COL_SEPARATOR);
        }
        String s = meta.getColumnName(i + 1);
        sb.append((s == null) ? "NULL" : s);
        s = meta.getColumnTypeName(i + 1);
        sb.append((s == null) ? "(NULL)" : "("+s+")");
    }
    logger.info(sb.toString());


    // the result set is a cursor into the data.  You can only
    // point to one row at a time
    // assume we are pointing to BEFORE the first row
    // rs.next() points to next row and returns true
    // or false if there is no next row, which breaks the loop
    for (; rs.next();) {
        sb = new StringBuilder(512);
        for (i = 0; i < colmax; ++i) {
            if(i>0) {
                sb.append(COL_SEPARATOR);
            }
            o = rs.getObject(i + 1);    // Is SQL the first column is indexed
            sb.append((o == null) ? "NULL" : o.toString());
        }

        logger.info(sb.toString());
    }
}

}

【问题讨论】:

    标签: hibernate jpa schema derby


    【解决方案1】:

    访问架构的编程方式是使用 DatabaseMetaData 类:http://docs.oracle.com/javase/6/docs/api/java/sql/DatabaseMetaData.html

    从getTables()方法开始,打印出返回的信息。

    【讨论】:

    • 我更喜欢德比本土的东西,即。我希望 Derby 告诉我它的架构是什么样的。我不能通过一些方法调用简单地执行“dblook”吗?
    • 当然! Java 程序可以调用其他 Java 程序。 db.apache.org/derby/docs/10.9/tools/ctoolsdblook.html
    【解决方案2】:

    pom.xml:

    <dependency>
        <groupId>org.apache.derby</groupId>
        <artifactId>derbytools</artifactId>
        <version>10.9.1.0</version>
    </dependency>
    

    代码:

    new dblook(new String[]{"-d", "jdbc:derby:memory:unit-testing;", "-verbose"});
    

    没有可打印帮助的参数:

    new dblook(new String[]{});
    

    结果:

    -- Timestamp: 2013-03-09 00:19:49.733
    -- Source database is: memory
    -- Connection URL is: jdbc:derby:memory:unit-testing;
    -- appendLogs: false
    
    -- ----------------------------------------------
    -- DDL Statements for schemas
    -- ----------------------------------------------
    
    CREATE SCHEMA "ROOT";
    
    -- ----------------------------------------------
    -- DDL Statements for tables
    -- ----------------------------------------------
    
    CREATE TABLE "ROOT"."BLOG" ("DTYPE" VARCHAR(31) NOT NULL, "ID" BIGINT NOT NULL GENERATED BY DEFAULT AS IDENTITY (START WITH 1, INCREMENT BY 1), "BODY" VARCHAR(255), "CREATEDAT" TIMESTAMP, "RAWDATA" BLOB(2147483647), "SUBJECT" VARCHAR(255), "SENDER" VARCHAR(255));
    
    -- ----------------------------------------------
    -- DDL Statements for keys
    -- ----------------------------------------------
    
    -- primary/unique
    ALTER TABLE "ROOT"."BLOG" ADD CONSTRAINT "SQL130309001949220" PRIMARY KEY ("ID");
    

    JDBC 元数据操作似乎缺少一些东西,例如索引、触发器等。

    【讨论】:

    • 注意,如果你想将 DDL 存储到文件中以供进一步处理(而不是简单地输出到 stdout),请将额外参数“-o”、“filename”添加到 String[] 参数dblook 构造函数。
    猜你喜欢
    • 2016-01-28
    • 1970-01-01
    • 1970-01-01
    • 2012-01-20
    • 2013-10-21
    • 2014-09-08
    • 1970-01-01
    • 2018-09-13
    • 1970-01-01
    相关资源
    最近更新 更多