Re: JPA enhancer behavior - fat agent?

From: Dain Sundstrom (dai..q80.com)
Date: Thu Feb 22 2007 - 12:46:22 EST

  • Next message: Kevin Menard: "RE: podling BIS notifications (jars in svn & crypto)"

    Sorry, got busy and missed this email.

    This is such a common problem, it was addressed directly by the JPA
    specs. When loading classes for inspection use the class loader
    returned from
    javax.persistence.spi.PersistenceUnitInfo.getNewTempClassLoader().

    For Cayenne's own PersistenceUnitInfo implementation, I suggest you
    copy org.apache.openejb.core.TemporaryClassLoader which I copied from
    OpenJPA and cleaned up.

    -dain

    On Feb 20, 2007, at 4:31 AM, Andrus Adamchik wrote:

    > Dain Sundstrom (who is a member of Geronimo project) did some
    > preliminary testing of Cayenne JPA provider in the OpenEJB
    > container last week - you've seen some jiras that he opened. I am
    > taking further discussion to the list (not sure if Dain is
    > subscribed, so I am cc'ying to him as well).
    >
    > So the enhancer... I tried to run the OpenEJB JpaTest [1] with
    > Cayenne provider. It fails to enhance the Employee object [2], even
    > if it is explicitly mentioned in the PersistenceUnit, because it
    > was loaded in the JVM *before* Cayenne provider was started and
    > Provider.createContainerEntityManagerFactory(..) was called.
    >
    > I was trying to think of ways to "fix" it, but considering that
    > java.lang.instrument.Instrumentation doesn't allow to enhance
    > already loaded classes ("redefineClasses" method places serious
    > limitations on what can be done, namely adding new fields is not
    > allowed), looks like JPA users will have to deal with specific
    > startup order requirements. In-container and Java SE operation
    > modes will look different:
    >
    > 1. In-container: provider shouldn't directly access its own agent,
    > and simply register a needed ClassTransformer with container-
    > provided PersistenceUnitInfo. Container on the other hand has the
    > responsibility to hook up PersistenceUnitInfo implementor to the
    > agent, and ensure that provider is started *before* and persistence
    > classes are loaded in the app class loader. So I wonder whether the
    > fact that JpaTest worked with OpenJPA provider by some coincidence?
    >
    > 2. Standalone: for the enhancer to work, an application must ensure
    > a call to Persistence.createEntityManagerFactory() prior to the
    > entity classes loaded in runtime. This sucks, and the only way
    > around is to run enhancer straight from the agent. I think that's
    > what OpenJPA does. Some time ago we decided [3] to avoid putting
    > any Cayenne runtime classes in the agent, but it looks like we
    > don't have a choice. Unless somebody can suggest a better way of
    > providing reliable runtime enhancement, I will change the behavior
    > to provide a "fat" agent.
    >
    > [1] https://svn.apache.org/repos/asf/incubator/openejb/trunk/
    > openejb3/container/openejb-core/src/test/java/org/apache/openejb/
    > core/cmp/jpa/JpaTest.java
    > [2] https://svn.apache.org/repos/asf/incubator/openejb/trunk/
    > openejb3/container/openejb-core/src/test/java/org/apache/openejb/
    > core/cmp/jpa/Employee.java
    > [3] http://objectstyle.org/cayenne/lists/cayenne-devel/
    > 2006/08/0088.html
    >
    > Andrus
    >
    > P.S. Dain - are there any other show stopper issues in your testing
    > (except for no EJBQL)?



    This archive was generated by hypermail 2.0.0 : Thu Feb 22 2007 - 12:47:31 EST