savvas.andreas (4) [Avatar] Offline
#1
Hi there,

I have been following the examples in your very interesting book and have come across an issue I'd like to flag.

Following through the examples in the book I created in my environment locally all the necessary classes and tried running my first Arquillian test but this raised a NullPointerException. The problem was somewhere on the Arquillian side as my breakpoint in my test class was never hit when running in debug mode.

After spending a few hours I realised that this was due to the fact that the datasets file couldn't be parsed properly..and this was due to the fact that I had added a @Column annotation in one of my classes similar to the below:
@Min(1900)
@Column(name = "released_year")
private int releasedYear;


however, this column in the datasets file had been left to:

<movie id="1" title="Star Trek - First Contact" releasedYear="1996" director="Jonathan Frakes" optimistic_lock="1" />


which was causing Arquillian to throw a NullPointerException without any further explanation of what exactly was the problem (or even a hint it was an incorrect line in the datasets file).

This might be a good point to mention in your book so that future readers who may decide to modify slightly the examples code are aware of this.

Also, it might be worth raising this with the Arquillian team so that the exception that gets thrown in cases of an un-parseable datasets file is either more specialised or contains a more helpful message.


Finally, somewhere in the first chapters you warn your readers to avoid using the standard java-ee api dependencies due to:

The latter artifact contains classes with stripped method bodies,
which will cause your application to throw obscure Absent Code errors if present on the
classpath at runtime (even when running tests).


but I can confirm that using the following dependency:

<dependency>
    <groupId>javax</groupId>
    <artifactId>javaee-api</artifactId>
    <version>7.0</version>
    <scope>provided</scope>
</dependency>


doesn't throw (at least it hasn't so far) any exceptions.

I hope that helps,
Savvas
Jason Porter (18) [Avatar] Offline
#2
savvas.andreas wrote:Hi there,

I have been following the examples in your very interesting book and have come across an issue I'd like to flag.


Thanks so much for the interest! We appreciate it, and help us spread the word as well smilie

savvas.andreas wrote:
Following through the examples in the book I created in my environment locally all the necessary classes and tried running my first Arquillian test but this raised a NullPointerException. The problem was somewhere on the Arquillian side as my breakpoint in my test class was never hit when running in debug mode.


Do you have the full stack trace?

savvas.andreas wrote:After spending a few hours I realised that this was due to the fact that the datasets file couldn't be parsed properly..and this was due to the fact that I had added a @Column annotation in one of my classes similar to the below:
@Min(1900)
@Column(name = "released_year")
private int releasedYear;


however, this column in the datasets file had been left to:

<movie id="1" title="Star Trek - First Contact" releasedYear="1996" director="Jonathan Frakes" optimistic_lock="1" />


which was causing Arquillian to throw a NullPointerException without any further explanation of what exactly was the problem (or even a hint it was an incorrect line in the datasets file).

This might be a good point to mention in your book so that future readers who may decide to modify slightly the examples code are aware of this.

Also, it might be worth raising this with the Arquillian team so that the exception that gets thrown in cases of an un-parseable datasets file is either more specialised or contains a more helpful message.


Thanks for the heads up. We'll have to investigate where this exception is being swallowed. My guess is that dbunit is actually throwing the exception, but Arquillian is eating it and instead proceeding with the test, but something is null, again, a full stack trace would be very helpful.

savvas.andreas wrote:Finally, somewhere in the first chapters you warn your readers to avoid using the standard java-ee api dependencies due to:

The latter artifact contains classes with stripped method bodies,
which will cause your application to throw obscure Absent Code errors if present on the
classpath at runtime (even when running tests).


but I can confirm that using the following dependency:

<dependency>
    <groupId>javax</groupId>
    <artifactId>javaee-api</artifactId>
    <version>7.0</version>
    <scope>provided</scope>
</dependency>


doesn't throw (at least it hasn't so far) any exceptions.

I hope that helps,
Savvas


This was the case with the Java EE 6 artifacts from Oracle, but I believe has since been corrected. The artifacts from Apache and Red Hat / JBoss are good to use. As you also pointed out the Java EE 7 artifacts are fixed.

If you want the background behind this, the original Java EE 6 jars had been manipulated via bytecode manipulation after being compiled and having method bodies pulled out in a way which broken compilation against the jars. They worked fine in the IDE for code completion, but when you actually ran the code things broke.

We're still trying to decide if we use Java EE 7 in the book or Java EE 6. Do you have strong feelings one way or the other?
savvas.andreas (4) [Avatar] Offline
#3
Hi Jason,

Thanks for the quick reply.

Do you have the full stack trace?


Yup, here you go... smilie

