prashant-ramcharan / courgette-jvm

Multiprocess | Parallel Cucumber-JVM | Parallelize your Java Cucumber tests on a feature level or on a scenario level.
MIT License
132 stars 38 forks source link

NoSuchElementException when running in UNIX (5.9.0 and 5.8.0) #245

Closed pagmoro closed 3 years ago

pagmoro commented 3 years ago

Hi @prashant-ramcharan

We're getting the following Exception when running courgette-jvm Runner in one of our UNIX boxes. (Jenkins on UNIX server is fine). So, it possible something specific to the box ( for e.g , this box has a non-executable /tmp directory)

Any ideas on what could be the issue? (Stack trace below)

java.io.IOException: Cannot run program "java": error=2, No such file or directory
at java.lang.ProcessBuilder.start(ProcessBuilder.java:1048)
at courgette.runtime.CourgetteFeatureRunner.run(CourgetteFeatureRunner.java:25)
at courgette.runtime.CourgetteRunner.runFeature(CourgetteRunner.java:252)
at courgette.runtime.CourgetteRunner.lambda$run$3(CourgetteRunner.java:75)
at courgette.runtime.CourgetteRunner$$Lambda$220/1349500563.call(Unknown Source)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
Caused by: java.io.IOException: error=2, No such file or directory
at java.lang.UNIXProcess.forkAndExec(Native Method)
at java.lang.UNIXProcess.<init>(UNIXProcess.java:248)
at java.lang.ProcessImpl.start(ProcessImpl.java:134)
at java.lang.ProcessBuilder.start(ProcessBuilder.java:1029)
... 8 more
java.io.IOException: Cannot run program "java": error=2, No such file or directory
at java.lang.ProcessBuilder.start(ProcessBuilder.java:1048)
at courgette.runtime.CourgetteFeatureRunner.run(CourgetteFeatureRunner.java:25)
at courgette.runtime.CourgetteRunner.runFeature(CourgetteRunner.java:252)
at courgette.runtime.CourgetteRunner.lambda$run$3(CourgetteRunner.java:75)
at courgette.runtime.CourgetteRunner$$Lambda$220/1349500563.call(Unknown Source)
at java.util.concurrent.FutureTask.run(FutureTask.java:266)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at java.lang.Thread.run(Thread.java:745)
Caused by: java.io.IOException: error=2, No such file or directory
at java.lang.UNIXProcess.forkAndExec(Native Method)
at java.lang.UNIXProcess.<init>(UNIXProcess.java:248)
at java.lang.ProcessImpl.start(ProcessImpl.java:134)
at java.lang.ProcessBuilder.start(ProcessBuilder.java:1029)
... 8 more 

No value present
java.util.NoSuchElementException: No value present

