[jboss-user] [EJB 3.0] - Re: How to connect multiple databases at same time?

kmagnant do-not-reply at jboss.com
Mon Oct 15 12:29:05 EDT 2007


I have something that seems to work, although I don't know if it the best solution - feel free to comment/improve (or trash, if appropriate) this approach.

The problem space dictates that the application operate on a schema that is determined by user input, So the schema must be derived at runtime.  The application id deployed in several environments as it evolves from current branch development to production - this is still a challenge as I am required to change code, the list of persistence units; I am looking at ant hacks to accommodate this. 

The basic approach is to define a Stateless Session Bean base class that defines the PersistenceUnits that the application has available to it.  My entities are all wrapped by generated session facades.  Each method in the session facade must call super.getEntitymanager(persistenceUnitName) to ensure that an EntityManager is available.  The PersistenceUnitName is determined by the client of the session facade.

One cool aspect of this design is that the table centric set of entities and session facades contain absolutely no business logic.  Business logic goes in subclasses of the session facades to accomplish application/webService specific tasks.  The result is a set of beans that expose the database and a common definition of property names.  The brings naming consistence to all web services that are based on these tables.  Not terribly slick, but it removes naming challenges/convention/religion from other development organizations that use them.

The Session Bean base class looks like:


  | package com.czncorp.base.session;
  | 
  | import javax.ejb.Stateless;
  | import javax.naming.*;
  | import javax.persistence.*;
  | 
  | @Stateless
  | @PersistenceUnits({
  |    @PersistenceUnit(name="persistence/CM5AZ",  unitName="CM5AZ"),
  |    @PersistenceUnit(name="persistence/CM5CA",  unitName="CM5CA"),
  |    @PersistenceUnit(name="persistence/CM5EA",  unitName="CM5EA"),
  |    @PersistenceUnit(name="persistence/CM5US",  unitName="CM5US")
  | })
  | public class BaseStatelessSession implements BaseStatelessSessionLocal {
  |    
  |    protected EntityManager entityManager;
  |    
  |    public void getEntityManager(String persistenceUnit) {
  |       
  |       try {
  |          if (entityManager == null) {
  |             InitialContext jndiContext = new InitialContext();
  |             EntityManagerFactory emf = (EntityManagerFactory)jndiContext.lookup("java:comp/env/persistence/" + persistenceUnit);
  |             entityManager = emf.createEntityManager();
  |          }
  |       }
  |       catch (NamingException ne) {
  |         ;;  // Handle this based on your needs
  |       }
  |    }
  | }
  | 


Session facades (TableBeans) wrap entities with CRUD capabilities, nothing more.  These look like:


  | package com.czncorp.as400.tables.blsbl;
  | 
  | import com.czncorp.base.session.BaseStatelessSession;
  | import com.czncorp.as400.tables.svord.LogUtil;
  | 
  | import java.util.List;
  | import java.util.logging.Level;
  | import javax.ejb.Stateless;
  | 
  | 
  | /**
  |  * Facade for entity Blsbl.
  |  * 
  |  * @see com.czncorp.as400.tables.blsbl.Blsbl
  |  * @author MyEclipse Persistence Tools
  |  */
  | @ Stateless
  | 
  | public class BlsblFacade extends BaseStatelessSession implements BlsblFacadeLocal, BlsblFacadeRemote {
  | 
  |    public void save(String persistenceUnit, Blsbl transientInstance) {
  |       LogUtil.log("saving Blsbl instance", Level.INFO, null);
  |       try {
  |          super.getEntityManager(persistenceUnit);  // <<---- make sure there is an Entity Manager
  |          entityManager.persist(transientInstance);
  |          LogUtil.log("save successful", Level.INFO, null);
  |       }
  |       catch (RuntimeException re) {
  |          LogUtil.log("save failed", Level.SEVERE, re);
  |          throw re;
  |       }
  |    }
  | 
  |    public void delete(String persistenceUnit, Blsbl persistentInstance) {
  |       LogUtil.log("deleting Blsbl instance", Level.INFO, null);
  |       try {
  |          super.getEntityManager(persistenceUnit);
  |          entityManager.remove(persistentInstance);
  |          LogUtil.log("delete successful", Level.INFO, null);
  |       }
  |       catch (RuntimeException re) {
  |          LogUtil.log("delete failed", Level.SEVERE, re);
  |          throw re;
  |       }
  |    }
  | 
  |    public Blsbl update(String persistenceUnit, Blsbl detachedInstance) {
  |       LogUtil.log("updating Blsbl instance", Level.INFO, null);
  |       try {
  |          super.getEntityManager(persistenceUnit);
  |          Blsbl result = entityManager.merge(detachedInstance);
  |          LogUtil.log("update successful", Level.INFO, null);
  |          return result;
  |       }
  |       catch (RuntimeException re) {
  |          LogUtil.log("update failed", Level.SEVERE, re);
  |          throw re;
  |       }
  |    }
  | ...
  | ...
  | ...
  | 

Current challenge, and I think it is just a deployment issue I need to work through, is to deploy the TableBeans (stuff above) in it's own EAR.  Other deployable units that implement business logic will subclass the session facades of TableBeans.  Currently I am deploying two separate jars, problem is that the TableBean super class of my application specific session bean, a subclass of BlsblFacade in this case, can't find the Blsbl entity when the subclass calls methods in BlsblFacade.  Of course, everything works fine if the subclasses are deployed in the same jar as TableBeans, so I know I am close.  If that makes any sense, I am not beyond taking your suggestions.

Hope this helps others trying to determine the schema to use at runtime.  Be aware that because you are using an EntityManagerFactory, the PersistenceContext will be "EXTENDED".  I thought I could make it "TRANSACTION" since the container was doing everything, but that did not work for me.

View the original post : http://www.jboss.com/index.html?module=bb&op=viewtopic&p=4095311#4095311

Reply to the post : http://www.jboss.com/index.html?module=bb&op=posting&mode=reply&p=4095311



More information about the jboss-user mailing list