Intellj multi module maven project not finding main class

Viewed 521

I'm trying maven multi-module project https://github.com/shekharkhairnar/maven-multimodule-example

the following is my project structure:

enter image description here

I did mvn clean install on parent project and moved to sktech-buseness/target and

when I execute java -jar sktech-business-1.0-SNAPSHOT.jar

I'm getting no main manifest attribute, in sktech-business-1.0-SNAPSHOT.jar

I have tried with maven assembly plugin, shad plugin but not use

--Edit---

After comment by "konstantin-annikov" I have added maven-jar-plugin to sktech-business pom file as:

<build>
        <plugins>
            <plugin>
                <!-- Build an executable JAR -->
                <groupId>org.apache.maven.plugins</groupId>
                <artifactId>maven-jar-plugin</artifactId>
                <version>3.1.0</version>
                <configuration>
                    <archive>
                        <manifest>
                            <addClasspath>true</addClasspath>
                            <classpathPrefix>lib/</classpathPrefix>
                            <mainClass>org.sktech.business.BusinessTest</mainClass>
                        </manifest>
                    </archive>
                </configuration>
            </plugin>
        </plugins>
    </build>

but getting exception while run the jar as:

Exception in thread "main" java.lang.NoClassDefFoundError: org/sktch/domain/Student
        at org.sktech.business.BusinessTest.main(BusinessTest.java:12)
Caused by: java.lang.ClassNotFoundException: org.sktch.domain.Student
        at java.net.URLClassLoader.findClass(Unknown Source)
        at java.lang.ClassLoader.loadClass(Unknown Source)
        at sun.misc.Launcher$AppClassLoader.loadClass(Unknown Source)
        at java.lang.ClassLoader.loadClass(Unknown Source)
        ... 1 more

any help is greatly appreciated.

3 Answers

Lets check your Manifest file. You can simply unzip your .jar files with any unzip utility. (jar format is based on the popular ZIP format).

When I open sktech-business-1.0-SNAPSHOT/META-INF/MANIFEST.MF i see the following contents:

MANIFEST.MF:

Manifest-Version: 1.0
Created-By: Apache Maven 3.5.0
Built-By: guicey
Build-Jdk: 11.0.5
Class-Path: lib/sktech-domain-1.0-SNAPSHOT.jar
Main-Class: org.sktech.business.BusinessTest

Your application is expecting to find additional java classes to run your application with in lib/sktech-domain-1.0-SNAPSHOT.jar. So the directory where you are running the following command java -jar sktech-business-1.0-SNAPSHOT.jar should have a lib directory with a file named sktech-domain-1.0-SNAPSHOT.jar.

In case you don't want to copy/move directories, you can use the following maven plugin to copy all dependent classes to a jar-with-dependencies. Add the following snippet to your pom.xml file in the module where the Main-Class is: maven-multimodule-example/sktech-business/pom.xml.

maven-assembly-plugin snippet:

<build>
    <plugins>
        <plugin>
            <artifactId>maven-assembly-plugin</artifactId>
            <executions>
                <execution>
                    <phase>package</phase>
                    <goals>
                        <goal>single</goal>
                    </goals>
                </execution>
            </executions>
            <configuration>
                <archive>
                    <manifest>
                        <mainClass>org.sktech.business.BusinessTest</mainClass>
                    </manifest>
                </archive>
                <descriptorRefs>
                    <descriptorRef>jar-with-dependencies</descriptorRef>
                </descriptorRefs>
            </configuration>
        </plugin>
    </plugins>
</build>

And you can run the jar with dependencies by executing the following command: java -jar sktech-business-1.0-SNAPSHOT-jar-with-dependencies.jar

Program output:

[ComplimentryCourse(id=1, name=Java 8 Fetures), ComplimentryCourse(id=2, name=Advance Java), ComplimentryCourse(id=3, name=Spring Boot), ComplimentryCourse(id=4, name=Database Management)]

Also you can use the following way without any Maven plugins in your pom.xml.

For Maven project:

java --class-path sktech-business/target/sktech-business-1.0-SNAPSHOT.jar:sktech-domain/target/sktech-domain-1.0-SNAPSHOT.jar org.sktech.business.BusinessTest

For structure:

.
├── sktech-business-1.0-SNAPSHOT.jar
└── sktech-domain-1.0-SNAPSHOT.jar

Use:

java --class-path sktech-business-1.0-SNAPSHOT.jar:sktech-domain-1.0-SNAPSHOT.jar org.sktech.business.BusinessTest

Adding a manifest was the first step, but java.lang.NoClassDefFoundError: org/sktch/domain/Student means:

You don't have a src/main/java/org/sktch/domain/Student.java file.
(following the Maven standard directory layout)

Make sure the file and class is there first, then mvn build again.

Related