at java.util.Optional.get(Optional.java:135)
at courgette.runtime.CourgetteNdJsonCreator.createTestRunStarted(CourgetteNdJsonCreator.java:199)
at courgette.runtime.CourgetteNdJsonCreator.mutateMessages(CourgetteNdJsonCreator.java:92)
at courgette.runtime.CourgetteNdJsonCreator.getScenarioMessages(CourgetteNdJsonCreator.java:88)
at courgette.runtime.CourgetteNdJsonCreator.createScenarioMessages(CourgetteNdJsonCreator.java:55)
at courgette.runtime.CourgetteReporter.createMessages(CourgetteReporter.java:123)
at courgette.runtime.CourgetteReporter.<init>(CourgetteReporter.java:33)
at courgette.runtime.CourgetteRunner.createCucumberReport(CourgetteRunner.java:166)
at courgette.api.junit.Courgette.run(Courgette.java:53)
at org.junit.runner.JUnitCore.run(JUnitCore.java:137)
at org.junit.runner.JUnitCore.run(JUnitCore.java:115)
at org.junit.vintage.engine.execution.RunnerExecutor.execute(RunnerExecutor.java:43)
at org.junit.vintage.engine.VintageTestEngine$$Lambda$203/890057964.accept(Unknown Source)
at java.util.stream.ForEachOps$ForEachOp$OfRef.accept(ForEachOps.java:184)
at java.util.stream.ReferencePipeline$3$1.accept(ReferencePipeline.java:193)
at java.util.Iterator.forEachRemaining(Iterator.java:116)
at java.util.Spliterators$IteratorSpliterator.forEachRemaining(Spliterators.java:1801)
at java.util.stream.AbstractPipeline.copyInto(AbstractPipeline.java:512)
at java.util.stream.AbstractPipeline.wrapAndCopyInto(AbstractPipeline.java:502)
at java.util.stream.ForEachOps$ForEachOp.evaluateSequential(ForEachOps.java:151)
at java.util.stream.ForEachOps$ForEachOp$OfRef.evaluateSequential(ForEachOps.java:174)
at java.util.stream.AbstractPipeline.evaluate(AbstractPipeline.java:234)
at java.util.stream.ReferencePipeline.forEach(ReferencePipeline.java:418)
at org.junit.vintage.engine.VintageTestEngine.executeAllChildren(VintageTestEngine.java:82)
at org.junit.vintage.engine.VintageTestEngine.execute(VintageTestEngine.java:73)
at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:220)
at org.junit.platform.launcher.core.DefaultLauncher.lambda$execute$6(DefaultLauncher.java:188)
at org.junit.platform.launcher.core.DefaultLauncher$$Lambda$187/1657477687.accept(Unknown Source)
at org.junit.platform.launcher.core.DefaultLauncher.withInterceptedStreams(DefaultLauncher.java:202)
at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:181)
at org.junit.platform.launcher.core.DefaultLauncher.execute(DefaultLauncher.java:128)
at org.gradle.api.internal.tasks.testing.junitplatform.JUnitPlatformTestClassProcessor$CollectAllTestClassesExecutor.processAllTestClasses(JUnitPlatformTestClassProcessor.java:102)
at org.gradle.api.internal.tasks.testing.junitplatform.JUnitPlatformTestClassProcessor$CollectAllTestClassesExecutor.access$000(JUnitPlatformTestClassProcessor.java:82)
at org.gradle.api.internal.tasks.testing.junitplatform.JUnitPlatformTestClassProcessor.stop(JUnitPlatformTestClassProcessor.java:78)
at org.gradle.api.internal.tasks.testing.SuiteTestClassProcessor.stop(SuiteTestClassProcessor.java:61)
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.gradle.internal.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:36)
at org.gradle.internal.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:24)
at org.gradle.internal.dispatch.ContextClassLoaderDispatch.dispatch(ContextClassLoaderDispatch.java:33)
at org.gradle.internal.dispatch.ProxyDispatchAdapter$DispatchingInvocationHandler.invoke(ProxyDispatchAdapter.java:94)
at com.sun.proxy.$Proxy2.stop(Unknown Source)
at org.gradle.api.internal.tasks.testing.worker.TestWorker.stop(TestWorker.java:132)
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.gradle.internal.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:36)
at org.gradle.internal.dispatch.ReflectionDispatch.dispatch(ReflectionDispatch.java:24)
at org.gradle.internal.remote.internal.hub.MessageHubBackedObjectConnection$DispatchWrapper.dispatch(MessageHubBackedObjectConnection.java:182)
at org.gradle.internal.remote.internal.hub.MessageHubBackedObjectConnection$DispatchWrapper.dispatch(MessageHubBackedObjectConnection.java:164)
at org.gradle.internal.remote.internal.hub.MessageHub$Handler.run(MessageHub.java:412)
at org.gradle.internal.concurrent.ExecutorPolicy$CatchAndRecordFailures.onExecute(ExecutorPolicy.java:64)
at org.gradle.internal.concurrent.ManagedExecutorImpl$1.run(ManagedExecutorImpl.java:48)
at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
at org.gradle.internal.concurrent.ThreadFactoryImpl$ManagedThreadRunnable.run(ThreadFactoryImpl.java:56)
at java.lang.Thread.run(Thread.java:745) 
prashant-ramcharan commented 3 years ago

Hi @pagmoro

The exception Cannot run program "java" would suggest that Java is either:

  1. Not installed on the machine
  2. Java is not on the system path on the machine

Can you log into the box and try java -version from a terminal session?

pagmoro commented 3 years ago

Thank you! That fixed it. Perhaps in the next release , it would be good if you could throw a User friendly exception which indicates that Java was not found , so users can fix it themselves.

prashant-ramcharan commented 3 years ago

With regards to the exception, It's prudent to ensure you have the tools (i.e. Java) installed in your machine before attempting to use a library that requires Java.

A library shouldn't check for availability of tools on the machine. It's up to the owner to ensure that tools are installed on the machine.

Courgette does not check for availability of tools (and unlikely to do so) as this falls outside the remit of this library.

pagmoro commented 3 years ago

Actually , this happens when running the courgette-jvm runner through intellij - so users expect the in-built java to be used , but are not aware that it is starting a new java process and they need java configured outside intellij. I have seen many utilities warn about JAVA_HOME or java in Path - however this is not a big deal , there are very few users who have this unique setup , so I'm good with it. Thank you!