部署Spring Boot应用程序在Docker镜像中的Tomcat中

huangapple go评论75阅读模式
英文:

Deploying a Spring Boot Application in Tomcat in a Docker image

问题

一个朋友和我正在尝试在 Docker 镜像中设置一个 Tomcat 服务器,该服务器将运行我们提供的 .war 文件。

我们已经成功运行了 Docker 镜像,以下是 Dockerfile 的内容:

FROM tomcat:10-jdk8

ADD ./Build/sample.war /usr/local/tomcat/webapps/

EXPOSE 8080

正如您所见,它使用了 Tomcat 的 Docker 镜像,并将我们的 sample.war 添加到 webapps 文件夹中。在我看来,这应该足够运行它。

这个 Java 应用程序是一个简单的 Spring Boot 应用程序,以下是主类:

package com.example.demo;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.web.servlet.support.SpringBootServletInitializer;

@SpringBootApplication
public class DemoApplication extends SpringBootServletInitializer {

    public static void main(String[] args) {
        SpringApplication.run(DemoApplication.class, args);
    }

}

这是我们正在使用的控制器:

package com.example.demo.repos;

import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
@RequestMapping("/")
public class UltraRepository {
    @GetMapping("/test")
    public String testGet() {
        return "Wow, it works!";
    }
}

当我在本地运行应用程序,或者构建 .war 文件并在本地计算机上运行它时,它都可以正常工作。在浏览器中访问 http://localhost:8080/test 会显示 "Wow, it works"。

但是当我们在 Docker 镜像中运行它,并尝试访问 http://localhost:8080/sample/test 时(我假设这是正确的 URL),我们会得到以下消息:
链接

然而,当我们查看运行 Tomcat 的 Docker 容器的日志时,它显示已成功启动了应用程序。

有谁知道我们需要进行哪些更改以使其正常工作吗?

提前谢谢!

英文:

A friend and I are trying to setup a tomcat server in a docker image that will run a .war file that we will supply to it.

We got the Docker image running, this is the Dockerfile:

FROM tomcat:10-jdk8

ADD ./Build/sample.war /usr/local/tomcat/webapps/

EXPOSE 8080

As you can see, it takes the tomcat docker image and adds a our sample.war to the webapps folder. In my eyes, this should be enough to run it.

The Java application is a simple Spring Boot application, this is the main class:

package com.example.demo;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.web.servlet.support.SpringBootServletInitializer;

@SpringBootApplication
public class DemoApplication extends SpringBootServletInitializer {

    public static void main(String[] args) {
        SpringApplication.run(DemoApplication.class, args);
    }

}

And this is the Controller we are using:

package com.example.demo.repos;

import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
@RequestMapping("/")
public class UltraRepository {
    @GetMapping("/test")
    public String testGet() {
        return "Wow, it works!";
    }
}

When I run the application locally, or build the .war file and run it locally on my pc, it works fine. Giving me "Wow, it works" when I go to http://localhost:8080/test.

But when we run it inside a docker file, and go to http://localhost:8080/sample/test (I assume this would be the right url), we get the following message:
https://i.stack.imgur.com/tMQQC.png

While when we look in the logs of the docker which runs tomcat, it says it has started the application successfully.

Does anyone know what we might have to change to get this working?

Thanks in advance!

答案1

得分: 0

你正在使用的命令来运行容器是什么?您需要使用 -p 选项将本地端口映射到容器端口,就像这样:Docker run -p 8080:8080 image_name。

英文:

What is the command that you are using to run the Container ? you need to map your local port to the container port, with -p option, like this: Docker run -p 8080:8080 image_name

答案2

得分: 0

你正在扩展 SpringBootServletInitializer,但没有覆盖其 configure 方法。您可以在 DemoApplication 类中添加以下方法来解决此问题。

@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
    return application.sources(DemoApplication.class);
}

SpringBootServletInitializer 类允许我们在由Servlet容器运行时配置我们的应用程序,方法是覆盖 configure() 方法。

英文:

You are extending the SpringBootServletInitializer but not overriding its configure method. You can add the following method in a DemoApplication class to fix the issue.

@Override
protected SpringApplicationBuilder configure(SpringApplicationBuilder application) {
	return application.sources(DemoApplication.class);
}

SpringBootServletInitializer class allows us to configure our application when it's run by the servlet container, by overriding the configure() method.

答案3

得分: 0

结果发现这是因为我们使用了 tomcat:10-jdk8,而我们必须使用 tomcat:jdk11,因为 SpringBoot 应用程序也是使用 Java 11 制作的。

英文:

Turns out this was happening because we used tomcat:10-jdk8, while we had to use tomcat:jdk11, since the SpringBoot application is also made with Java 11.

huangapple
  • 本文由 发表于 2020年10月1日 23:04:31
  • 转载请务必保留本文链接:https://go.coder-hub.com/64158116.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定