1. 相关概念
1.1 什么是Docker
Docker是一种开源的应用容器引擎,基于Go语言开发。它可以让开发者打包应用以及应用的依赖包到一个轻量级、可移植的容器中,然后发布到任何流行的Linux机器或Windows机器上,也可以实现虚拟化。它是一种容器化技术的具体实现。
1.2 什么是Docker Compose
Docker Compose 是 Docker 官方编排工具,用于定义和运行多容器 Docker 应用程序。通过 docker-compose.yml 文件来配置应用程序的服务,然后使用单个命令即可创建并启动所有服务。它是一种编排技术的具体实现。
1.3 核心概念
- 镜像(Image): Docker镜像是一个只读的模板,用来创建Docker容器。例如,一个镜像可以包含一个完整的Ubuntu操作系统环境。
- 容器(Container): Docker利用容器来运行应用。容器是从镜像创建的运行实例,可以被启动、开始、停止、删除。
- 仓库(Repository): 集中存放镜像文件的场所。每个仓库可以包含多个标签(tag)的镜像。
- Dockerfile: 一个文本文件,包含了一条条的指令,用于创建镜像。
- docker-compose.yml: 定义服务和项目配置的文件,包含端口映射、路径映射等,用于创建容器。
- 服务(Service): 应用中的某个服务组件。
- 项目(Project): 完整的应用项目,包含多个服务,在
docker-compose.yml文件中定义。 - 容器化(Containerizatio): 一种操作系统级别的虚拟化技术,将应用程序及其依赖打包到轻量级、可移植的容器中。
- 编排(Orchestration): 自动化容器的部署、管理、扩展和联网的过程。
2. 软件架构
2.1 Docker架构组件
Docker Client -> Docker Daemon -> Container Runtime -> Container
Docker Compose CLI -> Docker Engine API -> Docker Daemon -> Containers
- Docker客户端(Docker Client): 用户与Docker交互的主要方式,通过命令行或其他工具发送指令。
- Docker守护进程(Docker Daemon): 运行在主机上的后台进程,负责管理Docker对象如镜像、容器、网络和卷等。
- Docker注册中心(Registry): 存储Docker镜像的地方,Docker Hub是最常用的公共注册中心。
- Container Runtime: 容器运行时环境
graph TDA[Docker Client] --> B[Docker Daemon]B --> C[Container Runtime<br/>containerd/runc]subgraph "Docker Daemon"BCendsubgraph "镜像管理"D[Docker Registry<br/>Docker Hub/私有仓库] --> E[Image Layers]E --> F[Local Image Cache]B --> FF --> G[Container]endsubgraph "Docker Compose编排"H[docker-compose.yml] --> I[Docker Compose CLI]I --> J[Project<br/>多服务应用]J --> K[Service 1<br/>Web App]J --> L[Service 2<br/>Database]J --> M[Service 3<br/>Cache]endsubgraph "容器运行时"G --> N[Namespaces<br/>隔离]G --> O[CGroups<br/>资源限制]G --> P[Union FS<br/>文件系统]endsubgraph "网络与存储"Q[Docker Network] --> KQ --> LQ --> MR[Docker Volume] --> LendK --> BL --> BM --> Bstyle H fill:#e1f5festyle I fill:#e1f5festyle J fill:#f3e5f5style K fill:#f3e5f5style L fill:#f3e5f5style M fill:#f3e5f5style D fill:#fff3e0style E fill:#fff3e0style F fill:#fff3e0
2.2 底层技术支持
- Namespaces: 提供隔离的工作区,包括PID、Network、Mount、UTS、IPC、User等命名空间。
- Control Groups(cgroups): 限制和隔离资源使用(CPU、内存、磁盘I/O等)。
- Union File Systems: 用于构建层次化的文件系统,支持Docker镜像的轻量级和快速。
3. 关键交互流程
3.1. 镜像生命周期
Docker Client→Docker Daemon: 发送pull命令Docker Daemon→Docker Registry: 下载镜像层Docker Registry→Docker Daemon: 返回镜像数据Docker Daemon→ 本地存储: 缓存镜像层
3.2. 容器运行流程
Docker Client→Docker Daemon: 发送run命令Docker Daemon→Local Image Cache: 获取镜像Docker Daemon→Container Runtime: 创建容器Container Runtime→ 内核: 应用Namespaces和CGroups
3.3 Docker Compose编排流程
Docker Compose CLI→ 解析docker-compose.ymlDocker Compose CLI→Docker Daemon: 依次创建服务Docker Daemon→ 自动创建: 网络、数据卷等资源Docker Compose CLI→ 管理: 服务间的依赖关系和生命周期
4. 基本原理
4.1 容器化与虚拟化区别
| 特性 | 容器化 | 虚拟化 |
|---|---|---|
| 启动速度 | 秒级 | 分钟级 |
| 硬盘使用 | MB级别 | GB级别 |
| 性能 | 接近原生 | 有一定损耗 |
| 系统支持量 | 单机支持上千个容器 | 一般几十个 |
4.2 镜像分层原理
Docker镜像采用分层存储架构:
- 每个镜像由一系列只读层组成
- 每一层代表Dockerfile中的一条指令
- 容器运行时添加一个可读写层(RW layer)
FROM ubuntu:18.04 # Layer 1
COPY . /app # Layer 2
RUN make /app # Layer 3
CMD ["python", "/app/app.py"] # Layer 4
4.3 容器生命周期管理
- 创建:
docker create - 启动:
docker start - 运行:
docker run - 暂停:
docker pause - 恢复:
docker unpause - 停止:
docker stop - 重启:
docker restart - 删除:
docker rm
4.4 服务间通信原理
- 默认网络: Docker Compose 会自动创建一个默认网络,所有服务都在此网络中
- 服务发现: 服务可以通过服务名称进行DNS解析和通信
- 网络隔离: 不同项目的服务默认网络隔离
5. Docker + Docker Compose实践
5.1 如何搭建Docker环境?
######## 一、安装docker 和 docker compose
【CentOS系统】
# 1. 安装Docker服务
sudo yum update -y
sudo yum install -y docker# 2. 启动Docker服务并实现开机自启动
sudo systemctl start docker
sudo systemctl enable docker# 3. 安装Docker Compose
sudo curl -L "https://github.com/docker/compose/releases/download/v2.20.0/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose【Ubuntu系统】
## 1. 安装Docker服务
# 更新apt包索引
sudo apt update -y# 安装必要的包
sudo apt install -y apt-transport-https ca-certificates curl gnupg lsb-release# 添加Docker官方GPG密钥
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /usr/share/keyrings/docker-archive-keyring.gpg
或
curl -fsSL --tlsv1.2 https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /usr/share/keyrings/docker-archive-keyring.gpg# 添加Docker仓库
echo "deb [arch=$(dpkg --print-architecture) signed-by=/usr/share/keyrings/docker-archive-keyring.gpg] https://download.docker.com/linux/ubuntu $(lsb_release -cs) stable" | sudo tee /etc/apt/sources.list.d/docker.list > /dev/null# 更新apt包索引
sudo apt update -y# 安装Docker Engine
sudo apt install -y docker-ce docker-ce-cli containerd.io docker-compose-plugin# 配置docker镜像加速器(解决网络问题导致下载镜像失败问题)
sudo vim /etc/docker/daemon.json
{"registry-mirrors": ["https://docker-0.unsee.tech"]
}
注:其它镜像地址可参考 https://cloud.tencent.com/developer/article/2524388## 2. 启动Docker服务
# 启动Docker服务
sudo systemctl start docker# 设置开机自启
sudo systemctl enable docker# 将当前用户添加到docker组(可选,避免每次使用sudo)
sudo usermod -aG docker $USER## 3. 安装Docker Compose
# 方法一:使用apt安装(推荐)
sudo apt install -y docker-compose-plugin
sudo apt install docker-compose# 方法二:或者下载二进制文件
sudo curl -L "https://github.com/docker/compose/releases/download/v2.20.0/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
sudo chmod +x /usr/local/bin/docker-compose# 验证安装
docker-compose version
docker compose version
例:
docker-compose version 1.25.0, build unknown
docker-py version: 4.1.0
CPython version: 3.8.10
OpenSSL version: OpenSSL 1.1.1f 31 Mar 2020
例:
Docker Compose version v2.35.1
5.2 如何部署第三方的MySQL服务?
# 1.进入mysql docker文件夹位置
cd /xx/xx/mysql# 2.创建并编写docker-compose.yml文件
version: '3.3'
services:mysql:image: mysql:8.0container_name: mysql-serverrestart: alwaysenvironment:MYSQL_ROOT_PASSWORD: rootpassword# 指定需要创建的数据库名MYSQL_DATABASE: myappMYSQL_USER: appuserMYSQL_PASSWORD: userpasswordports:- "3306:3306"volumes:- mysql_data:/var/lib/mysql- ./init:/docker-entrypoint-initdb.dcommand: --default-authentication-plugin=mysql_native_password# 定义命名卷,右侧空白代表使用默认配置
volumes:mysql_data:# 3.创建并后台启动容器
docker-compose up -d# 4.运行效果如下图所示
实践:



