mirror of
https://github.com/yeasy/docker_practice.git
synced 2026-03-11 04:14:38 +00:00
Fix naming of the chapter dir
This commit is contained in:
41
09_network/README.md
Normal file
41
09_network/README.md
Normal file
@@ -0,0 +1,41 @@
|
||||
# 网络配置
|
||||
|
||||
Docker 容器需要网络来与外部世界通信、容器之间相互通信以及与宿主机通信。Docker 在安装时会自动配置网络基础设施,大多数情况下开箱即用。
|
||||
|
||||
## 概述
|
||||
|
||||
Docker 启动时自动创建以下网络组件:
|
||||
|
||||
```mermaid
|
||||
graph TD
|
||||
subgraph Host [宿主机]
|
||||
eth0[物理网卡 eth0<br>192.168.1.100]
|
||||
docker0[docker0 网桥<br>172.17.0.1]
|
||||
|
||||
subgraph Containers
|
||||
subgraph ContainerA [容器 A]
|
||||
eth0_A[eth0<br>172.17.0.2]
|
||||
end
|
||||
subgraph ContainerB [容器 B]
|
||||
eth0_B[eth0<br>172.17.0.3]
|
||||
end
|
||||
end
|
||||
|
||||
eth0 <--> docker0
|
||||
docker0 <--> eth0_A
|
||||
docker0 <--> eth0_B
|
||||
end
|
||||
|
||||
Internet((互联网)) <--> eth0
|
||||
```
|
||||
|
||||
本章将详细介绍 Docker 网络配置的各个方面。
|
||||
|
||||
## 本章内容
|
||||
|
||||
* [配置 DNS](dns.md)
|
||||
* [外部访问容器](port_mapping.md)
|
||||
* [网络类型](network_types.md)
|
||||
* [自定义网络](custom_network.md)
|
||||
* [容器互联](container_linking.md)
|
||||
* [网络隔离](network_isolation.md)
|
||||
62
09_network/container_linking.md
Normal file
62
09_network/container_linking.md
Normal file
@@ -0,0 +1,62 @@
|
||||
## 9.5 容器互联
|
||||
|
||||
容器之间的网络通信是 Docker 网络的核心功能之一。本节介绍容器互联的几种方式。
|
||||
|
||||
### 9.5.1 同一网络内的容器
|
||||
|
||||
同一自定义网络内的容器可以直接通过容器名通信,这是推荐的容器互联方式:
|
||||
|
||||
```bash
|
||||
## 创建网络
|
||||
|
||||
$ docker network create app-net
|
||||
|
||||
## 启动应用和数据库
|
||||
|
||||
$ docker run -d --name redis --network app-net redis
|
||||
$ docker run -d --name app --network app-net myapp
|
||||
|
||||
## app 容器中可以用 redis:6379 连接 Redis
|
||||
|
||||
...
|
||||
```
|
||||
|
||||
### 9.5.2 连接到多个网络
|
||||
|
||||
一个容器可以同时连接到多个网络,这对于需要跨网络通信的中间件容器特别有用:
|
||||
|
||||
```bash
|
||||
## 启动容器
|
||||
|
||||
$ docker run -d --name multi-net-container --network frontend nginx
|
||||
|
||||
## 再连接到另一个网络
|
||||
|
||||
$ docker network connect backend multi-net-container
|
||||
|
||||
## 查看容器的网络
|
||||
|
||||
$ docker inspect multi-net-container --format '{{json .NetworkSettings.Networks}}'
|
||||
```
|
||||
|
||||
### 9.5.3 ⚠️ --link 已废弃
|
||||
|
||||
`--link` 是 Docker 早期用于容器互联的方式,**已经被废弃**,不建议在新项目中使用。请使用自定义网络替代:
|
||||
|
||||
```bash
|
||||
## 旧方式(不推荐)
|
||||
|
||||
$ docker run --link db:database myapp
|
||||
|
||||
## 新方式(推荐)
|
||||
|
||||
$ docker network create mynet
|
||||
$ docker run --network mynet --name db postgres
|
||||
$ docker run --network mynet --name app myapp
|
||||
```
|
||||
|
||||
使用自定义网络的优势在于:
|
||||
|
||||
- 原生支持 DNS 解析
|
||||
- 不需要在容器启动时显式声明依赖
|
||||
- 更灵活,可以动态 connect/disconnect
|
||||
93
09_network/custom_network.md
Normal file
93
09_network/custom_network.md
Normal file
@@ -0,0 +1,93 @@
|
||||
## 9.4 用户自定义网络 (推荐)
|
||||
|
||||
在生产环境中,推荐使用用户自定义网络代替默认的 bridge 网络。自定义网络提供了更好的隔离性和服务发现能力。
|
||||
|
||||
### 9.4.1 为什么要用自定义网络
|
||||
|
||||
默认 bridge 网络存在以下局限,而自定义网络可以很好地解决这些问题:
|
||||
|
||||
| 问题 | 自定义网络的优势 |
|
||||
|------|-----------------|
|
||||
| 只能用 IP 通信 | 支持容器名 DNS 解析 |
|
||||
| 所有容器在同一网络 | 更好的隔离性 |
|
||||
| 需要 --link (已废弃)| 原生支持服务发现 |
|
||||
|
||||
### 9.4.2 创建自定义网络
|
||||
|
||||
使用 `docker network create` 命令可以创建自定义网络:
|
||||
|
||||
```bash
|
||||
## 创建网络
|
||||
|
||||
$ docker network create mynet
|
||||
|
||||
## 查看网络详情
|
||||
|
||||
$ docker network inspect mynet
|
||||
```
|
||||
|
||||
### 9.4.3 使用自定义网络
|
||||
|
||||
启动容器时通过 `--network` 参数指定连接的网络:
|
||||
|
||||
```bash
|
||||
## 启动容器并连接到自定义网络
|
||||
|
||||
$ docker run -d --name web --network mynet nginx
|
||||
$ docker run -d --name db --network mynet postgres
|
||||
|
||||
## 在 web 容器中可以直接用容器名访问 db
|
||||
|
||||
$ docker exec web ping db
|
||||
PING db (172.18.0.3): 56 data bytes
|
||||
64 bytes from 172.18.0.3: seq=0 ttl=64 time=0.083 ms
|
||||
```
|
||||
|
||||
### 9.4.4 容器名 DNS 解析
|
||||
|
||||
自定义网络自动提供 DNS 服务。Docker 守护进程在 `127.0.0.11` 运行了一个嵌入式 DNS 服务器,容器内的 DNS 请求会被转发到这里:
|
||||
|
||||
- 如果是容器名,解析为容器 IP
|
||||
- 如果是外部域名 (如 google.com),转发给上游 DNS
|
||||
|
||||
```mermaid
|
||||
flowchart LR
|
||||
subgraph MyNet ["mynet 网络 : web 容器可以用 'db' 作为主机名访问 db 容器"]
|
||||
direction LR
|
||||
Web["web<br/>172.18.0.2"] -- "DNS: 'db' → 172.18.0.3" --> DB["db<br/>172.18.0.3"]
|
||||
end
|
||||
```
|
||||
|
||||
### 9.4.5 常用网络命令
|
||||
|
||||
以下是 Docker 网络管理中常用的命令:
|
||||
|
||||
```bash
|
||||
## 列出网络
|
||||
|
||||
$ docker network ls
|
||||
|
||||
## 创建网络
|
||||
|
||||
$ docker network create mynet
|
||||
|
||||
## 查看网络详情
|
||||
|
||||
$ docker network inspect mynet
|
||||
|
||||
## 连接容器到网络
|
||||
|
||||
$ docker network connect mynet mycontainer
|
||||
|
||||
## 断开网络连接
|
||||
|
||||
$ docker network disconnect mynet mycontainer
|
||||
|
||||
## 删除网络
|
||||
|
||||
$ docker network rm mynet
|
||||
|
||||
## 清理未使用的网络
|
||||
|
||||
$ docker network prune
|
||||
```
|
||||
106
09_network/dns.md
Normal file
106
09_network/dns.md
Normal file
@@ -0,0 +1,106 @@
|
||||
## 9.2 配置 DNS
|
||||
|
||||
Docker 容器的 DNS 配置决定了容器如何解析域名。理解 DNS 机制对于容器网络的正确配置至关重要。
|
||||
|
||||
### 9.2.1 容器的 DNS 机制
|
||||
|
||||
Docker 容器的 DNS 配置有两种情况:
|
||||
|
||||
1. **默认 Bridge 网络**:继承宿主机的 DNS 配置 (`/etc/resolv.conf`)。
|
||||
2. **自定义网络** (推荐):使用 Docker 嵌入式 DNS 服务器 (Embedded DNS),支持通过 **容器名** 进行服务发现。
|
||||
|
||||
---
|
||||
|
||||
### 9.2.2 嵌入式 DNS
|
||||
|
||||
这是 Docker 网络最强大的功能之一。在自定义网络中,容器可以通过 "名字" 找到彼此,而不需要知道对方的 IP (因为 IP 可能会变)。
|
||||
|
||||
```bash
|
||||
## 1. 创建自定义网络
|
||||
|
||||
$ docker network create mynet
|
||||
|
||||
## 2. 启动容器 web 并加入网络
|
||||
|
||||
$ docker run -d --name web --network mynet nginx
|
||||
|
||||
## 3. 启动容器 client 并尝试 ping web
|
||||
|
||||
$ docker run -it --rm --network mynet alpine ping web
|
||||
PING web (172.18.0.2): 56 data bytes
|
||||
64 bytes from 172.18.0.2: seq=0 ttl=64 time=0.074 ms
|
||||
```
|
||||
|
||||
**原理**:
|
||||
Docker 守护进程在 `127.0.0.11` 运行了一个 DNS 服务器。容器内的 DNS 请求会被转发到这里。如果是容器名,解析为容器 IP;如果是外部域名 (如 google.com),转发给上游 DNS。
|
||||
|
||||
---
|
||||
|
||||
### 9.2.3 配置 DNS 参数
|
||||
|
||||
如果你需要手动配置容器的 DNS (例如使用内网 DNS 服务器),可以在 `docker run` 中使用以下参数:
|
||||
|
||||
#### 1. --dns
|
||||
|
||||
指定 DNS 服务器 IP。
|
||||
|
||||
```bash
|
||||
$ docker run -it --dns=114.114.114.114 ubuntu cat /etc/resolv.conf
|
||||
nameserver 114.114.114.114
|
||||
```
|
||||
|
||||
#### 2. --dns-search
|
||||
|
||||
指定 DNS 搜索域。例如设置为 `example.com`,则 `ping host` 会尝试解析 `host.example.com`。
|
||||
|
||||
```bash
|
||||
$ docker run --dns-search=example.com myapp
|
||||
```
|
||||
|
||||
#### 3. --hostname (-h)
|
||||
|
||||
设置容器的主机名。
|
||||
|
||||
```bash
|
||||
$ docker run -h myweb nginx
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### 9.2.4 全局 DNS 配置
|
||||
|
||||
如果希望所有容器都使用特定的 DNS 服务器 (而不是继承宿主机),可以修改 `/etc/docker/daemon.json`:
|
||||
|
||||
```json
|
||||
{
|
||||
"dns": [
|
||||
"114.114.114.114",
|
||||
"8.8.8.8"
|
||||
]
|
||||
}
|
||||
```
|
||||
|
||||
修改后需要重启 Docker 服务:`systemctl restart docker`。
|
||||
|
||||
---
|
||||
|
||||
### 9.2.5 常见问题
|
||||
|
||||
以下是使用容器 DNS 时常见的问题及解决方法:
|
||||
|
||||
#### Q:容器无法解析域名
|
||||
|
||||
**现象**:`ping www.baidu.com` 失败,但 `ping 8.8.8.8` 成功。**解决**:
|
||||
|
||||
1. 宿主机的 `/etc/resolv.conf` 可能有问题 (例如使用了本地回环地址 127.0.0.53,特别是 Ubuntu 系统)。Docker 可能会尝试修复,但有时会失败。
|
||||
2. 尝试手动指定 DNS:`docker run --dns 8.8.8.8 ...`
|
||||
3. 检查防火墙是否拦截了 UDP 53 端口。
|
||||
|
||||
#### Q:无法通过容器名通信
|
||||
|
||||
**现象**:`ping db` 提示 `bad address 'db'`。**原因**:
|
||||
|
||||
- 你可能在使用 **默认的 bridge 网络**。默认 bridge 网络 **不支持** 通过容器名进行 DNS 解析 (这是一个历史遗留设计)。
|
||||
- **解决**:使用自定义网络 (`docker network create ...`)。
|
||||
|
||||
---
|
||||
81
09_network/network_isolation.md
Normal file
81
09_network/network_isolation.md
Normal file
@@ -0,0 +1,81 @@
|
||||
## 9.7 网络隔离
|
||||
|
||||
Docker 网络提供了天然的隔离能力,不同网络之间的容器默认无法通信。这是 Docker 网络安全的重要基础。
|
||||
|
||||
### 9.7.1 网络隔离原理
|
||||
|
||||
不同网络之间默认隔离,容器只能与同一网络中的容器直接通信:
|
||||
|
||||
```bash
|
||||
## 创建两个网络
|
||||
|
||||
$ docker network create frontend
|
||||
$ docker network create backend
|
||||
|
||||
## 容器 A 在 frontend
|
||||
|
||||
$ docker run -d --name web --network frontend nginx
|
||||
|
||||
## 容器 B 在 backend
|
||||
|
||||
$ docker run -d --name db --network backend postgres
|
||||
|
||||
## web 无法直接访问 db(不同网络)
|
||||
|
||||
$ docker exec web ping db
|
||||
ping: db: Name or service not known
|
||||
```
|
||||
|
||||
### 9.7.2 安全优势
|
||||
|
||||
这种隔离机制带来以下安全优势:
|
||||
|
||||
| 场景 | 说明 |
|
||||
|------|------|
|
||||
| **前后端分离** | 前端容器无法直接访问数据库网络 |
|
||||
| **微服务隔离** | 不同微服务组可以使用不同网络 |
|
||||
| **多租户** | 不同租户的容器在不同网络中完全隔离 |
|
||||
| **最小权限** | 容器只能访问必要的网络资源 |
|
||||
|
||||
### 9.7.3 跨网络通信
|
||||
|
||||
如果确实需要某个容器跨网络通信,可以将其同时连接到多个网络:
|
||||
|
||||
```bash
|
||||
## 创建一个中间件容器,连接到两个网络
|
||||
|
||||
$ docker run -d --name api --network frontend myapi
|
||||
$ docker network connect backend api
|
||||
|
||||
## 现在 api 容器既可以访问 frontend 中的 web,也可以访问 backend 中的 db
|
||||
```
|
||||
|
||||
这种方式让你可以精确控制哪些容器可以跨网络通信,遵循最小权限原则。
|
||||
|
||||
### 9.7.4 典型网络架构
|
||||
|
||||
一个典型的多层应用网络架构如下:
|
||||
|
||||
```mermaid
|
||||
graph TD
|
||||
subgraph FrontendNet ["frontend 网络"]
|
||||
LB["负载均衡器"]
|
||||
Web1["Web 服务器 1"]
|
||||
Web2["Web 服务器 2"]
|
||||
end
|
||||
|
||||
subgraph BackendNet ["backend 网络"]
|
||||
API["API 服务器"]
|
||||
DB["数据库"]
|
||||
Cache["Redis 缓存"]
|
||||
end
|
||||
|
||||
LB --> Web1
|
||||
LB --> Web2
|
||||
Web1 -.-> API
|
||||
Web2 -.-> API
|
||||
API --> DB
|
||||
API --> Cache
|
||||
```
|
||||
|
||||
在这种架构中,API 服务器同时连接到 `frontend` 和 `backend` 网络,充当两个网络之间的桥梁。负载均衡器和 Web 服务器无法直接访问数据库,增强了安全性。
|
||||
78
09_network/network_types.md
Normal file
78
09_network/network_types.md
Normal file
@@ -0,0 +1,78 @@
|
||||
## 9.3 Docker 网络类型
|
||||
|
||||
Docker 提供了多种网络驱动来满足不同的使用场景。安装 Docker 后,系统会自动创建三个默认网络:
|
||||
|
||||
```bash
|
||||
$ docker network ls
|
||||
NETWORK ID NAME DRIVER SCOPE
|
||||
abc123... bridge bridge local
|
||||
def456... host host local
|
||||
ghi789... none null local
|
||||
```
|
||||
|
||||
### 9.3.1 网络类型对比
|
||||
|
||||
各网络类型的特点和适用场景如下:
|
||||
|
||||
| 网络类型 | 说明 | 适用场景 |
|
||||
|---------|------|---------|
|
||||
| **bridge** | 默认类型,容器连接到虚拟网桥 | 大多数单机场景 |
|
||||
| **host** | 容器直接使用宿主机网络栈 | 需要最高网络性能时 |
|
||||
| **none** | 禁用网络 | 完全隔离的容器 |
|
||||
| **overlay** | 跨主机网络 | Docker Swarm 集群 |
|
||||
| **macvlan** | 容器拥有独立 MAC 地址 | 需要直接接入物理网络 |
|
||||
|
||||
### 9.3.2 Bridge 网络 (默认)
|
||||
|
||||
Bridge 是 Docker 默认使用的网络模式。Docker 启动时会自动创建 `docker0` 虚拟网桥,所有未指定网络的容器都会连接到这个网桥上。
|
||||
|
||||
核心组件如下:
|
||||
|
||||
| 组件 | 说明 |
|
||||
|------|------|
|
||||
| **docker0** | 虚拟网桥,充当交换机角色 |
|
||||
| **veth pair** | 虚拟网卡对,一端在容器内,一端连接网桥 |
|
||||
| **容器 eth0** | 容器内的网卡 |
|
||||
| **IP 地址** | 自动从 172.17.0.0/16 网段分配 |
|
||||
|
||||
### 9.3.3 Host 网络
|
||||
|
||||
使用 `--network host` 参数启动的容器会直接使用宿主机的网络栈,不再拥有独立的网络命名空间。容器内的端口就是宿主机的端口,无需端口映射。
|
||||
|
||||
```bash
|
||||
$ docker run -d --network host nginx
|
||||
```
|
||||
|
||||
这种模式下网络性能最高,但容器之间和宿主机之间没有网络隔离。
|
||||
|
||||
### 9.3.4 None 网络
|
||||
|
||||
使用 `--network none` 参数启动的容器只有 `lo` 回环网卡,完全没有外部网络连接。适用于只需要运行计算任务、不需要网络的容器。
|
||||
|
||||
```bash
|
||||
$ docker run -it --network none alpine ip addr
|
||||
1: lo: <LOOPBACK,UP,LOWER_UP> ...
|
||||
inet 127.0.0.1/8 scope host lo
|
||||
```
|
||||
|
||||
### 9.3.5 数据流向
|
||||
|
||||
容器网络中的数据流向可以分为以下几种情况:
|
||||
|
||||
```mermaid
|
||||
flowchart LR
|
||||
subgraph Comm1 ["容器间通信"]
|
||||
direction LR
|
||||
C1A["容器 A (172.17.0.2)"] --> D0A["docker0"] --> C1B["容器 B (172.17.0.3)"]
|
||||
end
|
||||
|
||||
subgraph Comm2 ["访问外网"]
|
||||
direction LR
|
||||
C2A["容器 A (172.17.0.2)"] --> D0B["docker0"] --> Eth0A["eth0"] --> InternetA["互联网"]
|
||||
end
|
||||
|
||||
subgraph Comm3 ["被外部访问,需端口映射"]
|
||||
direction LR
|
||||
Req["外部请求"] --> Eth0B["eth0"] --> D0C["docker0"] --> C3A["容器 A"]
|
||||
end
|
||||
```
|
||||
144
09_network/port_mapping.md
Normal file
144
09_network/port_mapping.md
Normal file
@@ -0,0 +1,144 @@
|
||||
## 9.6 外部访问容器
|
||||
|
||||
容器运行在自己的隔离网络环境中 (通常是 Bridge 模式)。为了让外部网络访问容器内的服务,我们需要将容器的端口映射到宿主机的端口。
|
||||
|
||||
### 9.6.1 为什么要映射端口
|
||||
|
||||
容器的网络访问规则如下:
|
||||
|
||||
- **容器之间**:可以通过 IP 或容器名 (自定义网络) 互通。
|
||||
- **宿主机访问容器**:可以通过容器 IP 访问。
|
||||
- **外部网络访问容器**:❌ 默认无法直接访问。
|
||||
|
||||
为了让外部 (如你的浏览器、其他局域网机器) 访问容器内的服务,我们需要将容器的端口 **映射** 到宿主机的端口。
|
||||
|
||||
```mermaid
|
||||
flowchart TD
|
||||
User["外部用户 (Browser)"] --> Host["宿主机 (localhost:8080)"]
|
||||
Host --> Proxy["Docker Proxy<br/>端口映射 (8080 -> 80)"]
|
||||
Proxy --> Container["容器 (Class B: 80)"]
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### 9.6.2 端口映射方式
|
||||
|
||||
Docker 提供了多种方式来指定端口映射。
|
||||
|
||||
#### 1. 指定映射
|
||||
|
||||
使用 `-p <宿主机端口>:<容器端口>` 格式:
|
||||
|
||||
```bash
|
||||
## 将宿主机的 8080 端口映射到容器的 80 端口
|
||||
|
||||
$ docker run -d -p 8080:80 nginx
|
||||
```
|
||||
|
||||
此时访问 `http://localhost:8080` 即可看到 Nginx 页面。
|
||||
|
||||
**多种格式**:
|
||||
|
||||
| 格式 | 含义 | 示例 |
|
||||
|------|------|------|
|
||||
| `ip:hostPort:containerPort` | 绑定指定 IP 的特定端口 | `-p 127.0.0.1:8080:80` (仅本机访问) |
|
||||
| `ip::containerPort` | 绑定指定 IP 的随机端口 | `-p 127.0.0.1::80` |
|
||||
| `hostPort:containerPort` | 绑定所有 IP (0.0.0.0) 的特定端口 | `-p 8080:80` (默认) |
|
||||
| `containerPort` | 绑定所有 IP 的随机端口 | `-p 80` |
|
||||
|
||||
#### 2. 随机映射
|
||||
|
||||
如果不关心宿主机使用哪个端口,可以使用随机映射。使用 `-P` (大写) 参数,Docker 会随机映射 Dockerfile 中 `EXPOSE` 指令暴露的所有端口到宿主机的高端口 (49000-49900)。
|
||||
|
||||
```bash
|
||||
$ docker run -d -P nginx
|
||||
```
|
||||
|
||||
查看映射结果:
|
||||
|
||||
```bash
|
||||
$ docker ps
|
||||
CONTAINER ID PORTS
|
||||
abc123456 0.0.0.0:49153->80/tcp
|
||||
```
|
||||
|
||||
此时 Nginx 被映射到了宿主机的 49153 端口。
|
||||
|
||||
---
|
||||
|
||||
### 9.6.3 查看端口映射
|
||||
|
||||
可以使用以下命令查看容器的端口映射:
|
||||
|
||||
#### docker port
|
||||
|
||||
运行 `docker port` 可以查看到指定容器的端口映射情况:
|
||||
|
||||
```bash
|
||||
$ docker port mycontainer
|
||||
80/tcp -> 0.0.0.0:8080
|
||||
80/tcp -> [::]:8080
|
||||
```
|
||||
|
||||
#### docker ps
|
||||
|
||||
运行 `docker ps` 可以查看到所有容器的端口映射列表:
|
||||
|
||||
```bash
|
||||
$ docker ps
|
||||
CONTAINER ID IMAGE PORTS NAMES
|
||||
abc123456 nginx 0.0.0.0:8080->80/tcp web
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### 9.6.4 最佳实践与安全
|
||||
|
||||
在配置端口映射时,需要注意以下安全事项:
|
||||
|
||||
#### 1. 限制监听 IP
|
||||
|
||||
默认情况下,`-p 8080:80` 会监听 `0.0.0.0:8080`,这意味着任何人只要能连接你的宿主机 IP,就能访问该服务。
|
||||
|
||||
如果不希望对外暴露 (例如数据库服务),应绑定到 `127.0.0.1`:
|
||||
|
||||
```bash
|
||||
## 仅允许本机访问
|
||||
|
||||
$ docker run -d -p 127.0.0.1:3306:3306 mysql
|
||||
```
|
||||
|
||||
#### 2. 避免端口冲突
|
||||
|
||||
如果宿主机 8080 已经被占用了,容器将无法启动。
|
||||
|
||||
**解决**:
|
||||
|
||||
- 更换宿主机端口:`-p 8081:80`
|
||||
- 让 Docker 自动分配:`-p 80`
|
||||
|
||||
#### 3. UDP 映射
|
||||
|
||||
默认是 TCP 协议。如果要映射 UDP 服务 (如 DNS,Syslog):
|
||||
|
||||
```bash
|
||||
$ docker run -d -p 53:53/udp dns-server
|
||||
```
|
||||
|
||||
---
|
||||
|
||||
### 9.6.5 实现原理
|
||||
|
||||
Docker 使用 `docker-proxy` 进程 (用户态) 或 `iptables` DNAT 规则 (内核态) 来实现端口转发。
|
||||
|
||||
当流量到达宿主机端口时,iptables 规则将其目标地址修改为容器 IP 并转发:
|
||||
|
||||
```bash
|
||||
## 简化的 iptables 逻辑
|
||||
|
||||
iptables -t nat -A DOCKER -p tcp --dport 8080 -j DNAT --to-destination 172.17.0.2:80
|
||||
```
|
||||
|
||||
这也是为什么你在容器内部看到的访问来源 IP 通常是网关 IP (如 172.17.0.1),而不是真实的外部 Client IP (除非使用 host 网络模式)。
|
||||
|
||||
---
|
||||
24
09_network/summary.md
Normal file
24
09_network/summary.md
Normal file
@@ -0,0 +1,24 @@
|
||||
## 9.8 本章小结
|
||||
|
||||
本章介绍了 Docker 网络配置的各个方面:
|
||||
|
||||
| 概念 | 要点 |
|
||||
|------|------|
|
||||
| **DNS 配置** | 自定义网络支持嵌入式 DNS,可通过容器名解析 |
|
||||
| **网络类型** | bridge (默认)、host、none、overlay、macvlan |
|
||||
| **自定义网络** | 推荐使用,支持容器名 DNS 解析和更好的隔离 |
|
||||
| **容器互联** | 同一自定义网络内容器可直接通过容器名通信 |
|
||||
| **端口映射** | `-p 宿主机端口:容器端口` 暴露服务到外部 |
|
||||
| **网络隔离** | 不同网络默认隔离,增强安全性 |
|
||||
| **--link** | 已废弃,使用自定义网络替代 |
|
||||
|
||||
### 9.8.1 延伸阅读
|
||||
|
||||
- [配置 DNS](dns.md):自定义 DNS 设置
|
||||
- [网络类型](network_types.md):Bridge、Host、None 等网络模式
|
||||
- [自定义网络](custom_network.md):创建和管理自定义网络
|
||||
- [容器互联](container_linking.md):容器间通信方式
|
||||
- [端口映射](port_mapping.md):高级端口配置
|
||||
- [网络隔离](network_isolation.md):网络安全与隔离策略
|
||||
- [EXPOSE 指令](../07_dockerfile/7.9_expose.md):在 Dockerfile 中声明端口
|
||||
- [Compose 网络](../11_compose/10.5_compose_file.md):Compose 中的网络配置
|
||||
Reference in New Issue
Block a user