我有一个简单的 Spring Boot 服务,它使用 MySQL 执行 CRUD 操作。我对我的服务进行了 docker 化,并提取了 mysql 的映像,并使这些映像在同一网络上运行并工作。
问题是我无法使用默认公开端口(定义为 7070)访问该服务。
这是我在 application.properties 中定义的 spring 数据源属性:
spring.datasource.url=jdbc:mysql://0.0.0.0:3306/test
#spring.datasource.url=jdbc:mysql://mysql:3306/test
spring.datasource.username=root
spring.datasource.password=image
spring.datasource.driver-class-name=com.mysql.cj.jdbc.Driver
spring.jpa.hibernate.ddl-auto=update
spring.jpa.show-sql=true
#----ADDITIONAL PROPERTIES-----#
server.port = 7070
server.servlet.context-path=/jpatest
server.servlet.session.timeout=15m
这是我拉取并运行 mysql 映像的方法:
$ docker network create image
$ docker run --name mysql --network image -p 3306:3306 -e MYSQL_ROOT_PASSWORD=<pwd> -d mysql:8.3.0
$ docker run -it --network image --rm mysql mysql -hmysql -uroot -p<pwd>
这是我的 DOCKERFILE:
FROM eclipse-temurin:17-jdk-focal as build
WORKDIR /app
COPY gradlew .
COPY gradle gradle
COPY build.gradle settings.gradle ./
COPY src src
RUN ./gradlew clean build
FROM openjdk:17-jdk-slim
WORKDIR /app
COPY --from=build /app/build/libs/*.jar ./
EXPOSE 7070
ENTRYPOINT ["java", "-jar", "jpatest-0.0.1-SNAPSHOT.jar"]
这是docker启动命令:
docker run -it --network image --publish 7070 <image_name>
以下是 spring 启动日志:
. ____ _ __ _ _
/\\ / ___'_ __ _ _(_)_ __ __ _ \ \ \ \
( ( )\___ | '_ | '_| | '_ \/ _` | \ \ \ \
\\/ ___)| |_)| | | | | || (_| | ) ) ) )
' |____| .__|_| |_|_| |_\__, | / / / /
=========|_|==============|___/=/_/_/_/
:: Spring Boot :: (v3.2.2)
2024-07-01T11:07:30.356Z INFO 1 --- [ main] com.test.jpatest.JpatestApplication : Starting JpatestApplication v0.0.1-SNAPSHOT using Java 17.0.2 with PID 1 (/app/jpatest-0.0.1-SNAPSHOT.jar started by root in /app)
2024-07-01T11:07:30.369Z INFO 1 --- [ main] com.test.jpatest.JpatestApplication : No active profile set, falling back to 1 default profile: "default"
2024-07-01T11:07:32.646Z INFO 1 --- [ main] .s.d.r.c.RepositoryConfigurationDelegate : Multiple Spring Data modules found, entering strict repository configuration mode
2024-07-01T11:07:32.652Z INFO 1 --- [ main] .s.d.r.c.RepositoryConfigurationDelegate : Bootstrapping Spring Data JDBC repositories in DEFAULT mode.
2024-07-01T11:07:32.723Z INFO 1 --- [ main] .RepositoryConfigurationExtensionSupport : Spring Data JDBC - Could not safely identify store assignment for repository candidate interface com.test.jpatest.repo.TXBooking_MasterRepository; If you want this repository to be a JDBC repository, consider annotating your entities with one of these annotations: org.springframework.data.relational.core.mapping.Table.
2024-07-01T11:07:32.728Z INFO 1 --- [ main] .RepositoryConfigurationExtensionSupport : Spring Data JDBC - Could not safely identify store assignment for repository candidate interface com.test.jpatest.repo.UserRepository; If you want this repository to be a JDBC repository, consider annotating your entities with one of these annotations: org.springframework.data.relational.core.mapping.Table.
2024-07-01T11:07:32.730Z INFO 1 --- [ main] .s.d.r.c.RepositoryConfigurationDelegate : Finished Spring Data repository scanning in 64 ms. Found 0 JDBC repository interfaces.
2024-07-01T11:07:32.745Z INFO 1 --- [ main] .s.d.r.c.RepositoryConfigurationDelegate : Multiple Spring Data modules found, entering strict repository configuration mode
2024-07-01T11:07:32.747Z INFO 1 --- [ main] .s.d.r.c.RepositoryConfigurationDelegate : Bootstrapping Spring Data JPA repositories in DEFAULT mode.
2024-07-01T11:07:32.985Z INFO 1 --- [ main] .s.d.r.c.RepositoryConfigurationDelegate : Finished Spring Data repository scanning in 229 ms. Found 2 JPA repository interfaces.
2024-07-01T11:07:34.491Z INFO 1 --- [ main] o.s.b.w.embedded.tomcat.TomcatWebServer : Tomcat initialized with port 7070 (http)
2024-07-01T11:07:34.514Z INFO 1 --- [ main] o.apache.catalina.core.StandardService : Starting service [Tomcat]
2024-07-01T11:07:34.517Z INFO 1 --- [ main] o.apache.catalina.core.StandardEngine : Starting Servlet engine: [Apache Tomcat/10.1.18]
2024-07-01T11:07:34.616Z INFO 1 --- [ main] o.a.c.c.C.[.[localhost].[/jpatest] : Initializing Spring embedded WebApplicationContext
2024-07-01T11:07:34.620Z INFO 1 --- [ main] w.s.c.ServletWebServerApplicationContext : Root WebApplicationContext: initialization completed in 4065 ms
2024-07-01T11:07:35.404Z INFO 1 --- [ main] o.hibernate.jpa.internal.util.LogHelper : HHH000204: Processing PersistenceUnitInfo [name: default]
2024-07-01T11:07:35.536Z INFO 1 --- [ main] org.hibernate.Version : HHH000412: Hibernate ORM core version 6.4.1.Final
2024-07-01T11:07:35.610Z INFO 1 --- [ main] o.h.c.internal.RegionFactoryInitiator : HHH000026: Second-level cache disabled
2024-07-01T11:07:36.180Z INFO 1 --- [ main] o.s.o.j.p.SpringPersistenceUnitInfo : No LoadTimeWeaver setup: ignoring JPA class transformer
2024-07-01T11:07:36.244Z INFO 1 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Starting...
2024-07-01T11:07:37.071Z INFO 1 --- [ main] com.zaxxer.hikari.pool.HikariPool : HikariPool-1 - Added connection com.mysql.cj.jdbc.ConnectionImpl@2d8c729f
2024-07-01T11:07:37.077Z INFO 1 --- [ main] com.zaxxer.hikari.HikariDataSource : HikariPool-1 - Start completed.
2024-07-01T11:07:39.256Z INFO 1 --- [ main] o.h.e.t.j.p.i.JtaPlatformInitiator : HHH000489: No JTA platform available (set 'hibernate.transaction.jta.platform' to enable JTA platform integration)
2024-07-01T11:07:39.772Z INFO 1 --- [ main] j.LocalContainerEntityManagerFactoryBean : Initialized JPA EntityManagerFactory for persistence unit 'default'
2024-07-01T11:07:40.413Z INFO 1 --- [ main] o.s.d.j.r.query.QueryEnhancerFactory : JSqlParser is in classpath; If applicable, JSqlParser will be used
2024-07-01T11:07:40.414Z INFO 1 --- [ main] o.s.d.j.r.query.QueryEnhancerFactory : Hibernate is in classpath; If applicable, HQL parser will be used.
2024-07-01T11:07:41.374Z WARN 1 --- [ main] JpaBaseConfiguration$JpaWebConfiguration : spring.jpa.open-in-view is enabled by default. Therefore, database queries may be performed during view rendering. Explicitly configure spring.jpa.open-in-view to disable this warning
2024-07-01T11:07:42.851Z INFO 1 --- [ main] o.s.b.a.e.web.EndpointLinksResolver : Exposing 14 endpoint(s) beneath base path '/actuator'
2024-07-01T11:07:43.022Z INFO 1 --- [ main] o.s.b.w.embedded.tomcat.TomcatWebServer : Tomcat started on port 7070 (http) with context path '/jpatest'
2024-07-01T11:07:43.055Z INFO 1 --- [ main] com.test.jpatest.JpatestApplication : Started JpatestApplication in 14.028 seconds (process running for 15.228)
但是当我使用我定义的端口(7070)访问服务时,它找不到页面。但是当我在图像检查中使用定义的 HostPort 时,该服务运行得非常好。以下是我的服务图像配置的片段。
"Ports": {
"7070/tcp": [
{
"HostIp": "0.0.0.0",
"HostPort": "32770"
},
{
"HostIp": "::",
"HostPort": "32770"
}
]
},
当我使用
http://0.0.0.0:32770/jpatest
或 http://localhost:32770/jpatest
时,该服务可以正常工作
我每次都必须检查容器以获取定义的 HostPort,因为每次我停止和启动服务时它都会不断变化。
有什么办法解决这个问题吗?
当我使用 http://0.0.0.0:32770/jpatest 或 http://localhost:32770/jpatest
时,该服务可以工作我每次都必须检查容器以获取定义的 HostPort,因为每次我停止和启动服务时它都会不断变化。
我希望我的服务可以在我公开的端口(7070)上访问,但事实并非如此。
有什么办法解决这个问题吗?
您需要在服务容器上发布端口,并指定要发布到哪个主机端口。现在您发布了它,但没有指定主机端口,因此 Docker 会为您选择一个。在您的示例中端口 32770。
要将端口 7070 映射到主机端口,请使用
-p <port>:7070
命令上的 --publish <port>:7070
或 docker run
。
因此,要将容器端口发布到主机端口 7070,您可以使用
docker run -it --network image --publish 7070:7070 <image_name>
然后您的服务将在主机上的端口 7070 上可用。