Java Application中的多数据库支持

时间:2013-12-30 09:23:18

标签: java sql hibernate jpa

我有一个Java Web应用程序,它目前支持DB2和Oracle作为后端数据库。我也计划支持MySQL,因此面临这个问题。

到目前为止,我一直在代码本身内部进行硬编码查询,并在必要时为Oracle和DB2的查询设置if-else条件。

例如。要获得高薪的前10名员工,我必须像这样编码

String query = null;
if(DatabaseUtil.getDatabaseName().equalsIgnoreCase("oracle"))
{
    query = "select * from ( select * from emp order by sal desc ) where ROWNUM <= 5";
}
else if(DatabaseUtil.getDatabaseName().equalsIgnoreCase("db2"))
{
    query = "select * from emp order by sal desc fetch first 5 rows only";
}

如果我添加了Mysql,if-else条件会增长并且会变得混乱。

if(DatabaseUtil.getDatabaseName().equalsIgnoreCase("oracle"))
{
    query = "select * from ( select * from emp order by sal desc ) where ROWNUM <= 5";
}
else if(DatabaseUtil.getDatabaseName().equalsIgnoreCase("db2"))
{
    query = "select * from emp order by sal desc fetch first 5 rows only";
}
else if(DatabaseUtil.getDatabaseName().equalsIgnoreCase("mysql"))
{
    query = "select * from emp order by sal desc limit 0,5";
}

您认为解决方案是什么? Hibernate / JPA可以解决这个问题吗?

我尝试过的事情

1)编写工厂设计模式以进行基于接口的查询选择。只需调用Interface.getHighSalEmployees(),它将根据加载的驱动程序返回具体类实现的查询。也就是说,如果应用程序连接到Oracle,它将给我OracleConcreteClass.getHighSalEmployees()

2)阅读有关Hibernate / HQL的内容 - 但无法找到合理的东西。

2 个答案:

答案 0 :(得分:0)

您可以指定使用Hibernate时要使用的方言。您可以在https://github.com/hibernate/hibernate-orm/tree/master/hibernate-core/src/main/java/org/hibernate/dialect中找到Hibernate方言列表。例如,有Oracle10gDialectH2DialectMySQL5Dialect

如果需要,您也可以创建自己的方言。

如果您只使用HQL或JP QL(并且从不直接发出本机查询),您应该能够删除 if - else 条件。在启动应用程序时,您的代码需要在创建持久化上下文时选择正确的JDBC驱动程序和Hibernate方言。

如果在应用程序中使用多个数据库,则应该能够创建具有不同方言的多重持久性上下文。

答案 1 :(得分:0)

据我所知,您的问题完全适合在数据库和Java逻辑之间使用ORM的想法。我们的想法是在数据库表,视图等之上构建Hibernate(比如一个实现)实体,并委托ORM构建特定底层数据库语法中的查询,更新等。

部署应用程序时,您应该使用其配置文件来实例化正确的JDBC驱动程序和Hibernate配置,以及配置文件中的所有内容,因此您永远不会更改逻辑。完成这项工作后,将应用程序移植到您能想象到的任何其他RDBM上都是微不足道的。