0
votes

I have my j2ee application, and I've designed an EJB module that use JPA for storing items on database. Inside this EJB package I have the persistence.xml that is referring to a JTA data source usually provided by the application server.

Now I have to build another application that use just the EJB module of my application. It is a stand alone application, so no j2ee server. How should I do it? I need an EJB container and a JPA provider, I understand that much, but I also need to provide the data source in the jndi as defined in the persistence.xml inside the ejb jar. I use also container managed transaction and dependency injection in my ejb package, and I want that everything just works like the j2ee counterpart, without modifying the ejb module.

1

1 Answers

1
votes

I am using a JEE JPA module from a standalone application for testing, but the idea is the same. There is a method, EntityManagerFactory createEmf(), that creates the EntityManagerFactory as follows:

public static EntityManagerFactory createEmf() {
    try {
        HashMap<String,String> cfg = new HashMap<String,String>();

        String connUrl = ...;
        String userName = ...;
        String password = ...;

        cfg.put("hibernate.dialect", "org.hibernate.dialect.MySQL5InnoDBDialect");
        cfg.put("hibernate.connection.driver_class", "com.mysql.jdbc.Driver");

        cfg.put("javax.persistence.transactionType", "RESOURCE_LOCAL");
        cfg.put("hibernate.connection.username", userName);
        cfg.put("hibernate.connection.password", password);
        cfg.put("hibernate.connection.url", connUrl);
        // worked for Hibernate 4.0.1; doesn't work for 4.3:
        //cfg.put("javax.persistence.jtaDataSource", "");
        // works for 4.3:
        cfg.put("javax.persistence.jtaDataSource", null);
        cfg.put("hibernate.hbm2ddl.auto", "create");
        cfg.put("hibernate.show_sql", "true");
        EntityManagerFactory emf = Persistence.createEntityManagerFactory("xxxxxPU",cfg);
        return emf;
    }
    catch(RuntimeException re) {
        throw re;
    }
    catch(Exception e) {
        throw new RuntimeException(e);
    }
}

The core is the Persistence.createEntityManagerFactory(name,properties) method. The properties override and complement values declared in persistence.xml.

In the real implementation I read the connection parameters from a proerties file. So no need for a DataSource (hopefully, there will only be one connection if this is a client application, so no need for a pool).

This way however, you have to manage transactions manually!!! A workaround would be to use CDI or AOP interceptors to wrap your business methods with transactions. That needs some effort, but will probably save you the overhead of starting a standalone EJB container.