admin管理员组文章数量:1287628
I have managed to setup and run a Docker Image for a simple Hello World Java console application, but I am struggling with it when I add packages. I have this working:
Folder contents:
Dockerfile HelloWorld.class HelloWorld.java
Dockerfile:
FROM openjdk:11-jdk-slim
WORKDIR /app
COPY HelloWorld.java .
RUN javac HelloWorld.java
CMD ["java", "HelloWorld"]
Java class:
public class HelloWorld {
public static void main(String[] args) {
System.out.println("Hello, Docker World!");
}
}
This works fine with
sudo docker build -t hello-world-java .
sudo docker run hello-world-java
But if I add a package for the class to the folder contents and the class:
Java class:
package hello;
public class HelloWorld {
public static void main(String[] args) {
System.out.println("Hello, Docker World!");
}
}
Contents
~/workspace/helloWorldPackage$ tree
.
├── Dockerfile
└── hello
├── HelloWorld.class
└── HelloWorld.java
2 directories, 3 files
And modify Dockerfile like:
FROM openjdk:11-jdk-slim
WORKDIR /app
COPY hello/ .
RUN javac HelloWorld.java
CMD ["java", "hello.HelloWorld"]
I can docker build it, but when running I get:
Error: Could not find or load main class hello.HelloWorld
Caused by: java.lang.ClassNotFoundException: hello.HelloWorld
exit status 1
I have tried several modifications in the Dockerfile to no avail. Mostly modifying the classpath on the CMD, or what it is copied in COPY/WORKDIR, but I think i do not understand exactly what such commands do. Is CMD run from inside the folder at WORKDIR? How does it interact with the COPY folder? And with the java command? I think there is something I lack there to make it work.
I can only find tutorials or answers for Java web apps or Java local apps without packages. I am expecting a similar behavior to what I get for a packageless Java application. I.e. the correct Dockerfile description for java to catch the correct classpath.
I have managed to setup and run a Docker Image for a simple Hello World Java console application, but I am struggling with it when I add packages. I have this working:
Folder contents:
Dockerfile HelloWorld.class HelloWorld.java
Dockerfile:
FROM openjdk:11-jdk-slim
WORKDIR /app
COPY HelloWorld.java .
RUN javac HelloWorld.java
CMD ["java", "HelloWorld"]
Java class:
public class HelloWorld {
public static void main(String[] args) {
System.out.println("Hello, Docker World!");
}
}
This works fine with
sudo docker build -t hello-world-java .
sudo docker run hello-world-java
But if I add a package for the class to the folder contents and the class:
Java class:
package hello;
public class HelloWorld {
public static void main(String[] args) {
System.out.println("Hello, Docker World!");
}
}
Contents
~/workspace/helloWorldPackage$ tree
.
├── Dockerfile
└── hello
├── HelloWorld.class
└── HelloWorld.java
2 directories, 3 files
And modify Dockerfile like:
FROM openjdk:11-jdk-slim
WORKDIR /app
COPY hello/ .
RUN javac HelloWorld.java
CMD ["java", "hello.HelloWorld"]
I can docker build it, but when running I get:
Error: Could not find or load main class hello.HelloWorld
Caused by: java.lang.ClassNotFoundException: hello.HelloWorld
exit status 1
I have tried several modifications in the Dockerfile to no avail. Mostly modifying the classpath on the CMD, or what it is copied in COPY/WORKDIR, but I think i do not understand exactly what such commands do. Is CMD run from inside the folder at WORKDIR? How does it interact with the COPY folder? And with the java command? I think there is something I lack there to make it work.
I can only find tutorials or answers for Java web apps or Java local apps without packages. I am expecting a similar behavior to what I get for a packageless Java application. I.e. the correct Dockerfile description for java to catch the correct classpath.
Share Improve this question asked Feb 24 at 11:17 JudeJude 111 bronze badge1 Answer
Reset to default 0When you try to launch hello.HelloWorld
as the main class, the JVM looks (among other places) for a hello/HelloWorld.class
file. You need to keep that hello
structure when you copy files into the container.
The COPY
line should include the entire hello
directory. The RUN javac ...
line should use a relative path to the source file. Together this looks like
FROM openjdk:11-jdk-slim
WORKDIR /app
COPY hello/ hello/ # relative path on right-hand side
RUN javac hello/HelloWorld.java # relative path in filename
CMD ["java", "hello.HelloWorld"]
(For any larger project you may want a more substantial build system, like Maven or Gradle. For Java it's not uncommon to build the application outside Docker and only COPY
the jar file into the image; or if you're running the build in the Dockerfile, make sure to COPY
the entire src
tree in standard project layouts.)
本文标签: Create and Run a Docker Image for Java Application with PackagesStack Overflow
版权声明:本文标题:Create and Run a Docker Image for Java Application with Packages - Stack Overflow 内容由网友自发贡献,该文观点仅代表作者本人, 转载请联系作者并注明出处:http://www.betaflare.com/web/1741274348a2369640.html, 本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容,一经查实,本站将立刻删除。
发表评论