5.3 如何部署自定义的SpringBoot服务?
代码工程结构:
project-root/
├── src/
├── pom.xml
├── Dockerfile
├── docker-compose.yml
├── application-docker.yml
└── .dockerignore部署目录结构:
demoAPP/
├── Dockerfile
├── docker-compose.yml
├── application-docker.yml
└── .dockerignore
└── demo.jar
1. 创建Dockerfile 和 .dockerignore
######### Dockerfile
# 基础镜像
FROM openjdk:8-jdk-alpine# 设置时区
RUN apk add --no-cache tzdata
ENV TZ=Asia/Shanghai# 创建应用目录
WORKDIR /app# 复制jar包
COPY *.jar app.jar# 复制用于docker环境部署的业务配置文件
COPY application-docker.yml /app/config/# 暴露端口
EXPOSE 9100# 启动应用
ENTRYPOINT ["java", "-jar", "app.jar"]######### .dockerignore
# 构建输出目录
target/
!.mvn/wrapper/maven-wrapper.jar# Git相关文件
.git
.gitignore# IDE相关文件
.idea/
.vscode/
*.iml
*.iws# 日志文件
*.log
logs/# 临时文件
tmp/
temp/# 配置文件(如果不想包含)
application-local.yml
.env# 文档文件
README.md
docs/
2. 创建docker-compose.yml
version: '3.3'
services: # springboot服务demoapp: build: . container_name: demoService ports: - "9100:9100" volumes: - ./logs:/app/logs - ./application-docker.yml:/app/config/application-docker.yml environment: - spring.profiles.active=docker# 使用host网络模式,可以直接访问宿主机网络network_mode: "host"
3. 创建docker运行环境配置文件
创建 application-docker.yml(专门用于docker环境部署,用于与原环境进行隔离且原配置文件不动):
# application-docker.yml
server:port: 9100 # 保持与原配置一致idworker:workerId: 1datacenterId: 1max-http-header-size: 10240servlet:context-path: /forumtomcat:uri-encoding: UTF-8spring:profiles:active: dockerapplication:name: ForumApplicationservlet:multipart:max-request-size: 20MBmax-file-size: 10MBcloud:sentinel:transport:dashboard: sentinel-dashboard:8080 # 使用服务名port: 8719eager: trueweb-context-unify: false# 数据源配置 - 使用环境变量datasource:type: com.alibaba.druid.pool.DruidDataSourcedriverClassName: com.mysql.cj.jdbc.Driverdruid:url: jdbc:mysql://${DB_HOST:192.168.75.244}:${DB_PORT:6668}/dev_db_forum?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8username: ${DB_USERNAME:root}password: ${DB_PASSWORD:sfdgdh}initialSize: 5minIdle: 10maxActive: 20maxWait: 60000timeBetweenEvictionRunsMillis: 60000minEvictableIdleTimeMillis: 300000maxEvictableIdleTimeMillis: 900000validationQuery: SELECT 1 FROM DUALtestWhileIdle: truetestOnBorrow: falsetestOnReturn: falsewebStatFilter:enabled: truestatViewServlet:enabled: trueurl-pattern: /druid/*filter:stat:enabled: truelog-slow-sql: trueslow-sql-millis: 1000merge-sql: truewall:config:multi-statement-allow: true# Redis缓存配置 - 使用环境变量redis:cluster:nodes: ${REDIS_NODES:192.168.75.244:7000,192.168.75.244:7001,192.168.75.244:7002,192.168.75.244:7003,192.168.75.244:7004,192.168.75.244:7005}password: ${REDIS_PASSWORD:dfsfs}timeout: 5000lettuce:pool:max-active: 200max-idle: 10min-idle: 5max-wait: -1database: 8# 健康检查
management:health:defaults:enabled: false# mybatis plus 设置
mybatis-plus:mapper-locations: classpath*:mapper/**/*Mapper.xmltypeAliasesPackage: com.fenda.**.entityglobal-config:banner: falsedb-config:id-type: AUTOtable-underline: trueconfiguration:call-setters-on-nulls: true
4. 构建和部署流程
# 1.打包应用 并 上传到服务器指定位置/xx/xx/demoAPP/
mvn clean package -DskipTests
或
IDEA 右侧栏 先后点击clean和Install# 2.构建并后台启动所有服务
cd /xx/xx/demoAPP/
docker-compose up -d
注:该命令会先自动检测本地是否存在镜像,不存在则会基于DockFile执行docker build构建镜像,再基于镜像构建容器和启动相关服务# 3.查看服务状态
docker-compose ps
或
docker ps
注:服务状态为up则代表容器启动成功# 4.查看服务日志
docker-compose logs -f <服务名># 5.进入容器环境可查看映射的文件夹、文件、执行系统命令等
docker exec -it aa48dd91c15e bash
或
docker exec -it aa48dd91c15e sh
6. 常见问题与解决方案
6.1 容器间通信
使用Docker网络或Docker Compose实现容器互联。
6.2 数据持久化
通过数据卷或绑定挂载确保数据不会因容器删除而丢失。
6.3 镜像大小优化
使用多阶段构建、Alpine基础镜像等方式减小镜像体积。
6.4 性能调优
合理配置CPU和内存限制,使用合适的存储驱动。
