Object-Relational-Mapping via Hibernate. exports an EntityManagerFactory and EntityManager services.
This module extends jdbc module, before going forward, make sure you read the doc of the jdbc module first.
This module provides an advanced and recommended Open Session in View
pattern, which basically keeps the Session opened until the view is rendered. But it uses two database transactions:
-
first transaction is committed before rendering the view and then
-
a read only transaction is opened for rendering the view.
- An interceptor with a Open Session in View
EntityManagerFactoryEntityManagerduring request/response cycles
<dependency>
<groupId>org.jooby</groupId>
<artifactId>jooby-hbm</artifactId>
<version>1.0.0.CR6</version>
</dependency>{
use(new Hbm(EntityA.class, EntityB.class));
get("/", req -> {
EntityManager em = req.require(EntityManager.class);
// work with em...
});
}At bootstrap time you will see something similar to this:
* /** [*/*] [*/*] (hbm)The hbm route is the Open Session in View filter.
You are free to inject an EntityManagerFactory create a new
EntityManagerFactory#createEntityManager(), start transactions and do everything you
need.
For the time being, this doesn't work for an EntityManager. An EntityManager is
bound to the current request, which means you can't freely access from every single thread (like
manually started thread, started by an executor service, quartz, etc...).
Another restriction, is the access from Singleton services. If you need access from a
singleton services, you need to inject a Provider.
@Singleton
public class MySingleton {
@Inject
public MySingleton(Provider<EntityManager> em) {
this.em = em;
}
}This is because the EntityManager is bound as RequestScoped.
Still, we strongly recommend to leave your services in the default scope and avoid to use
Singleton objects, except of course for really expensive resources. This is also
recommend it by Guice.
Services in the default scope won't have this problem and are free to inject the EntityManager directly.
Classpath scanning is OFF by default, so you need to explicitly tell Hibernate which classes are persistent. This intentional and helps to reduce bootstrap time and have explicit control over persistent classes.
If you don't care about bootstrap time and/or just like the auto-discover feature, just do:
{
use(new Hbm().scan());
}After calling scan(), Hibernate will auto-discover all the entities application's
namespace. The namespace is defined by the package of your application. Given:
org.myproject.App it will scan everything under org.myproject.
Hibernate options can be set from your application.conf file, just make sure to prefix them with hibernate.*
hibernate.hbm2ddl.auto = updatehibernate {
id.new_generator_mappings = true
archive.autodetection = class
# update for dev, validate for others
# hbm2ddl.auto = update
current_session_context_class = managed
}
javax.persistence {
}