Compose 中的网络
重要
Docker 文档参考并描述了 Compose V2 功能。
自 2023 年 7 月起,Compose V1 已停止接收更新,并且不再包含在新的 Docker Desktop 版本中。Compose V2 已取代它,现已集成到所有当前的 Docker Desktop 版本中。更多信息,请参阅迁移到 Compose V2。
默认情况下,Compose 为你的应用设置单个网络。服务的每个容器都加入默认网络,并且可以通过该网络上的其他容器访问,也可以通过服务的名称被发现。
注意
你的应用网络名称基于“项目名称”,而项目名称基于其所在目录的名称。你可以使用
--project-name
标志或COMPOSE_PROJECT_NAME
环境变量来覆盖项目名称。
例如,假设你的应用位于名为 myapp
的目录中,并且你的 compose.yaml
如下所示
services:
web:
build: .
ports:
- "8000:8000"
db:
image: postgres
ports:
- "8001:5432"
当你运行 docker compose up
时,会发生以下情况
- 创建名为
myapp_default
的网络。 - 使用
web
的配置创建一个容器。它以web
的名称加入myapp_default
网络。 - 使用
db
的配置创建一个容器。它以db
的名称加入myapp_default
网络。
现在每个容器都可以查找服务名称 web
或 db
并获取相应容器的 IP 地址。例如,web
的应用程序代码可以连接到 URL postgres://db:5432
并开始使用 Postgres 数据库。
区分 HOST_PORT
和 CONTAINER_PORT
至关重要。在上面的例子中,对于 db
,HOST_PORT
是 8001
,而容器端口是 5432
(Postgres 默认)。网络化的服务间通信使用 CONTAINER_PORT
。当定义了 HOST_PORT
时,该服务也可以在 swarm 外部访问。
在 web
容器内,你连接到 db
的连接字符串将类似于 postgres://db:5432
,而在主机上,连接字符串将类似于 postgres://{DOCKER_IP}:8001
,例如如果你的容器在本地运行,则是 postgres://localhost:8001
。
更新网络上的容器
如果你更改了服务的配置并运行 docker compose up
进行更新,旧容器将被移除,新容器以不同的 IP 地址但相同的名称加入网络。正在运行的容器可以查找该名称并连接到新地址,但旧地址将不再可用。
如果任何容器与旧容器有打开的连接,这些连接将被关闭。容器有责任检测这种情况,再次查找名称并重新连接。
提示
在可能的情况下,尽量通过名称而不是 IP 地址引用容器。否则,你需要不断更新使用的 IP 地址。
链接容器
Links 允许你定义额外的别名,其他服务可以通过这些别名访问某个服务。它们并非服务间通信所必需的。默认情况下,任何服务都可以通过其名称访问其他任何服务。在以下示例中,可以从 web
通过主机名 db
和 database
访问 db
:
services:
web:
build: .
links:
- "db:database"
db:
image: postgres
有关更多信息,请参阅links 参考。
多主机网络
当在启用了Swarm 模式的 Docker Engine 上部署 Compose 应用时,你可以使用内置的 overlay
驱动来启用多主机通信。
Overlay 网络总是被创建为 attachable
。你可以选择将attachable
属性设置为 false
。
请查阅Swarm 模式章节以了解如何设置 Swarm 集群,以及多主机网络入门以了解多主机 overlay 网络。
指定自定义网络
除了使用默认的应用网络,你还可以使用顶级 networks
键指定自己的网络。这允许你创建更复杂的拓扑,并指定自定义网络驱动和选项。你也可以使用它将服务连接到不由 Compose 管理的外部创建的网络。
每个服务都可以使用服务级 networks
键指定要连接到哪些网络,该键是一个名称列表,引用顶级 networks
键下的条目。
以下示例显示了一个定义了两个自定义网络的 Compose 文件。proxy
服务与 db
服务是隔离的,因为它们不共享同一个网络。只有 app
可以与两者通信。
services:
proxy:
build: ./proxy
networks:
- frontend
app:
build: ./app
networks:
- frontend
- backend
db:
image: postgres
networks:
- backend
networks:
frontend:
# Specify driver options
driver: bridge
driver_opts:
com.docker.network.bridge.host_binding_ipv4: "127.0.0.1"
backend:
# Use a custom driver
driver: custom-driver
可以通过为每个连接的网络设置ipv4_address 和/或 ipv6_address 来配置网络的静态 IP 地址。
网络也可以指定自定义名称
services:
# ...
networks:
frontend:
name: custom_frontend
driver: custom-driver-1
配置默认网络
除了指定自己的网络外,你还可以通过在 networks
下定义一个名为 default
的条目来更改应用范围默认网络的设置。
services:
web:
build: .
ports:
- "8000:8000"
db:
image: postgres
networks:
default:
# Use a custom driver
driver: custom-driver-1
使用预先存在的网络
如果你想让你的容器加入一个预先存在的网络,请使用external
选项
services:
# ...
networks:
network1:
name: my-pre-existing-network
external: true
Compose 不会尝试创建一个名为 [项目名]_default
的网络,而是查找名为 my-pre-existing-network
的网络,并将你的应用容器连接到该网络。
更多参考信息
有关可用的网络配置选项的完整详细信息,请参阅以下参考资料