kweb-core icon indicating copy to clipboard operation
kweb-core copied to clipboard

Kweb works running from gradle run but does not work once bundled as a shadowJar with gradle

Open Timmeey opened this issue 4 years ago • 4 comments

I wanted to use KWeb in a little application, nothing fancy or complex.

Once i was done and everything was working from within the IDE, i pushed it to our CI (buildkite) Then the problem began. Starting it inside the docker container (kubernetes) did not work, it started gave the first few output lines and then nothing, no webinterface nothing.

So i played around a little. Working means: Webinterface is reachable and shows information Not working means: webinterface is not reachable, but console output is coming

When i start the Main method from the IDE directly it works When i use the ./gradlew run it works When i use the ./gradlew shadowJar; java -jar $filename.jar it does NOT work

I have no idea why it breaks in this weird way once it is bundled as a jar

i attached a mini reproducible artifact, containing a little project. You can start it with gradle run and then connect to localhost:8080 to get a "Hello test" page once you bundle it up with gradle shadowJar and then start the JAR it does not work

Hint: I'm sure that SOMETHING is running with an open port even when started with the bundled jar because the browser reports "Connection RESET" if nothing is running it reports "Connection REFUSED"

KWeb Version 0.6.2 (but also happens on 0.6.4)

ui1.zip

Timmeey avatar Mar 19 '20 15:03 Timmeey

(just a tip: the shadow plugin comes with a task called runShadow, which compiles the fatjar and runs it, just like you are doing with ./gradlew shadowJar; java -jar $filename.jar but perhaps a bit easier)

I added logback to your sample project and set the log level to trace (see logging in ktor) and now I am seeing the following exception for every request:

java.lang.ExceptionInInitializerError: null
        at org.eclipse.jetty.server.HttpConnection.<clinit>(HttpConnection.java:56)
        at org.eclipse.jetty.server.HttpConnectionFactory.newConnection(HttpConnectionFactory.java:86)
        at org.eclipse.jetty.server.ServerConnector$ServerConnectorManager.newConnection(ServerConnector.java:549)
        at org.eclipse.jetty.io.ManagedSelector.createEndPoint(ManagedSelector.java:271)
        at org.eclipse.jetty.io.ManagedSelector.access$1800(ManagedSelector.java:62)
        at org.eclipse.jetty.io.ManagedSelector$Accept.run(ManagedSelector.java:759)
        at org.eclipse.jetty.util.thread.QueuedThreadPool.runJob(QueuedThreadPool.java:806)
        at org.eclipse.jetty.util.thread.QueuedThreadPool$Runner.run(QueuedThreadPool.java:938)
        at java.lang.Thread.run(Thread.java:748)
Caused by: java.lang.ArrayIndexOutOfBoundsException: 1
        at org.eclipse.jetty.http.PreEncodedHttpField.<clinit>(PreEncodedHttpField.java:68)
        ... 9 common frames omitted

Which seems to be a bug in Jetty. There are several issues in the jetty repo saying that this will happen when the jar isn't packaged properly but it appears that shadow is including all the necessary things. Perhaps someone with more jetty knowledge can chime in.

Another thing to try is using a different embedded server. Ktor also supports embedded netty servers (see the sample projects).

ethanmdavidson avatar Mar 19 '20 17:03 ethanmdavidson

Thank you for the quick response.

For the gradle tip, i was already using shadowRun, but to prevent any miscommunication, i explicitly tried the shadowJar; java -jar route.

Tried the Netty idea, and it works perfectly. Thank you very much.

Unfortunately i have no idea how to help with the original issue.

Timmeey avatar Mar 20 '20 12:03 Timmeey

I'm glad to hear Netty worked. It was a much earlier version of Ktor, but I did use Netty initially and found it to be unstable, which is why I switched to Jetty.

If Netty is now more stable than Jetty then we may want to consider switching back.

sanity avatar Mar 20 '20 16:03 sanity

I faced this issue "Connection REFUSED" many times on different builds when trying to build it as FatJAR as build - artifacts, on some builds it was ok, but mostly "Connection REFUSED"... found a fix here with using ShadowJar

resolved by adding this part to build.gradle

import com.github.jengelman.gradle.plugins.shadow.transformers.ServiceFileTransformer
shadowJar {
    transform(ServiceFileTransformer) {
        path = 'META-INF/services'
        include 'org.eclipse.jetty.http.HttpFieldPreEncoder'
    }
}
  • in my case i also need to add a main class name variable in this section

GenerRR avatar May 29 '20 11:05 GenerRR

This issue is stale because it has been open 30 days with no activity. Remove stale label or comment or this will be closed in 5 days.

github-actions[bot] avatar Oct 13 '22 03:10 github-actions[bot]