我的Linux主机上的docker容器中运行着一个spring-boot java应用程序。 我要从正在运行的容器连接到主机上,并安装了一个postgresql实例。
我尝试了多种不同的方法(--network =“ host”不是我想要的)。
我的Dockerfile看起来像这样:
FROM openjdk:13-ea-9-jdk-alpine3.9
EXPOSE 8080
CMD mkdir /opt/StatisticalRestService
COPY target/StatisticalRestService-0.0.1-SNAPSHOT.jar
/opt/StatisticalRestService/
COPY DockerConfig/application.yml /opt/StatisticalRestService/
RUN chmod 777 /opt/StatisticalRestService/StatisticalRestService-0.0.1-SNAPSHOT.jar \
&& ls -l /opt/StatisticalRestService/StatisticalRestService-0.0.1-SNAPSHOT.jar \
&& INTERNAL_HOST_IP=$(ip route show default | awk '/default/ {print $3}') \
&& echo "$INTERNAL_HOST_IP host.docker.internal" >> /etc/hosts \
&& chmod +r /etc/hosts \
&& cat /etc/hosts
ENTRYPOINT [ "java", "-jar", "-Dspring.config.location=/opt/StatisticalRestService/application.yml", "/opt/StatisticalRestService/StatisticalRestService-0.0.1-SNAPSHOT.jar" ]
application.yml:
spring:
application:
name: StatisticalRestService
jpa:
database: POSTGRESQL
show-sql: true
hibernate:
ddl-auto: create-drop
datasource:
platform: postgres
#url: jdbc:postgresql://host.docker.internal:5432/StatisticalRestService
url: jdbc:postgresql://172.17.0.1:5432/StatisticalRestService
username: statEntityUser
password: test123
driverClassName: org.postgresql.Driver
我已经配置了postresql的设置listen_addressess ='*',并且以下条目位于pg_hba.conf中:
host all all 172.17.0.0/16 md5
host all all 192.168.1.0/24 md5
ifconfig docker0:
arizon@tuxpad:~/Utveckling/StatisticalRestService$ ifconfig
docker0: flags=4099<UP,BROADCAST,MULTICAST> mtu 1500
inet 172.17.0.1 netmask 255.255.0.0 broadcast 172.17.255.255
inet6 fe80::42:3bff:fe4f:ed34 prefixlen 64 scopeid 0x20<link>
ether 02:42:3b:4f:ed:34 txqueuelen 0 (Ethernet)
RX packets 28 bytes 1506 (1.5 KB)
RX errors 0 dropped 0 overruns 0 frame 0
TX packets 198 bytes 25515 (25.5 KB)
TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
这是构建输出:
arizon@tuxpad:~/Utveckling/StatisticalRestService$ sudo docker build . -t arizon/statisticalrestservice:1.0.0-SNAPSHOT
Sending build context to Docker daemon 223.7MB
Step 1/7 : FROM openjdk:13-ea-9-jdk-alpine3.9
---> 6a6c49978498
Step 2/7 : EXPOSE 8080
---> Running in df7ebc70e950
Removing intermediate container df7ebc70e950
---> 417e50a9f5fd
Step 3/7 : CMD mkdir /opt/StatisticalRestService
---> Running in f33ca0acddf7
Removing intermediate container f33ca0acddf7
---> 59ae394176f3
Step 4/7 : COPY target/StatisticalRestService-0.0.1-SNAPSHOT.jar /opt/StatisticalRestService/
---> 4fbcfeb039f8
Step 5/7 : COPY DockerConfig/application.yml /opt/StatisticalRestService/
---> 244d31fc4755
Step 6/7 : RUN chmod 777 /opt/StatisticalRestService/StatisticalRestService-0.0.1-SNAPSHOT.jar && ls -l /opt/StatisticalRestService/StatisticalRestService-0.0.1-SNAPSHOT.jar && INTERNAL_HOST_IP=$(ip route show default | awk '/default/ {print $3}') && echo "$INTERNAL_HOST_IP host.docker.internal" >> /etc/hosts && chmod +r /etc/hosts && cat /etc/hosts
---> Running in 241f43aebbdc
-rwxrwxrwx 1 root root 35266534 Mar 16 19:52 /opt/StatisticalRestService/StatisticalRestService-0.0.1-SNAPSHOT.jar
127.0.0.1 localhost
::1 localhost ip6-localhost ip6-loopback
fe00::0 ip6-localnet
ff00::0 ip6-mcastprefix
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
172.17.0.2 241f43aebbdc
172.17.0.1 host.docker.internal
Removing intermediate container 241f43aebbdc
---> 5c6c53d8011d
Step 7/7 : ENTRYPOINT [ "java", "-jar", "-Dspring.config.location=/opt/StatisticalRestService/application.yml", "/opt/StatisticalRestService/StatisticalRestService-0.0.1-SNAPSHOT.jar" ]
---> Running in 213a87164e8f
Removing intermediate container 213a87164e8f
---> 802cd987771f
Successfully built 802cd987771f
Successfully tagged arizon/statisticalrestservice:1.0.0-SNAPSHOT
当我使用指向host.docker.internal的数据源URL来运行它时,尽管/ etc / hosts文件的输出确认它在那里,但我还是遇到了UnknownHostException。据我了解,alpine下/etc/nsswitch.conf可能存在问题。我尝试添加文件并从主机粘贴此行:
hosts: files mdns4_minimal [NOTFOUND=return] dns myhostname
无济于事。
当我使用指向172.17.0.1:5432的数据源URL运行它时,连接超时。
我通过将pgadmin指向192.168 IP来验证从主机对psql的访问,以验证listen_addresses ='*'是否有效:
host all all 192.168.1.0/24 md5
它的作用。这是一个不同的入口。
Docker版本:
Client:
Version: 18.09.2
API version: 1.39
Go version: go1.10.4
Git commit: 6247962
Built: Tue Feb 26 23:52:23 2019
OS/Arch: linux/amd64
Experimental: false
Server:
Engine:
Version: 18.09.2
API version: 1.39 (minimum version 1.12)
Go version: go1.10.4
Git commit: 6247962
Built: Wed Feb 13 00:24:14 2019
OS/Arch: linux/amd64
Experimental: false
PostgreSQL版本:
arizon@tuxpad:~/Utveckling/StatisticalRestService$ dpkg --list | grep postgresql
ii postgresql-10 10.6-0ubuntu0.18.04.1 amd64 object-relational SQL database, version 10 server
因此,TL; DR:两个问题: 1.如何让host.docker.internal在Linux下的Docker上工作? 2.如何将容器化的应用程序连接到主机postgresql实例?
答案 0 :(得分:0)
我不是以问问题时的预期方式解决此问题的,但解决了。
我最终也创建了一个postgres容器,该容器具有一定的容量以保持持久数据持久存在。
我为postgres创建了一个Dockerfile,如下所示:
FROM postgres:10-alpine
RUN mkdir /docker-entrypoint-initdb.d/
#COPY initdb.sql /docker-entrypoint-initdb.d/
COPY my-postgres.conf /usr/local/share/postgresql/postgresql.conf
#ENV POSTGRES_USER statEntityUser
#ENV POSTGRES_PASSWORD test123
#ENV POSTGRES_DB StatisticalRestService
ENTRYPOINT ["docker-entrypoint.sh"]
EXPOSE 5432
CMD [ "postgres" ]
initdb.sql脚本仅创建与注释的环境变量相同的东西,即用户,密码和数据库。当数据库启动并准备就绪时,放置在该文件夹中的sql脚本由入口点脚本运行(这是我衍生自的docker映像中的开箱即用功能)。他们被注释掉的原因是它在docker-compose文件中(请参阅下文)。 postgresql.conf基本上是包含在容器中的模板,但未注释listen_addresses ='*'。
我还制作了一个docker-compose.yml,以很好的方式一起运行这两个容器:
version: "3"
services:
statistical-rest-service:
build: ./StatisticalRestService
ports:
- 8081:8080
depends_on:
- postgres
networks:
- statisticsNet
postgres:
container_name: postgres
build: ./Postgres
ports:
- 5433:5432
volumes:
- postgres-volume:/var/lib/postgresql/data
command: postgres -c 'config_file=/usr/local/share/postgresql/postgresql.conf'
networks:
- statisticsNet
environment:
POSTGRES_USER: statEntityUser
POSTGRES_PASSWORD: test123
POSTGRES_DB: StatisticalRestService
networks:
statisticsNet:
volumes:
postgres-volume:
我不确定是必须先创建卷还是将其包含在docker-compose中,但是如果需要,它只是docker volume create postgres-volume
。
有关如何使用图像和/或从中获取图像的Postgres文档:Postgres on docker hub
注意::使用指定的卷启动容器时,犯了一些错误并关闭了该容器,再次启动它时,它不会与该卷上的现有数据库混淆。您可能会陷入一个“悬而未决的卷”的位置,这些卷是您已杀死并删除的旧运行时容器的陈旧版本,但它们可能产生意外行为(对我而言,由于以下原因未创建用户和数据库)这个)。
您可以使用以下命令清除它们:docker volume rm $(docker volume ls -qf dangling=true)
(或在$()中运行命令以列出最终的悬挂卷。
由于我在docker-compose文件中创建了专用的docker网络,因此容器可以按名称(请注意container_name)找到彼此。这使得我的Java的application.yml中的连接网址如下:url: jdbc:postgresql://postgres:5432/StatisticalRestService
我希望有人对此有所帮助:)