java.lang.NullPointerException
	at org.jboss.arquillian.transaction.impl.lifecycle.TransactionHandler.testRequiresRollbackDueToFailure(TransactionHandler.java:170)
	at org.jboss.arquillian.transaction.impl.lifecycle.TransactionHandler.rollbackRequired(TransactionHandler.java:159)
	at org.jboss.arquillian.transaction.impl.lifecycle.TransactionHandler.endTransaction(TransactionHandler.java:123)
	at org.jboss.arquillian.transaction.impl.lifecycle.TransactionHandler.endTransactionAfterTest(TransactionHandler.java:102)
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:497)
	at org.jboss.arquillian.core.impl.ObserverImpl.invoke(ObserverImpl.java:94)
	at org.jboss.arquillian.core.impl.EventContextImpl.proceed(EventContextImpl.java:88)
	at org.jboss.arquillian.testenricher.cdi.CreationalContextDestroyer.destory(CreationalContextDestroyer.java:44)
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:497)
	at org.jboss.arquillian.core.impl.ObserverImpl.invoke(ObserverImpl.java:94)
	at org.jboss.arquillian.core.impl.EventContextImpl.proceed(EventContextImpl.java:88)
	at org.jboss.arquillian.test.impl.TestContextHandler.createTestContext(TestContextHandler.java:130)
	at sun.reflect.GeneratedMethodAccessor57.invoke(Unknown Source)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:497)
	at org.jboss.arquillian.core.impl.ObserverImpl.invoke(ObserverImpl.java:94)
	at org.jboss.arquillian.core.impl.EventContextImpl.proceed(EventContextImpl.java:88)
	at org.jboss.arquillian.test.impl.TestContextHandler.createClassContext(TestContextHandler.java:92)
	at sun.reflect.GeneratedMethodAccessor56.invoke(Unknown Source)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:497)
	at org.jboss.arquillian.core.impl.ObserverImpl.invoke(ObserverImpl.java:94)
	at org.jboss.arquillian.core.impl.EventContextImpl.proceed(EventContextImpl.java:88)
	at org.jboss.arquillian.test.impl.TestContextHandler.createSuiteContext(TestContextHandler.java:73)
	at sun.reflect.GeneratedMethodAccessor55.invoke(Unknown Source)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:497)
	at org.jboss.arquillian.core.impl.ObserverImpl.invoke(ObserverImpl.java:94)
	at org.jboss.arquillian.core.impl.EventContextImpl.proceed(EventContextImpl.java:88)
	at org.jboss.arquillian.core.impl.ManagerImpl.fire(ManagerImpl.java:145)
	at org.jboss.arquillian.core.impl.ManagerImpl.fire(ManagerImpl.java:116)
	at org.jboss.arquillian.test.impl.EventTestRunnerAdaptor.after(EventTestRunnerAdaptor.java:122)
	at org.jboss.arquillian.junit.Arquillian$5$1.evaluate(Arquillian.java:264)
	at org.jboss.arquillian.junit.Arquillian.multiExecute(Arquillian.java:422)
	at org.jboss.arquillian.junit.Arquillian.access$200(Arquillian.java:54)
	at org.jboss.arquillian.junit.Arquillian$5.evaluate(Arquillian.java:259)
	at org.jboss.arquillian.junit.Arquillian$7$1.invoke(Arquillian.java:315)
	at org.jboss.arquillian.container.test.impl.execution.BeforeLifecycleEventExecuter.on(BeforeLifecycleEventExecuter.java:35)
	at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:497)
	at org.jboss.arquillian.core.impl.ObserverImpl.invoke(ObserverImpl.java:94)
	at org.jboss.arquillian.core.impl.EventContextImpl.invokeObservers(EventContextImpl.java:99)
	at org.jboss.arquillian.core.impl.EventContextImpl.proceed(EventContextImpl.java:81)
	at org.jboss.arquillian.test.impl.TestContextHandler.createTestContext(TestContextHandler.java:130)
	at sun.reflect.GeneratedMethodAccessor57.invoke(Unknown Source)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:497)
	at org.jboss.arquillian.core.impl.ObserverImpl.invoke(ObserverImpl.java:94)
	at org.jboss.arquillian.core.impl.EventContextImpl.proceed(EventContextImpl.java:88)
	at org.jboss.arquillian.test.impl.TestContextHandler.createClassContext(TestContextHandler.java:92)
	at sun.reflect.GeneratedMethodAccessor56.invoke(Unknown Source)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:497)
	at org.jboss.arquillian.core.impl.ObserverImpl.invoke(ObserverImpl.java:94)
	at org.jboss.arquillian.core.impl.EventContextImpl.proceed(EventContextImpl.java:88)
	at org.jboss.arquillian.test.impl.TestContextHandler.createSuiteContext(TestContextHandler.java:73)
	at sun.reflect.GeneratedMethodAccessor55.invoke(Unknown Source)
	at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.lang.reflect.Method.invoke(Method.java:497)
	at org.jboss.arquillian.core.impl.ObserverImpl.invoke(ObserverImpl.java:94)
	at org.jboss.arquillian.core.impl.EventContextImpl.proceed(EventContextImpl.java:88)
	at org.jboss.arquillian.core.impl.ManagerImpl.fire(ManagerImpl.java:145)
	at org.jboss.arquillian.core.impl.ManagerImpl.fire(ManagerImpl.java:116)
	at org.jboss.arquillian.test.impl.EventTestRunnerAdaptor.fireCustomLifecycle(EventTestRunnerAdaptor.java:159)
	at org.jboss.arquillian.junit.Arquillian$7.evaluate(Arquillian.java:311)
	at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
	at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
	at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
	at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
	at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
	at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
	at org.jboss.arquillian.junit.Arquillian$2.evaluate(Arquillian.java:204)
	at org.jboss.arquillian.junit.Arquillian.multiExecute(Arquillian.java:422)
	at org.jboss.arquillian.junit.Arquillian.access$200(Arquillian.java:54)
	at org.jboss.arquillian.junit.Arquillian$3.evaluate(Arquillian.java:218)
	at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
	at org.jboss.arquillian.junit.Arquillian.run(Arquillian.java:166)
	at org.junit.runner.JUnitCore.run(JUnitCore.java:137)
	at org.junit.runner.JUnitCore.run(JUnitCore.java:115)
	at org.jboss.arquillian.junit.container.JUnitTestRunner.execute(JUnitTestRunner.java:66)
	at org.jboss.arquillian.protocol.servlet.runner.ServletTestRunner.executeTest(ServletTestRunner.java:159)
	at org.jboss.arquillian.protocol.servlet.runner.ServletTestRunner.execute(ServletTestRunner.java:125)
	at org.jboss.arquillian.protocol.servlet.runner.ServletTestRunner.doGet(ServletTestRunner.java:89)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:687)
	at javax.servlet.http.HttpServlet.service(HttpServlet.java:790)
	at org.apache.catalina.core.StandardWrapper.service(StandardWrapper.java:1682)
	at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:318)
	at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:160)
	at org.apache.catalina.core.StandardPipeline.doInvoke(StandardPipeline.java:734)
	at org.apache.catalina.core.StandardPipeline.invoke(StandardPipeline.java:673)
	at com.sun.enterprise.web.WebPipeline.invoke(WebPipeline.java:99)
	at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:174)
	at org.apache.catalina.connector.CoyoteAdapter.doService(CoyoteAdapter.java:415)
	at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:282)
	at com.sun.enterprise.v3.services.impl.ContainerMapper$HttpHandlerCallable.call(ContainerMapper.java:459)
	at com.sun.enterprise.v3.services.impl.ContainerMapper.service(ContainerMapper.java:167)
	at org.glassfish.grizzly.http.server.HttpHandler.runService(HttpHandler.java:201)
	at org.glassfish.grizzly.http.server.HttpHandler.doHandle(HttpHandler.java:175)
	at org.glassfish.grizzly.http.server.HttpServerFilter.handleRead(HttpServerFilter.java:235)
	at org.glassfish.grizzly.filterchain.ExecutorResolver$9.execute(ExecutorResolver.java:119)
	at org.glassfish.grizzly.filterchain.DefaultFilterChain.executeFilter(DefaultFilterChain.java:284)
	at org.glassfish.grizzly.filterchain.DefaultFilterChain.executeChainPart(DefaultFilterChain.java:201)
	at org.glassfish.grizzly.filterchain.DefaultFilterChain.execute(DefaultFilterChain.java:133)
	at org.glassfish.grizzly.filterchain.DefaultFilterChain.process(DefaultFilterChain.java:112)
	at org.glassfish.grizzly.ProcessorExecutor.execute(ProcessorExecutor.java:77)
	at org.glassfish.grizzly.nio.transport.TCPNIOTransport.fireIOEvent(TCPNIOTransport.java:561)
	at org.glassfish.grizzly.strategies.AbstractIOStrategy.fireIOEvent(AbstractIOStrategy.java:112)
	at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy.run0(WorkerThreadIOStrategy.java:117)
	at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy.access$100(WorkerThreadIOStrategy.java:56)
	at org.glassfish.grizzly.strategies.WorkerThreadIOStrategy$WorkerThreadRunnable.run(WorkerThreadIOStrategy.java:137)
	at org.glassfish.grizzly.threadpool.AbstractThreadPool$Worker.doWork(AbstractThreadPool.java:565)
	at org.glassfish.grizzly.threadpool.AbstractThreadPool$Worker.run(AbstractThreadPool.java:545)
	at java.lang.Thread.run(Thread.java:745)


This was the case with the Java EE 6 artifacts from Oracle, but I believe has since been corrected. The artifacts from Apache and Red Hat / JBoss are good to use. As you also pointed out the Java EE 7 artifacts are fixed.

If you want the background behind this, the original Java EE 6 jars had been manipulated via bytecode manipulation after being compiled and having method bodies pulled out in a way which broken compilation against the jars. They worked fine in the IDE for code completion, but when you actually ran the code things broke.

We're still trying to decide if we use Java EE 7 in the book or Java EE 6. Do you have strong feelings one way or the other?


Cool, thanks for that. As long as I can have access to all JSR APIs with a single "provided" maven dependency (one that doesn't throw exceptions that is) I don't really mind to honest...however, the EE 7 version would probably be a lot more preferable since it would include all the latest features.

Thanks,
Savvas