tomee-users mailing list archives

Site index · List index
Message view « Date » · « Thread »
Top « Date » · « Thread »
From David Blevins <david.blev...@visi.com>
Subject Re: Obtaining EntityManager programatically for test purposes
Date Sat, 21 Feb 2009 20:00:01 GMT

On Feb 17, 2009, at 7:44 AM, <Thomas.TH.Hamacher@partner.bmw.ch> <Thomas.TH.Hamacher@partner.bmw.ch

 > wrote:

> Do I have any chance to get the hashcode as well?
>
> I could do the workaround to ignore the id and imply that the  
> persistence-unit is unique, but it would even be cleaner, if I would  
> look for the exact jndi-name.
>
> But as I do this programatically I currently never know the id  
> exactly.

There's no convenient way to get the hashcode.

> Just another question how to proceed further: I know I can create a  
> new EntityManager from the EntityManagerFactory, but is this the way  
> I should go here?
>
> Will this be the entityManager which is also injected into the other  
> SessionBeans by openEJB or will it be another one?
>
> The reason I am asking is, that I also use an EntityManager in my  
> Services, which I call within my tests. So wouldn´t it cause some  
> troubles if I work with different EntityManagers?

That's really the big question.  I'm not exactly sure how your tests  
are written, but it would be fine to use them both as long as it was  
understood they are two completely different Persistence Contexts  
(i.e. caches).  This is pretty much how things will look at runtime  
anyway -- i.e. multiple threads and transactions each with it's own  
persistence context.  If you don't attempt to use them together in the  
same transaction and you don't attempt to create two transactions in  
the same thread simultaneously, it should be fine.

The bigger thing will be to respect the mode in which the persistence  
unit in question is meant to work.  If it is a RESOURCE_LOCAL unit,  
you'll want to use the EntityTransaction API to transactionally demark  
you work with the created EntityManager.  If it is a JTA (the default)  
persistence unit, you'll want begin/commit transactions via either a  
UserTransaction or the TransactionManager directly when you work with  
the EntityManager.


-David



>
>
>
>
> Thanks a lot
>
>
>
> Thomas
>
>
>
>
>
>
>
>
>
>
>
> Hi Thomas,
>
>
>
> We actually do have something similar internally, but the trick is  
> that persistence unit names are not required to be unique outside  
> the persistence.xml file (i.e. it's legal to have multiple  
> persistence.xml files in various modules in your app all with the  
> same name despite that they are different persistence units). So  
> currently we generate an id for the persistence.xml file itself and  
> tack that on to the end of the persistence unit name before  
> registering it in JNDI. The format is:
>
> "java:openejb/PersistenceUnit/" + unitName + " " + id
>
>
>
> The id is a hashCode we generate to identify the exact  
> persistence.xml file.
>
> This is more for our purposes internally, but it is possible to get  
> a list of them outside an EJB or Servlet. Inside a Servlet or EJB  
> you don't currently have access to java:openejb though we plan to  
> add that.
>
> Here's a small example:
>
> The persistence.xml file
>
>
>
> <persistence xmlns="http://java.sun.com/xml/ns/persistence"<http://java.sun.com/xml/ns/persistence%22

> >; version="1.0">
>
>    <persistence-unit name="orange-unit">
>      <jta-data-source>Orange</jta-data-source>
>      <non-jta-data-source>OrangeUnmanagedamanged</non-jta-data-source>
>    </persistence-unit>
>    <persistence-unit name="lime-unit">
>      <jta-data-source>Lime</jta-data-source>
>      <non-jta-data-source>LimeUnmanagedamanged</non-jta-data-source>
>    </persistence-unit>
>  </persistence>
>
> If you executed code like this in your test case:
>
>    // Do not pass in LocalInitialContextFactory
>    Context context = new InitialContext();
>
>    context = (Context) context.lookup("java:openejb/PersistenceUnit");
>
>    Map<String,Object> map = Debug.contextToMap(context);
>    for (String key : map.keySet()) {
>        System.out.println(key);
>    }
>
> You see this in the output:
>
>   "lime-unit 3506402"
>   "orange-unit 3506402"
>
>
>
> Looking up these will give you the internal EntityManagerFactory we  
> use to create the various EntityManager instances at runtime (i.e.  
> transaction start for TRANSACTION scope or stateful session bean  
> creation for EXTENDED scope).
>
> Note the "Debug.contextToMap" call is just you standard iterate over  
> JNDI code. Here it is if you want it:
>
> public static Map<String,Object> contextToMap(Context context)  
> throws NamingException { Map<String, Object> map = new  
> TreeMap<String, Object>(String.CASE_INSENSITIVE_ORDER);
>
>        contextToMap(context, "", map);
>        return map;
>    }
>
>
>
> public static void contextToMap(Context context, String baseName,  
> Map<String,Object> results) throws NamingException  
> { NamingEnumeration<Binding> namingEnumeration =  
> context.listBindings("");
>
>        while (namingEnumeration.hasMoreElements()) {
>            Binding binding = namingEnumeration.nextElement();
>            String name = binding.getName();
>            String fullName = baseName + name;
>            Object object = binding.getObject();
>            results.put(fullName, object);
>            if (object instanceof Context) {
>
>
> contextToMap((Context) object, fullName + "/", results);
>
>            }
>        }
>    }
>
>
>
> Further note to future readers who might want to iterate over the  
> entire java:openejb tree. Caution should be used with the  
> java:openejb/ejb/, java:openejb/Deployment/, and java:openejb/ 
> client/ sections of the tree as they will contain any Stateful  
> session bean's you have in your platform and calling  
> "binding.getObject()" on those will cause stateful session bean  
> instances to be created.
>
> In terms of future functionality, we would like to provide an  
> alternate JNDI view of the persistence units that doesn't involve  
> the unique ID and simply is "unit name".
>
> -David
>
>
>
>


Mime
View raw message