Can't start web application in .WAR file : java.lang.ClassNotFoundException - java

I have a grails application written in Groovy. It is built and works when it's launched with :
./gradlew bootRun
Now I want to run it with java to put it in a Docker container. This is the Dockerfile I prepared :
FROM openjdk:8-jdk-alpine
ARG JAR_FILE=build/libs/*.war
ADD ${JAR_FILE} app.war
ENTRYPOINT ["java"]
CMD ["-Dgrails.env=development","-jar","app.war"]
The server fails to start because of the following error:
Caused by: org.springframework.beans.BeanInstantiationException: Failed to instantiate [grails.boot.config.GrailsApplicationPostProcessor]: Factory method 'grailsApplicationPostProcessor' threw exception; nested exception is java.lang.ClassNotFoundException: com.flosslab.eGrocery.showcase.CmsTagLib
at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:189)
at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:588)
... 29 more
Caused by: java.lang.ClassNotFoundException: com.flosslab.eGrocery.showcase.CmsTagLib
When I checked the classes folder in WEB-INF, I found that the class is there in the correct path. I tried with a Tomcat setup, with Docker and without Docker and I'm still encountering the exact same error. I think something is wrong with the .WAR build. Here is the build.gradle file
build.gradle:
buildscript {
ext {
grailsVersion = project.grailsVersion
}
repositories {
mavenLocal()
maven { url "https://repo.grails.org/core" }
maven { url "https://repo.grails.org/grails/core" }
maven { url "https://plugins.gradle.org/m2/" }
}
dependencies {
classpath "org.grails:grails-gradle-plugin:$grailsVersion"
classpath "com.bertramlabs.plugins:asset-pipeline-gradle:2.5.0"
// classpath "org.grails.plugins:hibernate4:5.0.2"
classpath 'org.springframework:springloaded:1.2.8.RELEASE'
classpath "gradle.plugin.com.github.viswaramamoorthy:gradle-util-plugins:0.1.0-RELEASE"
}
}
version "1.0.49"
group "com.flosslab.egrocery"
apply plugin: "com.github.ManifestClasspath"
apply plugin: "eclipse"
apply plugin: "idea"
apply plugin: "war"
apply plugin: "org.grails.grails-web"
apply plugin: "org.grails.grails-gsp"
apply plugin: "asset-pipeline"
war.archiveName = "egrocery-showcase.war"
ext {
grailsVersion = project.grailsVersion
gradleWrapperVersion = project.gradleWrapperVersion
}
repositories {
mavenLocal()
maven { url "https://repo.grails.org/core" }
maven { url "https://repo.grails.org/grails/core" }
maven { url "http://192.168.12.16:8081/artifactory/egrocery-local" }
maven { url "http://192.168.12.16:8081/artifactory/libs-release-local" }
maven { url "http://192.168.12.16:8081/artifactory/plugins-release-local" }
mavenCentral()
}
dependencyManagement {
imports {
mavenBom "org.grails:grails-bom:$grailsVersion"
}
applyMavenExclusions false
}
def elasticsearchVersion = '5.6.8'
ext['elasticsearch.version'] = elasticsearchVersion
dependencies {
compile fileTree(dir: "libs", includes: ["*.jar"])
compile "com.flosslab.egrocery:domain:1.0.49"
compile "org.springframework.boot:spring-boot-starter-logging"
compile "org.springframework.boot:spring-boot-autoconfigure"
compile "org.springframework.boot:spring-boot-starter-actuator"
provided "org.springframework.boot:spring-boot-starter-tomcat"
compile "org.grails:grails-core"
compile "org.grails:grails-dependencies"
compile "org.grails:grails-web-boot"
compile "org.grails:grails-datastore-rest-client:5.0.3.RELEASE"
console "org.grails:grails-console"
profile "org.grails.profiles:web:$grailsVersion"
compile "org.grails.plugins:cache"
compile "org.grails.plugins:scaffolding"
compile "org.grails.plugins:hibernate4"
compile "org.grails.plugins:spring-security-rest:2.0.0.M2"
compile "org.grails.plugins:spring-security-rest-gorm:2.0.0.M2"
runtime "org.grails.plugins:asset-pipeline"
runtime group: 'org.apache.logging.log4j', name: 'log4j-api', version: '2.7'
runtime group: 'org.apache.logging.log4j', name: 'log4j-core', version: '2.7'
// compile group: 'org.elasticsearch', name: 'elasticsearch', version: elasticsearchVersion
// compile group: 'org.elasticsearch.client', name: 'transport', version: elasticsearchVersion
// compile "org.grails.plugins:elasticsearch:1.4.1"
compile group: 'org.apache.httpcomponents', name: 'httpclient', version: '4.5.13'
compile "org.hibernate:hibernate-ehcache"
compile "org.grails.plugins:cache-ehcache:3.0.0.BUILD-SNAPSHOT"
compile "net.sf.ehcache:ehcache:2.10.2.2.21"
compile "net.sf.ehcache:ehcache-core:2.6.11"
compile "com.google.code.maven-play-plugin.net.tanesha.recaptcha4j:recaptcha4j:0.0.8"
runtime group: "org.postgresql", name: "postgresql", version: "42.1.4"
compile group: "net.java.dev.jna", name: "platform", version: "3.5.0"
compile group: "com.nimbusds", name: "nimbus-jose-jwt", version: "4.8"
compile group: "org.pac4j", name: "pac4j-core", version: "1.8.3"
compile "org.grails.plugins:fields"
testCompile "org.grails:grails-plugin-testing"
// testCompile "org.grails.plugins:geb"
testRuntime "org.seleniumhq.selenium:selenium-htmlunit-driver:2.47.1"
testRuntime "net.sourceforge.htmlunit:htmlunit:2.18"
}
configurations {
all {
exclude module: "bcmail-jdk14"
exclude module: "bctsp-jdk14"
exclude group: "com.google.guava", module: "guava"
exclude group: "com.google.guava", module: "guava-base"
}
}
task wrapper(type: Wrapper) {
gradleVersion = gradleWrapperVersion
}
assets {
minifyJs = true
minifyCss = true
}
gradle.properties:
grailsVersion=3.1.8
gradleWrapperVersion=2.11
Maybe there is something is lacking or something is wrong with the grails/groovy version ? I'm stuck for the entire day so I would appreciate your help.
Update :
Here is the Dockerfile I tried with Tomcat that I mentionned earlier. It gives me the exact same error.
FROM tomcat:8.5.75-jdk8-temurin
COPY egrocery-showcase.war /usr/local/tomcat/webapps
CMD ["catalina.sh", "run"]

I can't believe I wasted two days straight on this because someone wrote the package with an uppercase letter. There was a class in a package :
package com.flosslab.eGrocery.showcase
When I changed it to
package com.flosslab.egrocery.showcase
I got past this error.

Related

package sun.net.www.protocol.https is declared in module java.base, which does not export it

I am trying to build a java project using gradle6.6 and open jre 11.0.2, in eclipse 03-2020.
I am facing compilation issue, while building my project which uses the classes from jrt-fs.jar; e.g.'sun.net.www.protocol.http.Handler', which is in open jre 11.
public class Manager extends sun.net.www.protocol.https.Handler{
(package sun.net.www.protocol.https is declared in module java.base, which
does not export it)
1 error
FAILURE: Build failed with an exception.
* What went wrong:
Execution failed for task ':compileJava'.
> Compilation failed; see the compiler error output for details.
Following is my build.gradle:
apply plugin: 'java'
apply plugin: 'application'
allprojects {
apply plugin: 'java'
sourceCompatibility = '11.0.2'
targetCompatibility = JavaVersion.VERSION_11
}
repositories {
mavenCentral()
}
dependencies {
compile fileTree(dir: 'lib', include: '*.jar')
compile group: 'org.hamcrest', name: 'hamcrest-all', version: '1.3'
compile group: 'junit', name: 'junit', version: '4.10'
compile group: 'jmock', name: 'jmock', version: '1.0.1'
compile group: 'com.google.code.findbugs',name: 'findbugs', version: '1.3.9'
compile group: 'cglib', name: 'cglib', version: '2.1'
testCompile group: 'junit', name: 'junit', version: '4.10'
}
also, how can I avoid building the test classes, through gradle?
As #dave_thompson_085 suggested, Issue is due to modular restriction (JDK-1.9 onwards) on sun.net.* packages , as they are internal to JDK. The above packages are accessible in JDK -1.8. We need to fix our code
If you are using gradle, add this compilerArgs in build.gradle
options.encoding = "UTF-8"
options.incremental = true
options.compilerArgs.addAll([
"--add-exports",
"java.base/sun.net.www.protocol.http=ALL-UNNAMED"
])
}

Error in executing the Jar file in command Pompt (Gradle Build): NoClassDefFoundError: org/apache/poi/xssf/usermodel/XSSFWorkbook

I am building a Java Project using Gradle Build. The project has some external dependencies like Apache POI, Spring Core/Context, Log4j. When I run the project in my IDE , it is compiling and executing successfully without any errors.
However, when I build the Jar file using gradle build and run it in command prompt (using "java -jar file-name") I get Error -
NoClassDefFoundError: org/apache/poi/xssf/usermodel/XSSFWorkbook
Here is the my build.gradle file -
buildscript{
repositories{
mavenCentral()
}
dependencies{
classpath group: 'org.springframework', name: 'spring-core', version: '5.0.2.RELEASE'
classpath group: 'org.springframework', name: 'spring-context', version: '5.0.2.RELEASE'
classpath group: 'org.apache.poi', name: 'poi', version: '3.17'
classpath group: 'org.apache.poi', name: 'poi-ooxml', version: '3.17'
classpath group: 'org.apache.poi', name: 'poi-ooxml-schemas', version: '3.17'
classpath group: 'org.apache.commons', name: 'commons-collections4', version: '4.1'
classpath group: 'org.apache.xmlbeans', name: 'xmlbeans', version: '2.6.0'
}
}
apply plugin: 'java'
apply plugin: 'eclipse'
apply plugin: 'application'
sourceCompatibility = 1.8
targetCompatibility = 1.8
repositories {
mavenCentral()
}
mainClassName = '<package>.HelloWorld'
dependencies{
compile 'org.apache.poi:poi:3.17'
compile 'org.apache.poi:poi-ooxml:3.17'
compile 'org.apache.poi:poi-ooxml-schemas:3.17'
compile 'org.springframework:spring-core:5.0.2.RELEASE'
compile 'org.springframework:spring-context:5.0.2.RELEASE'
compile 'org.apache.commons:commons-collections4:4.1'
compile 'org.apache.xmlbeans:xmlbeans:2.6.0'
}
jar {
manifest{
attributes '<package>.HelloWorld'
}
baseName = 'finder-app'
version = '0.1.0'
}
The dependency jar files are present on my local machine.
Do I need to add the jar files when I package the jar using build.gradle? If yes, then how? OR
Do I need to add CLASSPATH (to external jar directory) to my local machine environment variable?
You can try the following build.gradle, it would deliver a uber jar, which package all the dependencies (doc reference).
buildscript {
repositories {
jcenter()
}
dependencies {
classpath 'com.github.jengelman.gradle.plugins:shadow:1.2.3'
}
}
apply plugin: 'java'
apply plugin: 'application'
apply plugin: 'com.github.johnrengelman.shadow'
repositories {
jcenter()
}
dependencies {
compile 'com.google.guava:guava:23.0'
testCompile 'junit:junit:4.12'
}
mainClassName = "com.github.Library"
dependencies{
compile 'org.apache.poi:poi:3.17'
compile 'org.apache.poi:poi-ooxml:3.17'
compile 'org.apache.poi:poi-ooxml-schemas:3.17'
compile 'org.springframework:spring-core:5.0.2.RELEASE'
compile 'org.springframework:spring-context:5.0.2.RELEASE'
compile 'org.apache.commons:commons-collections4:4.1'
compile 'org.apache.xmlbeans:xmlbeans:2.6.0'
}
shadowJar {
baseName = 'finder-app'
version = '0.1.0'
}
Just run ./gradlew :shadowJar, and then you can run java -jar build/libs/finder-app-0.1.0-all.jar. It would work for your favor.
NOTE, you dont need so many irrelevant dependencies in your buildscript{}, those are serves for plugins usage.
To run a java application you need to provide a classpath
You have two options:
provide the classpath in the jar manifest (META-INF/manifest) then you can run your jar using
java -jar myjar.jar
provide the classpath using -cp parameter then you can run your jar using
java -cp list_of_dependencies_jar_and_main_jar package.MyMainClass

Gradle Spring Boot plugin broken on Linux

I have a multimodule gradle build with a single module containing a spring boot application that consumes the artifacts of the other modules. I have the spring boot plugin applied to the single spring boot module.
Everything works correctly in Windows, but once I try the build on a Linux machine if fails. I have tried multiple linux machines (Jenkins server, Ubuntu VM, even bitbucket pipeline) and it fails with this error:
Problems reading data from Binary store in /tmp/gradle2075404181876889604.bin (exist: false)
I am not entirely sure what gradle uses this binary store for, but after debugging I found that this file name is different than binary store that every other module is using while building.
I have tried multiple gradle versions(2, 3, and 4) and several spring boot versions and they all fail with the same error. The only thing that fixes this is removing the spring boot plugin.
Here is the parent build.gradle
repositories {
mavenCentral()
}
def javaLangVersion = '1.8'
def gradleDir = "${rootProject.rootDir}/gradle"
def realProjects = allprojects - [project(':external'), project(':delivery')]
def javaProjects = realProjects - rootProject
def integrationTestProjects = javaProjects
configure(realProjects) {
group 'com.packagename'
version '1.0-SNAPSHOT'
apply plugin: 'eclipse'
apply plugin: 'idea'
}
configure(javaProjects) {
apply plugin: 'java'
targetCompatibility = javaLangVersion
sourceCompatibility = javaLangVersion
repositories {
mavenCentral()
}
dependencies {
compile group: 'org.slf4j', name: 'slf4j-api', version: "${slf4jVersion}"
compile group: 'org.slf4j', name: 'log4j-over-slf4j', version: "${slf4jVersion}"
testCompile group: 'junit', name: 'junit', version: "${junitVersion}"
testCompile group: 'org.mockito', name: 'mockito-core', version: "${mockitoVersion}"
testCompile group: 'nl.jqno.equalsverifier', name: 'equalsverifier', version: "${equalsverifierVersion}"
}
}
configure(integrationTestProjects) {
apply from: "${gradleDir}/integrationTest.gradle"
}
task wrapper(type: Wrapper) {
gradleVersion = '3.5'
}
Here is the spring boot module build.gradle file:
buildscript {
ext {
springBootVersion = '1.5.3.RELEASE'
}
repositories {
mavenCentral()
}
dependencies {
classpath("org.springframework.boot:spring-boot-gradle-plugin:${springBootStarterVersion}")
}
}
apply plugin: 'org.springframework.boot'
apply plugin: 'war'
war {
baseName = "${project.name}"
version = "${project.version}"
}
dependencies {
compile project(':module1')
compile project(':module2')
compile group: 'org.springframework.boot', name: 'spring-boot-starter-data-jpa'
compile group: 'org.springframework.boot', name: 'spring-boot-starter-data-rest'
compile group: 'org.apache.httpcomponents', name: 'httpcore', version: "${httpCoreVersion}"
compile group: 'org.apache.httpcomponents', name: 'httpclient', version: "${httpClientVersion}"
compile group: 'com.h2database', name: 'h2', version: "${h2Version}"
testCompile project(':test-utils')
testCompile group: 'org.springframework.boot', name: 'spring-boot-starter-test'
}
All other modules are plain java modules and only declare a dependencies block in the build file.
I have been working on this for 2 days now so any help or suggestions would be greatly appreciated. Thanks!
Well this is super embarrasing... I had a unit test using FileUtils.getTempDirectory() and then I was cleaning that directory using FileUtils.deleteQuietly after the test and it was deleting the gradle binary store that was in the /tmp folder. The reason it wasnt showing on windows is because windows locks files.
did you verify that your gradle.properties is OK on the Linux machine ?

Kotlin Capsule Gradle Error

I'm getting an error when trying to create a capsule using Gradle.
Failed to find Premain-Class manifest attribute in
E:\Dropbox\Projects\Kotlin\Games\CSGO\Charlatano\build\libs\capsule.jar
Error occurred during initialization of VM
agent library failed to init: instrument
CAPSULE: Client connection failed.
CAPSULE EXCEPTION: Accept timed out while processing null null: null (for stack trace, run with -Dcapsule.log=verbose)
Press any key to continue . . .
Here is my build.script
buildscript {
ext.kotlin_version = '1.1-M01'
ext.jna_version = '4.3.0-SNAPSHOT'
ext.quasar_version = '0.7.6'
ext.gdxVersion = '1.9.4'
repositories {
mavenCentral()
maven { url 'https://dl.bintray.com/kotlin/kotlin-eap-1.1' }
}
dependencies {
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlin_version"
}
}
apply plugin: 'java'
apply plugin: 'kotlin'
apply plugin: 'application'
group 'com.charlatano'
version '0.4.3'
mainClassName = 'com.charlatano.Charlatano'
sourceCompatibility = JavaVersion.VERSION_1_8
repositories {
mavenCentral()
maven { url "https://oss.sonatype.org/content/repositories/snapshots/" }
maven { url 'https://dl.bintray.com/kotlin/kotlin-eap-1.1' }
}
configurations {
quasar
capsule
}
dependencies {
compile group: 'org.jetbrains.kotlin', name: 'kotlin-stdlib', version: kotlin_version
compile group: 'net.java.dev.jna', name: 'jna', version: jna_version
compile group: 'net.java.dev.jna', name: 'jna-platform', version: jna_version
compile group: 'org.jire.arrowhead', name: 'arrowhead', version: '1.2.1'
capsule group: 'co.paralleluniverse', name: 'capsule', version: '1.0.3'
quasar group: 'co.paralleluniverse', name: 'quasar-core', version: quasar_version
compile group: 'co.paralleluniverse', name: 'quasar-core', version: quasar_version
compile group: 'co.paralleluniverse', name: 'quasar-actors', version: quasar_version
compile group: 'co.paralleluniverse', name: 'quasar-kotlin', version: quasar_version
compile "com.badlogicgames.gdx:gdx:$gdxVersion"
compile "com.badlogicgames.gdx:gdx-box2d:$gdxVersion"
compile "com.badlogicgames.gdx:gdx-backend-lwjgl:$gdxVersion"
compile "com.badlogicgames.gdx:gdx-platform:$gdxVersion:natives-desktop"
compile "com.badlogicgames.gdx:gdx-box2d-platform:$gdxVersion:natives-desktop"
}
task capsule(type: Jar, dependsOn: jar) {
archiveName = "capsule.jar"
from jar // embed our application jar
from { configurations.runtime } // embed dependencies
from(configurations.capsule.collect { zipTree(it) }) { include 'Capsule.class' } // we just need the single Capsule class
manifest {
attributes(
'Main-Class' : 'Capsule',
'Application-Class' : mainClassName,
'Extract-Capsule' : 'false', // no need to extract the capsule
'Min-Java-Version' : '1.8.0',
'JVM-Args' : run.jvmArgs.join(' '),
'System-Properties' : run.systemProperties.collect { k,v -> "$k=$v" }.join(' '),
'Java-Agents' : configurations.quasar.iterator().next().getName()
)
}
}
run {
jvmArgs "-javaagent:${configurations.quasar.iterator().next()}"
}
Here are the jar files it generates.
https://dl.dropboxusercontent.com/u/91292881/ShareX/2016/09/libs.zip
Please tell me what is wrong, thanks!
It seems that MANIFEST.md in capsule is broken and it misses a Premain-Class attribute like below:
Premain-Class: org.eclipse.package.ObjectSizeFetcher
Your's capsule manifest file should look like:
Manifest-Version: 1.0
Created-By: 1.5.0_18 (Sun Microsystems Inc.)
Premain-Class: org.eclipse.package.ObjectSizeFetcher
Check similar issue to find more: "Failed to load Premain-Class manifest attribute" while trying to get the size of an object using java agent

args4J doesn't work with gradle

I'm totally new to gradle so it may be a obvious problem:
I'm using eclipse with gradle and I actually have no problem adding dependencies for junit or stuff, it adds the junit lib to the gradle dependencies and there's no problem using junit, but if i try to use args4j (also with adding the dependency) it just doesn't work.
Just to make sure there's no problem with the build.gradle
apply plugin: 'java'
apply plugin: 'eclipse'
sourceCompatibility = 1.8
version = '1.0'
jar {
manifest {
attributes 'Implementation-Title': 'title',
'Implementation-Version': version,
'Main-Class':'path.to.main.Main'
}
}
repositories {
mavenCentral()
}
test {
systemProperties 'property': 'value'
}
dependencies{
compile 'args4j:args4j-site:2.0.25'
testCompile group: 'junit', name: 'junit', version: '4.+'
}
and No I'm not using title or path.to.main ^^
Eclipse shows me that the import (args4j) cannot be resolved
You forgot main "args4j" module:
compile group: 'args4j', name: 'args4j', version: '2.0.25'
compile group: 'args4j', name: 'args4j-site', version: '2.0.25'
With gradle-7.1 this works for me:
// build.gradle
repositories {
mavenCentral()
}
dependencies {
implementation group: 'args4j', name: 'args4j', version: '2.33'
implementation group: 'args4j', name: 'args4j-site', version: '2.33'
}

Categories

Resources