Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

NoSuchMethodError thrown with Scala 2.12 #1087

Closed
randomcoder opened this issue Dec 21, 2016 · 34 comments
Closed

NoSuchMethodError thrown with Scala 2.12 #1087

randomcoder opened this issue Dec 21, 2016 · 34 comments
Milestone

Comments

@randomcoder
Copy link

Summary

When running cucumber tests with cucumber-scala (1.2.5) using Scala 2.12.1 or 2.12.0 a noSuchMethodError is raised on startup

Here is a minimal project that reproduces the behaviour: https://github.com/randomcoder/cucumber-scala-2-12

Expected Behavior

The test cases should run

Current Behavior

The error below is thrown before any tests are executed

Exception in thread "main" java.lang.NoSuchMethodError: cucumber.api.scala.ScalaDsl.$init$(Lcucumber/api/scala/ScalaDsl;)V
	at steps.SimpleScenarioSteps.<init>(SimpleScenarioSteps.scala:6)
	at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
	at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
	at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
	at java.lang.reflect.Constructor.newInstance(Constructor.java:423)
	at java.lang.Class.newInstance(Class.java:442)
	at cucumber.runtime.scala.ScalaBackend$$anonfun$6.apply(ScalaBackend.scala:62)
	at cucumber.runtime.scala.ScalaBackend$$anonfun$6.apply(ScalaBackend.scala:62)
	at scala.collection.TraversableLike.$anonfun$map$1(TraversableLike.scala:234)
	at scala.collection.mutable.ArrayBuffer.foreach(ArrayBuffer.scala:48)
	at scala.collection.TraversableLike.map$(TraversableLike.scala:234)
	at scala.collection.AbstractTraversable.map(Traversable.scala:104)
	at cucumber.runtime.scala.ScalaBackend.loadGlue(ScalaBackend.scala:62)
	at cucumber.runtime.Runtime.<init>(Runtime.java:92)
	at cucumber.runtime.Runtime.<init>(Runtime.java:70)
	at cucumber.runtime.Runtime.<init>(Runtime.java:66)
	at cucumber.api.cli.Main.run(Main.java:35)
	at cucumber.api.cli.Main.main(Main.java:18)

Steps to Reproduce (for bugs)

  1. In the sample project execute sbt "run --dry-run --glue steps classpath:feature"
@davidboden
Copy link

I assume it's down to Java 8 and Scala 2.12 expecting to find the "init" method in the ScalaDsl.class file (new style Traits as interfaces) rather than in ScalaDsl$class.class file (old style Traits as interface and supporting class).

Using javap to look at ScalaDsl.class from cucumber-scala_2.12-1.2.5.jar , I see it has MajorVersion = 50 which means it was compiled under Java 6.

I think the Scala 2.12 package needs to be compiled (not just run) under Java 8 to avoid this problem.

@davidboden
Copy link

I've confirmed that adding this to scala/scala_2.12/pom.xml fixes the issue:

<pluginManagement> <plugins> <plugin> <groupId>org.apache.maven.plugins</groupId> <artifactId>maven-compiler-plugin</artifactId> <version>3.5.1</version> <configuration> <encoding>UTF-8</encoding> <source>1.8</source> <target>1.8</target> <compilerArgument>-Werror</compilerArgument> </configuration> </plugin> </plugins> </pluginManagement>

@davidboden
Copy link

If you can't wait for this to be fixed in the next Cucumber release build, my advice would be:

  • Clone the Cucumber build from Github.
  • Make the change to the pom.xml I've suggested.
  • Run the Maven Cucumber build with mvn -DskipTests -pl scala/scala_2.12 -am install

Then change your project's build to reference cucumber-scala version 1.2.6-SNAPSHOT.

From what you're saying, it sounds like you're building the Cucumber .java sources from inside your build. I'm sure you can get that to work if you need to but it doesn't seem like the obvious right thing to do (to me).

@paoloambrosio
Copy link
Member

It would help if someone could verify PR #1091, that should fix this issue.

The code linked to this issue seems to be behaving in the same way (so failing the second example) with:

  • Scala 2.12.1 and cucumber-scala 1.2.6-SNAPSHOT form the PR
  • Scala 2.11.8 and cucumber-scala 1.2.5

To try it:

  • From the code root of the PR
    • Run mvn clean install
  • In your project
    • Change cucumber-scala from 1.2.5 to 1.2.6-SNAPSHOT
    • If using SBT, add the local Maven repository (resolvers += Resolver.mavenLocal)

@davidboden
Copy link

PR #1091 fixes it for my project. Tests run successfully with Scala version 2.12.0 and 2.12.2. I confirmed before I ran with 1.2.6-SNAPSHOT (which I built locally from your pull request) that the tests were still failing as I expected with version 1.2.5.

@elkingut
Copy link

