Reputation: 21321
I have to work on a web Glassfish - Java EE based web app and we'll have to deploy the app to multiple environments and there are certain properties that are different depending on which env the app is deployed on. So my question is how can I make these configurations?
For example, in my orm.xml, I have something like this
<?xml version="1.0" encoding="UTF-8"?> <entity-mappings xmlns="http://java.sun.com/xml/ns/persistence/orm" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:schemaLocation="http://java.sun.com/xml/ns/persistence/orm orm_1_0.xsd" version="1.0">
<persistence-unit-metadata>
<persistence-unit-defaults>
<schema>DevSchema</schema>
</persistence-unit-defaults>
</persistence-unit-metadata> </entity-mappings>
How can I change DevSchema to ProdSchema, for example? Say I have 2 property files. dev.properties and prod. properties. How can I use values from the appropriate file dependign on the env?
Thanks!
Upvotes: 0
Views: 204
Reputation: 301
If you use Maven to build your application, you can benefit from Maven resource filtering to generate your persistence.xml
. Simply replace "DevSchema" with the key from your property file, and supply the file in the <filter>
tag of Maven resource plugin configuration (see the link above for details).
However, this implies that you'll end up with two different WAR artifacts for different environments. This is generally considered anti-pattern; you will have to track both artifacts, and your artifact repository (if any) will hold almost duplicate WARs. It is generally preferred that the single artifact be used for all the deployments. For that, you can define all your persistence units in a single persistence.xml
under different names, and use CDI to select the proper one. This can be done at least two ways.
Using producer method:
@PersistenceContext(unitName = "DevPU")
private EntityManager devEM;
@PersistenceContext(unitName = "ProdPU")
private EntityManager prodEM;
@Produces @MyDB EntityManager getEM() {
// Here you must detect your current environment and return the appropriate entity manager
}
To inject EntityManager into some other bean's field:
@Inject @MyDB private EntityManager em;
You will have to define your @MyDB
annotation type to indicate that a non-default EntityManager
has to be injected (the default one is chosen by application server).
Using producer fields:
@Produces
@DevDB
@PersistenceContext(unitName = "DevPU")
private EntityManager devEM;
@Produces
@ProdDB
@PersistenceContext(unitName = "ProdPU")
private EntityManager prodEM;
To inject EntityManager:
@Inject private Instance<EntityManager> instance;
void foo() {
// this could be ProdDB as well, depending on the environment
EntityManager em = instance.select(DevDB.class).get();
}
Here, you will have to define two annotation types, @ProdDB
and @DevDB
, and dynamically choose one via javax.enterprise.inject.Instance
injection (or that could be single annotation type with a parameter).
Upvotes: 1