Hi again,
I tinkered around in my code yesterday and I think, I've narrowed down
the problem. Forget about my last mail. I am pretty sure, that the
exception about incompatible classes is just a result of broken
dependencies somewhere in my Maven build. Probably different versions of
libraries used by stand-alone client and deployed JAR.
My main problem ist still the exception about a "wrong return type". I
moved the classes mentioned in my first mail to an Eclipse project and
tried a few things... The basic generic interface stays the same as in
my first mail:
public interface GenericEntity<PK extends Serializable> {
PK getEntityId();
void setEntityId();
}
For the Dummy interface I tried three different implementations, that
should lead to the same results:
(1)
public interface Dummy {
Long getEntityId();
void setEntityId(Long entityId);
}
(2)
public interface Dummy extends GenericEntity<Long> {
}
(3)
public interface Dummy extends GenericEntity<Long> {
Long getEntityId();
void setEntityId(Long entityId);
}
For the implementing class I tried two variations:
public class DummyImpl implements Dummy, Serializable {
private Long entityId; // variation (A)
private long entityId; // variation (B) with auto-boxing
Long getEntityId() { return entityId; }
void setEntityId(Long entityId) {
this.entityId = entityId;
}
}
I then compiled, deployed and executed the code with Java 1.5.0_12 and
Java 1.6.0_02. For variation (A) of the DummyImpl class the results
where rather boring:
*** interface (1) + variation (A), java 1.5 and java 6:
Everything works just fine!
*** interface (2)/(3) + variation (A), java 1.5 and java 6:
The EJB deploys correctly but during execution of the stand-alone client
I receive the known VerifyError because of a "wrong return type in
function" getEntityId(). See my first mail for the complete Stacktrace.
Things get more interesting with variation (B) of the DummyImpl class:
*** interface (1) + variation (B), java 1.5:
The EJB deploys successfully, but during execution of the client I
receive a warning, that getter and setter of the entityId violate some
requirements of OpenJPA. The warning is immediately followed by a NPE in
the enhancement code of OpenJPA. (See attachment trace_1_b.txt)
The warning says, that "Getters must return a single non-computed
field". I guess, that the auto-boxing violates this constraint. If this
is correct, then I would expect the same exception for interfaces (2)
and (3), but:
*** interface (2)/(3) + variation (B), java 1.5:
While executing the stand-alone process, OpenJPA parses the meta-data
successfully and tries to create the tables in the DB. However, he fails
to recognize the type of entityId and tries to create a table with a
primary key of type BLOB. This failes with a ReportingSQLException (see
strack trace in attachment trace_23_b.txt)
The experiments with variation (A) of the implementing class already
showed, that OpenJPA seems to fail due to the generic interface. The
ReportingSQLException in the last two cases further points to an
unrecognized return type of the getEntityId()-function. Reflection on
the DummyImpl-class returns two methods with the name getEntityId:
Serializable getEntityId(); // from GenericEntity
Long getEntityId(); // from either Dummy (1)/(3) or DummyImpl (2)
This is just a wild guess, but could it be, that OpenJPA's reflection
code takes the first appearance of the method and never discovers the
second one?
Regards, Janko
Janko Heilgeist wrote:
> Hi Jarek,
>
> thanks for your help. I just compiled, deployed and tested the modified
> code. The previous VerifyError is now replaced by another exception (see
> surefire-report below), but I guess the problem is the same and it's
> just java 1.5's way of expressing it. Looks like David was right with
> his first guess, that the enhancement changes the SUID of the entity.
>
> I already tried your code with a manually inserted serialVersionUID, but
> the result is identical.
>
> If the enhancement changes the SUID, then I should be able to enhance
> the entities before deployment and have client and appserver use the
> same pre-enhanced jar, correct?
>
> Regards, Janko
>
> -------------------------------------------------------------------------------
> Test set: mypackage.client.DummyTest
> -------------------------------------------------------------------------------
> Tests run: 1, Failures: 0, Errors: 1, Skipped: 0, Time elapsed: 0.143
> sec <<< FAILURE!
> testFoo(mypackage.client.DummyTest) Time elapsed: 0.104 sec <<< ERROR!
> javax.naming.NamingException: Cannot lookup
> '/generic-entity-ejb-1.0/DummyDAO/mypackage.dao.DummyDAORemote'. [Root
> exception is java.rmi.RemoteException: Cannot read the response from the
> server (OEJP/2.0) : org.apache.openejb.client.EJBMetaDataImpl; local
> class incompatible: stream classdesc serialVersionUID =
> -7734383756981201981, local class serialVersionUID =
> 2128092884552388429; nested exception is:
> java.io.InvalidClassException:
> org.apache.openejb.client.EJBMetaDataImpl; local class incompatible:
> stream classdesc serialVersionUID = -7734383756981201981, local class
> serialVersionUID = 2128092884552388429]
> at org.apache.openejb.client.JNDIContext.lookup(JNDIContext.java:205)
> at javax.naming.InitialContext.lookup(InitialContext.java:392)
> at mypackage.client.DummyTest.testFoo(DummyTest.java:26)
> Caused by: java.rmi.RemoteException: Cannot read the response from the
> server (OEJP/2.0) : org.apache.openejb.client.EJBMetaDataImpl; local
> class incompatible: stream classdesc serialVersionUID =
> -7734383756981201981, local class serialVersionUID =
> 2128092884552388429; nested exception is:
> java.io.InvalidClassException:
> org.apache.openejb.client.EJBMetaDataImpl; local class incompatible:
> stream classdesc serialVersionUID = -7734383756981201981, local class
> serialVersionUID = 2128092884552388429
> at org.apache.openejb.client.Client.processRequest(Client.java:197)
> at org.apache.openejb.client.Client.request(Client.java:43)
> at org.apache.openejb.client.JNDIContext.request(JNDIContext.java:74)
> at org.apache.openejb.client.JNDIContext.lookup(JNDIContext.java:199)
> ... 28 more
> Caused by: java.io.InvalidClassException:
> org.apache.openejb.client.EJBMetaDataImpl; local class incompatible:
> stream classdesc serialVersionUID = -7734383756981201981, local class
> serialVersionUID = 2128092884552388429
> at java.io.ObjectStreamClass.initNonProxy(ObjectStreamClass.java:562)
> at
> java.io.ObjectInputStream.readNonProxyDesc(ObjectInputStream.java:1583)
> at java.io.ObjectInputStream.readClassDesc(ObjectInputStream.java:1496)
> at
> java.io.ObjectInputStream.readOrdinaryObject(ObjectInputStream.java:1732)
> at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1329)
> at java.io.ObjectInputStream.readArray(ObjectInputStream.java:1667)
> at java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1323)
> at java.io.ObjectInputStream.readObject(ObjectInputStream.java:351)
> at
> org.apache.openejb.client.JNDIResponse.readExternal(JNDIResponse.java:64)
> at org.apache.openejb.client.Client.processRequest(Client.java:192)
> ... 31 more
>
> -------------------------------------------------------------------------------
>
>
> Jarek Gawor wrote:
>> Janko,
>>
>> Try the attached sample. It's the sample you sent us just cleaned it
>> up a bit. Changed the compiler option to 1.5 and integrated the
>> DummyClient as a test. This deployed and worked fine for me - didn't
>> see any exceptions.
>>
>> Jarek
>>
10415 test-unit TRACE [Thread-36] openjpa.MetaData - Set persistence-capable
superclass of "mypackage.DummyImpl" to "null".
10415 test-unit TRACE [Thread-36] openjpa.MetaData - Resolving metadata for
"[EMAIL PROTECTED]".
10415 test-unit TRACE [Thread-36] openjpa.MetaData - Resolving field
"[EMAIL PROTECTED]".
10415 test-unit TRACE [Thread-36] openjpa.MetaData - Preparing mapping for
"mypackage.DummyImpl".
10415 test-unit TRACE [Thread-36] openjpa.MetaData - Resolving field
"[EMAIL PROTECTED]".
10416 test-unit TRACE [Thread-36] openjpa.MetaData - "entityId" has
mapping strategy "org.apache.openjpa.jdbc.meta.strats.HandlerFieldStrategy".
10416 test-unit TRACE [Thread-36] openjpa.MetaData -
"mypackage.DummyImpl<discriminator>" has mapping strategy "none".
10416 test-unit TRACE [Thread-36] openjpa.MetaData -
"mypackage.DummyImpl<version>" has mapping strategy "none".
10416 test-unit TRACE [Thread-36] openjpa.MetaData - Resolving mapping for
"[EMAIL PROTECTED]".
10416 test-unit TRACE [Thread-36] openjpa.MetaData - "mypackage.DummyImpl"
has mapping strategy "full".
10418 test-unit TRACE [Thread-36] openjpa.Enhance - Enhancing type "class
mypackage.DummyImpl".
10426 test-unit WARN [Thread-36] openjpa.Enhance - [Possible violation of
subclassing contractdetected while processing persistent field
mypackage.DummyImpl.entityId, declared in null. Are you sure you are obeying
the OpenJPA requirements? Details: The getter for field entityId does not obey
OpenJPAs subclassing restrictions. Getters must return a single non-computed
field., Possible violation of subclassing contractdetected while processing
persistent field mypackage.DummyImpl.entityId, declared in null. Are you sure
you are obeying the OpenJPA requirements? Details: The setter for field
entityId does not obey OpenJPAs subclassing restrictions. Setters must assign
the passed-in parameter to a single field in the object.]
09:17:29,457 ERROR [OpenEJB] The bean instances business method encountered a
system exception: null
<1.0.0-r561970-r561970 nonfatal general error>
org.apache.openjpa.persistence.PersistenceException: null
at org.apache.openjpa.enhance.PCEnhancer.run(PCEnhancer.java:468)
at
org.apache.openjpa.enhance.ManagedClassSubclasser.prepareUnenhancedClasses(ManagedClassSubclasser.java:112)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at
sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at
sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at
org.apache.openjpa.kernel.AbstractBrokerFactory.loadPersistentTypes(AbstractBrokerFactory.java:286)
at
org.apache.openjpa.kernel.AbstractBrokerFactory.newBroker(AbstractBrokerFactory.java:196)
at
org.apache.openjpa.kernel.DelegatingBrokerFactory.newBroker(DelegatingBrokerFactory.java:142)
at
org.apache.openjpa.persistence.EntityManagerFactoryImpl.createEntityManager(EntityManagerFactoryImpl.java:190)
at
org.apache.openjpa.persistence.EntityManagerFactoryImpl.createEntityManager(EntityManagerFactoryImpl.java:55)
at
org.apache.geronimo.persistence.CMPEntityManagerTxScoped.createEntityManager(CMPEntityManagerTxScoped.java:74)
at
org.apache.geronimo.persistence.CMPEntityManagerTxScoped.getEntityManager(CMPEntityManagerTxScoped.java:55)
at
org.apache.geronimo.persistence.CMPEntityManagerTxScoped.persist(CMPEntityManagerTxScoped.java:81)
at mypackage.dao.DummyDAO.create(DummyDAO.java:18)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at
sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at
sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at
org.apache.openejb.core.interceptor.ReflectionInvocationContext$Invocation.invoke(ReflectionInvocationContext.java:146)
at
org.apache.openejb.core.interceptor.ReflectionInvocationContext.proceed(ReflectionInvocationContext.java:129)
at
org.apache.openejb.core.interceptor.InterceptorStack.invoke(InterceptorStack.java:67)
at
org.apache.openejb.core.stateless.StatelessContainer._invoke(StatelessContainer.java:203)
at
org.apache.openejb.core.stateless.StatelessContainer.invoke(StatelessContainer.java:165)
at
org.apache.openejb.server.ejbd.EjbRequestHandler.doEjbObject_BUSINESS_METHOD(EjbRequestHandler.java:206)
at
org.apache.openejb.server.ejbd.EjbRequestHandler.processRequest(EjbRequestHandler.java:118)
at
org.apache.openejb.server.ejbd.EjbDaemon.processEjbRequest(EjbDaemon.java:163)
at org.apache.openejb.server.ejbd.EjbDaemon.service(EjbDaemon.java:121)
at org.apache.openejb.server.ejbd.EjbDaemon.service(EjbDaemon.java:83)
at org.apache.openejb.server.ejbd.EjbServer.service(EjbServer.java:60)
at
org.apache.openejb.server.ServiceLogger.service(ServiceLogger.java:75)
at
org.apache.openejb.server.ServiceAccessController.service(ServiceAccessController.java:55)
at org.apache.openejb.server.ServiceDaemon$1.run(ServiceDaemon.java:117)
at java.lang.Thread.run(Thread.java:595)
Caused by: java.lang.NullPointerException
at
org.apache.openjpa.enhance.PCEnhancer.addAttributeTranslation(PCEnhancer.java:638)
at org.apache.openjpa.enhance.PCEnhancer.run(PCEnhancer.java:444)
... 33 more
8971 test-unit TRACE [Thread-32] openjpa.MetaData - Set persistence-capable
superclass of "mypackage.DummyImpl" to "null".
8971 test-unit TRACE [Thread-32] openjpa.MetaData - Resolving metadata for
"[EMAIL PROTECTED]".
8972 test-unit TRACE [Thread-32] openjpa.MetaData - Resolving field "[EMAIL
PROTECTED]".
8972 test-unit TRACE [Thread-32] openjpa.MetaData - Preparing mapping for
"mypackage.DummyImpl".
8972 test-unit TRACE [Thread-32] openjpa.MetaData - Resolving field "[EMAIL
PROTECTED]".
8972 test-unit WARN [Thread-32] openjpa.MetaData - OpenJPA cannot map field
"mypackage.DummyImpl.entityId" efficiently. It is of an unsupported type. The
field value will be serialized to a BLOB by default.
8972 test-unit TRACE [Thread-32] openjpa.MetaData - "entityId" has mapping
strategy "org.apache.openjpa.jdbc.meta.strats.HandlerFieldStrategy".
8972 test-unit TRACE [Thread-32] openjpa.MetaData -
"mypackage.DummyImpl<discriminator>" has mapping strategy "none".
8973 test-unit TRACE [Thread-32] openjpa.MetaData -
"mypackage.DummyImpl<version>" has mapping strategy "none".
8973 test-unit TRACE [Thread-32] openjpa.MetaData - Resolving mapping for
"[EMAIL PROTECTED]".
8973 test-unit TRACE [Thread-32] openjpa.MetaData - "mypackage.DummyImpl"
has mapping strategy "full".
8973 test-unit TRACE [Thread-32] openjpa.jdbc.Schema - Reading table
information for schema name "null", table name "DummyImpl".
8973 test-unit TRACE [Thread-32] openjpa.jdbc.JDBC - <t 19400654, conn
5881721> [0 ms] rollback
8974 test-unit TRACE [Thread-32] openjpa.jdbc.JDBC - <t 19400654, conn
5881721> getColumns: null, null, DUMMYIMPL, null
9008 test-unit TRACE [Thread-32] openjpa.jdbc.Schema - Reading table
information for schema name "null", table name "OPENJPASEQ".
9008 test-unit TRACE [Thread-32] openjpa.jdbc.JDBC - <t 19400654, conn
5881721> [0 ms] rollback
9009 test-unit TRACE [Thread-32] openjpa.jdbc.JDBC - <t 19400654, conn
5881721> getColumns: null, null, OPENJPASEQ, null
9013 test-unit TRACE [Thread-32] openjpa.jdbc.Schema - Reading sequence
information for schema "null", sequence name "null".
9013 test-unit TRACE [Thread-32] openjpa.jdbc.JDBC - <t 19400654, conn
5881721> [0 ms] commit
9013 test-unit TRACE [Thread-32] openjpa.jdbc.JDBC - <t 19400654, conn
5881721> [0 ms] close
9014 test-unit TRACE [Thread-32] openjpa.jdbc.Schema - Reading foreign keys
for schema name "null", table name "DummyImpl".
9014 test-unit TRACE [Thread-32] openjpa.jdbc.Schema - Reading foreign keys
for schema name "null", table name "OPENJPASEQ".
9014 test-unit TRACE [Thread-32] openjpa.jdbc.JDBC - <t 19400654, conn
30538228> [0 ms] commit
9014 test-unit TRACE [Thread-32] openjpa.jdbc.JDBC - <t 19400654, conn
30538228> [0 ms] close
9014 test-unit TRACE [Thread-32] openjpa.jdbc.JDBC - <t 19400654, conn
7411089> [0 ms] rollback
9014 test-unit TRACE [Thread-32] openjpa.jdbc.SQL - <t 19400654, conn
7411089> executing stmnt 4137578 CREATE TABLE DummyImpl (entityId BLOB NOT
NULL, PRIMARY KEY (entityId))
9066 test-unit TRACE [Thread-32] openjpa.jdbc.SQL - <t 19400654, conn
7411089> [52 ms] spent
9066 test-unit TRACE [Thread-32] openjpa.jdbc.JDBC - <t 19400654, conn
7411089> [0 ms] close
09:15:58,960 ERROR [OpenEJB] The bean instances business method encountered a
system exception: Columns of type 'BLOB' may not be used in CREATE INDEX, ORDER
BY, GROUP BY, UNION, INTERSECT, EXCEPT or DISTINCT statements because
comparisons are not supported for that type. {stmnt 4137578 CREATE TABLE
DummyImpl (entityId BLOB NOT NULL, PRIMARY KEY (entityId))} [code=30000,
state=X0X67]
<1.0.0-r561970-r561970 nonfatal general error>
org.apache.openjpa.persistence.PersistenceException: Columns of type 'BLOB' may
not be used in CREATE INDEX, ORDER BY, GROUP BY, UNION, INTERSECT, EXCEPT or
DISTINCT statements because comparisons are not supported for that type. {stmnt
4137578 CREATE TABLE DummyImpl (entityId BLOB NOT NULL, PRIMARY KEY
(entityId))} [code=30000, state=X0X67]
at org.apache.openjpa.jdbc.meta.MappingTool.record(MappingTool.java:549)
at org.apache.openjpa.jdbc.meta.MappingTool.record(MappingTool.java:449)
at
org.apache.openjpa.jdbc.kernel.JDBCBrokerFactory.synchronizeMappings(JDBCBrokerFactory.java:170)
at
org.apache.openjpa.jdbc.kernel.JDBCBrokerFactory.newBrokerImpl(JDBCBrokerFactory.java:130)
at
org.apache.openjpa.kernel.AbstractBrokerFactory.newBroker(AbstractBrokerFactory.java:185)
at
org.apache.openjpa.kernel.DelegatingBrokerFactory.newBroker(DelegatingBrokerFactory.java:142)
at
org.apache.openjpa.persistence.EntityManagerFactoryImpl.createEntityManager(EntityManagerFactoryImpl.java:190)
at
org.apache.openjpa.persistence.EntityManagerFactoryImpl.createEntityManager(EntityManagerFactoryImpl.java:55)
at
org.apache.geronimo.persistence.CMPEntityManagerTxScoped.createEntityManager(CMPEntityManagerTxScoped.java:74)
at
org.apache.geronimo.persistence.CMPEntityManagerTxScoped.getEntityManager(CMPEntityManagerTxScoped.java:55)
at
org.apache.geronimo.persistence.CMPEntityManagerTxScoped.persist(CMPEntityManagerTxScoped.java:81)
at mypackage.dao.DummyDAO.create(DummyDAO.java:18)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at
sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at
sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:585)
at
org.apache.openejb.core.interceptor.ReflectionInvocationContext$Invocation.invoke(ReflectionInvocationContext.java:146)
at
org.apache.openejb.core.interceptor.ReflectionInvocationContext.proceed(ReflectionInvocationContext.java:129)
at
org.apache.openejb.core.interceptor.InterceptorStack.invoke(InterceptorStack.java:67)
at
org.apache.openejb.core.stateless.StatelessContainer._invoke(StatelessContainer.java:203)
at
org.apache.openejb.core.stateless.StatelessContainer.invoke(StatelessContainer.java:165)
at
org.apache.openejb.server.ejbd.EjbRequestHandler.doEjbObject_BUSINESS_METHOD(EjbRequestHandler.java:206)
at
org.apache.openejb.server.ejbd.EjbRequestHandler.processRequest(EjbRequestHandler.java:118)
at
org.apache.openejb.server.ejbd.EjbDaemon.processEjbRequest(EjbDaemon.java:163)
at org.apache.openejb.server.ejbd.EjbDaemon.service(EjbDaemon.java:121)
at org.apache.openejb.server.ejbd.EjbDaemon.service(EjbDaemon.java:83)
at org.apache.openejb.server.ejbd.EjbServer.service(EjbServer.java:60)
at
org.apache.openejb.server.ServiceLogger.service(ServiceLogger.java:75)
at
org.apache.openejb.server.ServiceAccessController.service(ServiceAccessController.java:55)
at org.apache.openejb.server.ServiceDaemon$1.run(ServiceDaemon.java:117)
at java.lang.Thread.run(Thread.java:595)
Caused by: org.apache.openjpa.lib.jdbc.ReportingSQLException: Columns of type
'BLOB' may not be used in CREATE INDEX, ORDER BY, GROUP BY, UNION, INTERSECT,
EXCEPT or DISTINCT statements because comparisons are not supported for that
type. {stmnt 4137578 CREATE TABLE DummyImpl (entityId BLOB NOT NULL, PRIMARY
KEY (entityId))} [code=30000, state=X0X67]
at
org.apache.openjpa.lib.jdbc.LoggingConnectionDecorator.wrap(LoggingConnectionDecorator.java:192)
at
org.apache.openjpa.lib.jdbc.LoggingConnectionDecorator.access$800(LoggingConnectionDecorator.java:57)
at
org.apache.openjpa.lib.jdbc.LoggingConnectionDecorator$LoggingConnection$LoggingStatement.executeUpdate(LoggingConnectionDecorator.java:754)
at
org.apache.openjpa.lib.jdbc.DelegatingStatement.executeUpdate(DelegatingStatement.java:114)
at
org.apache.openjpa.jdbc.schema.SchemaTool.executeSQL(SchemaTool.java:1185)
at
org.apache.openjpa.jdbc.schema.SchemaTool.createTable(SchemaTool.java:949)
at org.apache.openjpa.jdbc.schema.SchemaTool.add(SchemaTool.java:526)
at org.apache.openjpa.jdbc.schema.SchemaTool.add(SchemaTool.java:344)
at org.apache.openjpa.jdbc.schema.SchemaTool.run(SchemaTool.java:321)
at org.apache.openjpa.jdbc.meta.MappingTool.record(MappingTool.java:497)
... 30 more