JPA,何时打开和关闭entityManager

时间:2015-11-16 11:50:24

标签: java hibernate jpa

我为Web应用程序设置了一个spring MVC应用程序,我正在使用JPA 2.1的Hibernates实现。

我已经创建了我的模型,并且能够很好地与数据库进行交互。

我还决定使用服务类来管理返回实体。我所做的是创建一个BaseService类,所以所有其他服务类都将在此基础上进行扩展,并且他们可以访问常见的函数,如create(),delete(),update()和list()。

我的问题是我不确定何时应该创建EntityManager以及何时应该关闭它?

目前,在我的控制器中,我在控制器加载时启动所需的服务;

@Controller
@RequestMapping("/mycontroller")
public class TestController {

    CarService carService = new CarService();
    ShowroomService showroomService = new ShowroomService();
    }
}

以下是其他服务扩展的BaseService;

public class Service<Ety> {

    EntityManager em = null;
    public Class<Ety> entityClass;

    public Service(Class<Ety> entityClass) {
        this.entityClass = entityClass;

        em = JPAUtil.getEntityManager();
    }

    public Ety get(int id) {
        Ety object = null;

        em.getTransaction().begin();
        object = em.find(entityClass, id);
        em.getTransaction().commit();

        return object;
    }

    public List list() {
        List<Ety> objects;

        em.getTransaction().begin();
        objects = em.createQuery("SELECT c FROM "+entityClass.getName()+" c").getResultList();
        em.getTransaction().commit();

        return objects;
    }

    public void save(Ety object) {
        em.getTransaction().begin();
        em.persist(object);
        em.getTransaction().commit();
    }

    public void update(Ety object) {
        em.getTransaction().begin();
        em.merge(object);
        em.getTransaction().commit();
    }

    public void delete(Ety object) {
        em.getTransaction().begin();
        em.remove(object);
        em.getTransaction().commit();
    }

}

这是一个扩展上述内容的示例服务;

public class CarService extends Service<Car> {

    public CarService() {
        super(Car.class);
    }

}

正如您所看到的,我在创建服务时创建了一个EntityManager,但目前我还没有在任何地方关闭它。

我是在正确的位置创建实体管理器?什么时候应该关闭它。

我曾考虑将实体管理器放在静态属性中并在过滤器中创建它,然后在应用程序结束时关闭它,但是我相信这不会是线程安全的并且会导致问题吗?

任何建议都将受到赞赏。

2 个答案:

答案 0 :(得分:1)

你的CarService应该是一个spring bean,而实例是从spring创建的。不是你的代码。与EntityManager相同。您可以将entityManager与@autowired注释一起使用。

答案 1 :(得分:0)

为每笔交易打开新的EntityManager。

这个EntityManager就像一个映射到数据库的Bag,但只有打开时内部管理零实体。 当你使用它时,这个Bag将被一些实体填充,Hibernate将会创建足够的请求。

您将关闭此行李以在交易结束时节省内存。

当然,有一些技巧可以为给定的EntityManager提供许多事务,但是你有最全面的想法。一如既往地取决于......

如果您使用Spring或JavaEE之类的框架,它将打开和关闭EntityManager,以及为您启动和提交事务。你只有自己的业务才能写作。