如何在运行时选择JDBC / JPA实现?

时间:2017-09-03 14:58:29

标签: java jpa optimization jdbc

我正在编写一个应用程序,用于管理数据库,使用 JDBC和JPA 进行考试。我希望用户在开始时选择一次使用的API,以便所有应用程序将使用所选的API (无论是JPA还是JDBC)。

目前我决定使用这种方法:

  1. 我为所有需要的方法声明创建了每个DAO类的接口(例如interface UserDAO)。
  2. 我为每个DAO 创建了两个类,使用的是(例如UserDAOImplJDBCUserDAOImplJPA)。它们都实现了接口(在我们的例子中,UserDAO)。
  3. 我创建了第三个类(例如UserDAOImpl),它扩展了JDBC实现类。 在我的所有代码中,我一直在使用此类。当我想切换到JPA时,我只需要在extends ***ImplDAOJDBCextends ***ImplDAOJPA的所有DAO类中进行更改。
  4. 现在,当我开始拥有许多DAO类时,每次修改代码都会变得复杂。

    有没有办法更快地更改所有extends? 我正在考虑在第一个屏幕中添加一个选项(例如radioGroup)来选择JDBC或JPA。但是我不知道如何使其工作而不必重新构建所有代码。有什么想法吗?

2 个答案:

答案 0 :(得分:2)

每次需要时,使用工厂获取相应的DAO:

public class UserDaoFactory {
    public UserDao create() {
        if (SomeSharedSingleton.getInstance().getPersistenceOption() == JDBC) {
            return new UserDAOImplJDBC();
        }
        else {
            return new UserDAOImplJPA();
        }
    }
}

这是一个经典的OO模式。

那就是说,我希望你意识到你在那里做的事情应该永远不会在真正的应用程序中完成:

  • 没有理由以两种不同的方式做同样的事情
  • JPA和JDBC的持久性模型极为不同:JPA实体由JPA引擎管理,因此对JPA实体的每次更改都是透明的持久性。 JDBC不是这种情况,您从数据库中获取的数据是分离的。因此,在JPA和JDBC之间实现业务逻辑的方式非常不同:在使用JPA时,通常永远不需要保存任何更改。

答案 1 :(得分:0)

你有1和2对,但3完全错误 例如,不要让Impl扩展其他实现之一,而是选择使用实用程序方法初始化哪个实现。假设您没有使用Spring等依赖注入框架。

UserDAO dao = DBUtils.getUserDAO();

public class DBUtils {

   public static boolean shouldUseJdbc() {
      // Decide on some configuration what should you use
   }

   public static UserDAO getUserDAO() {
      if (shouldUseJdbc()) {
          return new UserDAOImplJDBC();
      }
      else {
          return new UserDAOImplJPA();
      }
   }
}

这仍然是一个问题,因为你的DAO不需要每次都被实例化,但实际上应该是单身。