Hello @paoloambrosio @daveboden some date for the deployment of the solution? I need use cucumber-scala in my project. Thanks!!

@davidboden
Copy link

Hi. You need https://github.com/cucumber/cucumber-jvm

@fernandaalayon
Copy link

Hi @paoloambrosio & @davebassan,
You have a date in order to upload the new version of the library with the correction of this bug, when would it be?,.
I depend on this to decide which framework to implement in my project.
Thanks

@lewismj
Copy link

lewismj commented Apr 3, 2017

I have an SBT plugin/test framework for Scala/Cucumber here https://github.com/lewismj/cucumber
I get the same issue, any ETA on when Cucumber 1.2.6 is due to ship?

@lewismj
Copy link

lewismj commented Apr 17, 2017

Hi,
I still get this error, using 1.2.6-SNAPSHOT,
java.lang.NoSuchMethodError: cucumber.api.scala.ScalaDsl.$init$(Lcucumber/api/scala/ScalaDsl

Example project:
https://github.com/lewismj/cucumber

@bhgitgit
Copy link

bhgitgit commented May 9, 2017

hi @paoloambrosio , thanks for the fix.Have tried your fix, and dont get NoMethodError anymore, but code within stepdefnition does not get executed(though the tests pass without executing code within stepdefs).They get executed, when I switch to 2.11 version of cucumber i.e 1.2.4.Can you please confirm this if this is known issue with the fix

@stela
Copy link

stela commented May 9, 2017

@Bhavana-git see #1091, says step-executions and 0-arity functions fail with scala 2.12, for that pull request.

@bhgitgit
Copy link

bhgitgit commented May 9, 2017

@stela thanks , noticed it just now.

@szarnyasg
Copy link

szarnyasg commented May 30, 2017

This still does not work for us: with 2.12 we still get the exception mentioned in the first post (by @randomcoder) and later by @lewismj:

Exception in thread "main" java.lang.NoSuchMethodError: 
cucumber.api.scala.ScalaDsl.$init$(Lcucumber/api/scala/ScalaDsl;

Meanwhile, #1091 is still not merged. Is there any way to get this working with 2.12?

@szarnyasg
Copy link

I updated @randomcoder 's example to follow the transition from info.cukes to io.cucumber and use 2.0.0-SNAPSHOT, but it did not make a difference.

@szarnyasg
Copy link

szarnyasg commented Jun 26, 2017

tl;dr: the root of the problem is that the Scala 2.12 support dependes on version 2.12.0-M1, as noted in a comment:

    <properties>
        <!--
        Upgrading to 2.12.0-M2 or higher causes:
        initializationError(cucumber.runtime.scala.test.RunCukesTest)  Time elapsed: 0.006 sec  <<< ERROR! java.util.NoSuchElementException: next on empty iterator [no stack trace] -->
        <scala.version>2.12.0-M1</scala.version>
    </properties>

We have been struggling with this issue for some time, so I'd like to share our experience.

  • @randomcoder's original post has a small issue: instead of feature, it should be features on the classpath:

    sbt "run --dry-run --glue steps classpath:features"
    
  • @paoloambrosio's comment is correct and I could get the example in the issue working.

  • With @szdavid92, we created a fork from @paoloambrosio's scala-2.12-with-java-8 branch, merged this repository's current master branch and resolved the conflicts. This resulted in a working version, which is available on my fork. This works with @randomcoder's example, provided that the cucumber-scala-2-12 project also uses the milestone Scala version, else it will throw the error mentioned in the original post:

    java.lang.NoSuchMethodError: cucumber.api.scala.ScalaDsl.$init$(Lcucumber/api/scala/ScalaDsl;)V
    

    While this might seems a plausible approach, unfordunately mvn -pl scala/scala_2.12 -am install does not compile it - instead, it throws a ton of errors. Hence, I see no point of raising a PR from this.

  • Simply using the current 2.0.0-SNAPSHOT (as deployed in the Sonatype OSS Snapshots repository) returns in the following error:

    [error] (run-main-0) java.lang.NoClassDefFoundError: org/scalactic/TripleEqualsSupport$class java.lang.NoClassDefFoundError: org/scalactic/TripleEqualsSupport$class
    

    We tried to fix this by explicitly adding the appropriate Scalactic dependency ("org.scalactic" % "scalactic_2.12" % "3.0.3"), but it made no difference.

@szarnyasg
Copy link

@mpkorstanje
Copy link
Contributor

mpkorstanje commented Jul 7, 2017

@szarnyasg thanks for summarizing all that!

I've tried to solve the issue by building scala_2.12 module against java 8 but this break reflection. In some circumstances, I know not which, scala will compile the Steps into a Lambda rather then a class and erase the argument type information of the apply function.

@mpkorstanje
Copy link
Contributor

Ah right. #1091 solved that already.

Does anybody have any serious objections against discontinuing support for java 8 for scala 2.12.x and up?

@szarnyasg
Copy link

#1091 was quite difficult to merge (see my attempt at https://github.com/szarnyasg/cucumber-jvm/commits/scala-2.12-with-java-8), and it only solved the NoSuchMethodError issue - I could only get it working from a projet that also uses the milestone version.

discontinuing support for java 8 for scala 2.12.x and up?
I don't get this - AFAIK Scala 2.12 only works with Java 8.

@mpkorstanje
Copy link
Contributor

Eh. Typo. Meant to say that we'll only build scala 2.12.x and up for java 8.

I don't get this - AFAIK Scala 2.12 only works with Java 8.

Good. I was under the impression it could also work with 7.

@mpkorstanje
Copy link
Contributor

I could only get it working from a projet that also uses the milestone version.

I've updated 2.12.0-M1 to 2.12.2 and 2.11.8 to 2.11.11.

This seems to resolve the problems.

@mpkorstanje
Copy link
Contributor

I still have to test this against the reproducers but #1171 is passing my tests locally.

@mpkorstanje
Copy link
Contributor

mpkorstanje commented Jul 7, 2017

@stela

@Bhavana-git see #1091, says step-executions and 0-arity functions fail with scala 2.12, for that pull request.

This appears to be a feature of Scala.

When("""^I multiply x \* y$""") { 
    z = x * y
}

Will execute the statement z = x * y which returns Unit. The Unit is then passed onto the step definition. Executing it is a no-op.

On the other hand

When("""^I multiply x \* y$""") { () =>
    z = x * y
}

Will return a function with the signature () => Unit. Which can be sensibly executed.

*Apologies if this explanation is a bit sloppy or even wrong. Not that into Scala. :)

@mpkorstanje mpkorstanje added this to the 2.0.0 milestone Jul 7, 2017
@mpkorstanje mpkorstanje added the Bug label Jul 7, 2017
mpkorstanje added a commit that referenced this issue Jul 8, 2017
 - cucumber-scala_2.12 and scala-calculator are compiled to java8 byte code
 - Scala versions have been updated
   - 2.12.0-M1 to 2.12.2
   - 2.11.8    to 2.11.11
 - Manifest is used instead of Java reflection to provide type information

Related issues:
 - #1087
 - #1091

Fixes #1087
@mpkorstanje
Copy link
Contributor

I was wrong. The first example utilizes call by name, the second call by reference. We allow both. The original PR broke call by name. This has been fixed.

@mpkorstanje
Copy link
Contributor

@randomcoder @szarnyasg

What is the expected out come of the reproducer. It is currently failing because the steps instance is reused between examples in the scenario. This is a bug, but the behavior also appears to have been present for a long while.

@szarnyasg
Copy link

What is the expected out come of the reproducer.

@mpkorstanje Unfortunately, I am not an expert at Cucumber, so I cannot answer this.

@mpkorstanje
Copy link
Contributor

Then I'll consider it passing. The tests are running at least.

@lewismj
Copy link

lewismj commented Jul 9, 2017

Thanks, this is great news, any idea when it may be in the SNAPSHOT build?

@mpkorstanje
Copy link
Contributor

Propagation delays aside it should be available right now.

Do note the changed groupId

<repository>
    <id>sonatype-snapshots</id>
    <url>https://oss.sonatype.org/content/repositories/snapshots</url>
    <snapshots>
        <enabled>true</enabled>
    </snapshots>
</repository>

<dependency>
    <groupId>io.cucumber</groupId>
    <artifactId>cucumber-java</artifactId>
    <version>2.0.0-SNAPSHOT</version>
    <scope>test</scope>
</dependency>

@szarnyasg
Copy link

Great, the tests now work at https://travis-ci.org/szarnyasg/cucumber-scala-2-12. Thanks @mpkorstanje!

@jecklgamis
Copy link

thanks @mpkorstanje! , looks good with oracle java 8 + scala 2.12.2 + cucucumber-scala 2.0.0-SNAPSHOT
https://github.com/jecklgamis/cucumber-jvm-scala-example

@lewismj
Copy link

lewismj commented Jul 29, 2017

Thanks, this fixed my issue: lewismj/cucumber#28 , published an update for my sbt plugin to nexus.

@lock
Copy link

lock bot commented Oct 25, 2018

This thread has been automatically locked since there has not been any recent activity after it was closed. Please open a new issue for related bugs.

@lock lock bot locked as resolved and limited conversation to collaborators Oct 25, 2018
mpkorstanje added a commit that referenced this issue Oct 4, 2019
 - cucumber-scala_2.12 and scala-calculator are compiled to java8 byte code
 - Scala versions have been updated
   - 2.12.0-M1 to 2.12.2
   - 2.11.8    to 2.11.11
 - Manifest is used instead of Java reflection to provide type information

Related issues:
 - #1087
 - #1091

Fixes #1087
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests