ros*_*hal 4 java spring maven docker spring-boot
我有一个使用Spring Boot + Docker Compose + Eureka的非常简单的演示。
我的服务器在具有以下应用程序属性的端口8671上运行:
server:
port: 8761
eureka:
instance:
prefer-ip-address: true
client:
registerWithEureka: false
fetchRegistry: false
server:
waitTimeInMsWhenSyncEmpty: 0
Run Code Online (Sandbox Code Playgroud)
我的Eureka客户端使用以下应用程序属性在端口9000上运行:
server:
port: 9000
spring:
application:
name: user-registration
eureka:
client:
registerWithEureka: true
fetchRegistry: true
serviceUrl:
defaultZone: http://localhost:8761/eureka/
instance:
prefer-ip-address: true
Run Code Online (Sandbox Code Playgroud)
当我在父Maven项目中启动docker.compose文件时,这是我的docker-compose文件的内容:
eureka-server:
image: rosenthal/eureka-server
ports:
- "8761:8761"
user-registration:
image: rosenthal/user-registration
ports:
- "9000:9000"
links:
- eureka-server
Run Code Online (Sandbox Code Playgroud)
当我首先启动eureka服务器运行应用程序时,客户端通过
mvn spring-boot:run
Run Code Online (Sandbox Code Playgroud)
服务器成功注册了我的客户端(我称其为用户注册)。
当我通过docker-compose运行我的应用程序时,客户端无法向以下输出注册:
DiscoveryClient_USER-REGISTRATION/0fd640cbc3ba:user-registration:9000:
registering service...
user-registration_1 | 2017-06-21 04:36:05.120 ERROR 1 --- [nfoReplicator-0]
c.n.d.s.t.d.RedirectingEurekaHttpClient : Request execution error
user-registration_1 |
user-registration_1 | com.sun.jersey.api.client.ClientHandlerException:
java.net.ConnectException: Connection refused (Connection refused)
Run Code Online (Sandbox Code Playgroud)
我的第一个假设是,在等待服务器启动时,运行docker-compose进入了竞争状态,但是我的eureka客户端似乎心跳不断,试图调用配置了该服务器的服务器。这意味着它只是无法找到我注册的Eureka服务器(并且正在运行,我可以在localhost:8671上导航到它)。
我在这里想念什么?使用本地自带的tomcat容器启动spring-boot,一切都可以在本地正常运行。一旦我开始使用docker-compose进行操作,它就不会工作。
我相信,我意识到了自己的问题。所以docker不在本地主机上运行,而是在我启动docker时分配的公共IP上运行。导航到该ip +端口显示我的服务正在为Eureka Server运行。客户端仍然没有注册。
因此,我将我的eureka客户端的application.yml文件更改为:
serviceUrl:
defaultZone: http://192.168.59.103:8761/eureka/
Run Code Online (Sandbox Code Playgroud)
该IP是我的docker守护程序运行的IP。现在,当我执行docker-compose时,它会丢失第一次注册,但是第二个心跳会接我的客户端。
如何确保客户端等待服务器完全启动?我在摘要文件中使用了正确的docker“链接”字段,但是没有按我希望的那样工作。此外,如何查看defaultZone文件作为我的DOCKER_HOST IP?
生成的docker-compose文件使我一切正常:
eureka-server:
image: thorrism/eureka-server
ports:
- "8761:8761"
user-registration:
image: thorrism/user-registration
ports:
- "9000:9000"
links:
- eureka-server
environment:
EUREKA_CLIENT_SERVICEURL_DEFAULTZONE: http://eureka-server:8761/eureka
Run Code Online (Sandbox Code Playgroud)
设置环境属性以覆盖,eureka.client.serviceUrl.defaultZone以匹配docker compose文件中的服务名称。
eureka-server:
image: rosenthal/eureka-server
ports:
- "8761:8761"
user-registration:
image: rosenthal/user-registration
ports:
- "9000:9000"
environment:
- EUREKA_CLIENT_SERVICEURL_DEFAULTZONE: http://eureka-server:8761/eureka
Run Code Online (Sandbox Code Playgroud)
这将覆盖packaged中的属性application.properties。
注意:如注释中所述,您不需要links撰写文件中的该部分。我删除就是这样。有关此信息,请参阅https://docs.docker.com/compose/networking/。
更新:
看起来对于较新版本的 spring-boot (就我而言2.4.5),此解决方案不起作用。该EUREKA_CLIENT_SERVICEURL_DEFAULTZONE属性不会自动拾取。驼峰式封装存在一个永久性问题,会导致不一致。EUREKA_CLIENT_SERVICEURL_DEFAULTZONE不转换为eureka.client.serviceUrl.defaultZone. 它被转换为eureka.client.serviceurl.defaultzone. 请查看spring-cloud-netflix 的 Github Issue了解更多详细信息。他们现在无法更改参数,因为这将破坏向后兼容性。这是最终对我有用的代码
discovery:
container_name: discovery
build: .
ports:
- "8761:8761"
user-registration:
container_name: user-registration
build: .
ports:
- "8080:8080"
environment:
SPRING_APPLICATION_JSON: '{"eureka":{"client":{"serviceUrl":{"defaultZone":"http://discovery:8761/eureka"}}}}'
Run Code Online (Sandbox Code Playgroud)
为了仅通过环境变量设置此属性,您必须使用 user SPRING_APPLICATION_JSON。它很丑,但很有效。
如果对您有用,这就是我在生产环境中配置它的方式(docker-compose 文件版本 2):
\n\nversion: \'2\'\nservices:\n eureka-server:\n image: rosenthal/eureka-server\n expose:\n - "8761"\n user-registration:\n image: rosenthal/user-registration\n container_name: user-registration\n ports:\n - "9000:8080"\n environment:\n server.port: 8080\n eureka.client.enabled: \'true\'\n eureka.host: eureka-server\n eureka.instance.preferIpAddress: \'true\'\nRun Code Online (Sandbox Code Playgroud)\n\n从文档来看,这就是expose:
\n\n\n公开端口而不将它们发布到主机 - 它们\xe2\x80\x99只能由链接服务访问。只能指定内部端口。
\n
由于所有内容都位于同一网络中,因此容器可以相互查看,而它们之间没有链接。
\n\n边注
\n\n请记住,通过此配置,端口 9000 将在主机上可公开访问,并映射到用户注册容器的 8080 端口。
\n| 归档时间: |
|
| 查看次数: |
5160 次 |
| 最近记录: |