Docker入门

大家好,这依旧是一篇个人笔记,本次笔记内容是有关于Docker容器

本次笔记内容对应黑马JAVA WEB课程的191-197集

本次笔记由workbuddy协同完成,不喜勿喷,谢谢

一、Docker 核心概念

1.1 什么是 Docker

Docker 是一个开源的容器化平台,可以将应用程序及其依赖打包成一个标准化的单元(容器),实现快速部署和运行。

1.2 核心概念

|-----------------|---------------------------------|
| 概念 | 说明 |
| 镜像 (Image) | 一个只读的模板,包含运行应用所需的代码、库、环境变量和配置文件 |
| 容器 (Container) | 镜像的运行实例,是独立、隔离的运行环境 |
| 镜像仓库 (Registry) | 存储和分发镜像的服务,如 Docker Hub |

1.3 镜像命名规范

镜像名称格式:

复制代码
[repository]:[tag]

# 示例
nginx:latest
mysql:8.0
redis:7-alpine

二、Docker 常用命令

2.1 镜像操作命令

|-----------------------|--------------------|
| 命令 | 作用 |
| docker pull 镜像名 | 从仓库拉取镜像 |
| docker images | 查看本地所有镜像 |
| docker rmi 镜像ID | 删除指定镜像 |
| docker build -t 镜像名 . | 根据 Dockerfile 构建镜像 |

2.2 容器操作命令

|---------------------------|---------------|
| 命令 | 作用 |
| docker run 镜像名 | 创建并启动容器 |
| docker ps | 查看运行中的容器 |
| docker ps -a | 查看所有容器(包括停止的) |
| docker start 容器ID | 启动已停止的容器 |
| docker stop 容器ID | 停止运行中的容器 |
| docker rm 容器ID | 删除容器 |
| docker logs 容器ID | 查看容器日志 |
| docker exec -it 容器ID bash | 进入容器内部执行命令 |

2.3 docker run 常用参数

|-----------|--------------------|
| 参数 | 说明 |
| -d | 后台运行(守护模式) |
| --name | 为容器指定名称 |
| -p | 端口映射,格式 宿主机端口:容器端口 |
| -e | 设置环境变量 |
| -v | 挂载数据卷或目录 |
| --network | 指定容器网络 |

三、端口映射

3.1 端口映射的目的

容器是隔离的运行环境,外部无法直接访问容器内部。端口映射将宿主机的端口与容器端口关联,使外部请求可以通过宿主机访问容器服务。

3.2 端口映射的原理

当外部访问宿主机的某个端口时,Docker 会将请求转发到映射的容器端口,实现内外通信。

3.3 宿主机概念

宿主机(Host)是运行 Docker 的物理机或虚拟机。容器运行在宿主机上,共享宿主机的内核资源。

3.4 端口映射示例

复制代码
# 将宿主机的 80 端口映射到容器的 80 端口
docker run -d -p 80:80 --name nginx nginx:latest

# 将宿主机的 8080 端口映射到容器的 80 端口
docker run -d -p 8080:80 --name nginx nginx:latest

四、数据卷 (Volume)

4.1 为什么需要数据卷

Docker 容器默认是临时的,容器删除后数据会丢失。而且容器内部通常缺少 vim 等编辑工具,直接修改容器内文件不方便。

docker创建的容器很多linux有的命令都没有的,包括vim这种编辑文件的命令

因此,如果想要变价docker容器里面的文件的话,就必须借助"数据卷"

数据卷简单来说就是通过映射的形式把dockers容器里面的文件映射到宿主机上面,然后你要编辑docker文件的话直接编辑宿主机上面的映射文件即可

4.2 什么是数据卷

数据卷是一个虚拟目录,是容器内目录与宿主机目录之间的映射桥梁。通过数据卷,可以将容器内的文件映射到宿主机上,实现数据的持久化和便捷编辑。

4.3 数据卷操作命令

|--------------------------|-----------|
| 命令 | 作用 |
| docker volume create 卷名 | 创建数据卷 |
| docker volume ls | 查看所有数据卷 |
| docker volume rm 卷名 | 删除数据卷 |
| docker volume inspect 卷名 | 查看数据卷详情 |
| docker volume prune | 清理未使用的数据卷 |

4.4 数据卷挂载示例

复制代码
# 使用 -v 参数挂载数据卷
docker run -d \
  --name nginx \
  -p 80:80 \
  -v html:/usr/share/nginx/html \
  nginx:latest

提示

数据卷挂载后,修改宿主机上的映射文件会立即反映到容器中,反之亦然。

4.5 本地目录挂载

使用数据卷时,Docker 会自动管理存储位置(通常在 /var/lib/docker/volumes/ 下),路径较深不便操作。可以使用本地目录挂载,自定义宿主机路径:

复制代码
# 使用绝对路径或相对路径挂载本地目录
docker run -d \
  --name nginx \
  -p 80:80 \
  -v /home/user/nginx/html:/usr/share/nginx/html \
  nginx:latest

# 或使用相对路径(以 ./ 或 ../ 开头)
docker run -d \
  --name nginx \
  -p 80:80 \
  -v ./html:/usr/share/nginx/html \
  nginx:latest

4.6 两种挂载方式对比

|---------|-------------|---------------|
| 对比项 | 数据卷挂载 | 本地目录挂载 |
| 语法 | -v 卷名:容器路径 | -v /本地路径:容器路径 |
| 存储位置 | Docker 自动管理 | 用户自定义 |
| 适用场景 | 临时数据、缓存 | 配置文件、持久化数据 |

五、自定义镜像

5.1 镜像结构

Docker 镜像采用分层结构:

|------------|---------------------------------|
| 层级 | 说明 |
| BaseImage | 基础镜像层,包含基础系统文件(如 CentOS、Ubuntu) |
| Layer | 中间层,执行各种构建指令(如安装 JDK、复制应用文件) |
| Entrypoint | 入口层,配置容器启动时执行的命令 |

5.2 Dockerfile 常用指令

|------------|-------------|
| 指令 | 说明 |
| FROM | 指定基础镜像 |
| ENV | 设置环境变量 |
| COPY | 复制本地文件到镜像中 |
| RUN | 执行命令(构建时执行) |
| EXPOSE | 声明容器暴露的端口 |
| ENTRYPOINT | 容器启动时执行的命令 |

5.3 构建 Java 镜像示例

以下是一个构建 Java 应用的 Dockerfile 示例:

复制代码
# 基于 CentOS 7 基础镜像
FROM centos:7

# 设置环境变量
ENV JAVA_DIR=/usr/local

# 复制 JDK 和应用 jar 包到镜像
COPY ./jdk8.tar.gz $JAVA_DIR/
COPY ./docker-demo.jar /tmp/app.jar

# 解压 JDK 并配置环境变量
RUN cd $JAVA_DIR \
 && tar -xf ./jdk8.tar.gz \
 && mv ./jdk1.8.0_144 ./java8

ENV JAVA_HOME=$JAVA_DIR/java8
ENV PATH=$PATH:$JAVA_HOME/bin

# 暴露端口
EXPOSE 8090

# 容器启动命令
ENTRYPOINT ["java", "-jar", "/tmp/app.jar"]

5.4 构建镜像命令

复制代码
# 构建镜像
# -t: 指定镜像名称和标签
# .: 指定 Dockerfile 所在目录
docker build -t my-java-app:1.0 .

六、Docker 网络

6.1 默认网络的问题

默认情况下,Docker 创建的容器都连接到 Docker 自带的虚拟网桥。容器之间可以通过 IP 地址通信,但容器 IP 是随机分配的。如果容器重启,IP 地址会改变,导致依赖该 IP 的其他容器无法正常访问。

默认情况下,docker创建的容器都是连接到dockers自己提供的一个虚拟网桥上面,各个容器之间可以通过访问ip的形式去实现容器之间的通信(比如java引用去连接数据库)

但是由于ip地址是随机分配的,如果一开始先启动了一个容器A,并且容器B已经通过ip地址的形式和容器A实现了通信,这个时候关闭容器A再打开,此时容器A的ip地址就会发生改变,但是容器B访问的那个ip地址还是旧的容器A的地址,那就需要修改,非常不方便

因此为了应对这种情况,我们就可以自定义网络

6.2 自定义网络解决方案

创建自定义网络后,将容器加入该网络,容器之间可以通过容器名称(而非 IP)互相访问。即使容器重启导致 IP 变化,名称解析仍然有效。

6.3 网络操作命令

|---------------------------------|----------|
| 命令 | 作用 |
| docker network create 网络名 | 创建自定义网络 |
| docker network ls | 查看所有网络 |
| docker network rm 网络名 | 删除网络 |
| docker network connect 网络 容器 | 将容器连接到网络 |
| docker network disconnect 网络 容器 | 将容器从网络断开 |
| docker network inspect 网络名 | 查看网络详情 |

6.4 自定义网络使用示例

复制代码
# 1. 创建自定义网络
docker network create my-network

# 2. 启动容器时连接到自定义网络
docker run -d \
  --name mysql \
  --network my-network \
  -e MYSQL_ROOT_PASSWORD=123456 \
  mysql:8.0

# 3. Java 应用容器通过容器名访问 MySQL
docker run -d \
  --name java-app \
  --network my-network \
  -e DB_HOST=mysql \
  my-java-app:1.0

# 在 Java 应用中,使用 mysql 作为数据库主机名即可
相关推荐
测试员周周3 小时前
【Appium 系列】第16节-WebView-H5上下文切换 — 混合应用的自动化难点
运维·开发语言·人工智能·功能测试·appium·自动化·测试用例
风落无尘4 小时前
Stable Diffusion WebUI & ComfyUI 完整安装教程:官方部署+一键整合包+Docker容器化(2026最新)
docker·容器·stable diffusion
在角落发呆6 小时前
Linux转发配置:解锁网络互联的核心密码
linux·运维·网络
裴东青8 小时前
10-实战:RuoYi-Cloud的自动化发布
运维·ci/cd·自动化
哎呦,帅小伙哦8 小时前
Linux 时间:从原子钟到 clock_gettime 的每一面
linux·运维·服务器
sxgzzn8 小时前
新能源场站数智化转型:基于数字孪生与AI的智慧运维管理平台解析
大数据·运维·人工智能
张小姐的猫8 小时前
【Linux】多线程 —— 线程互斥
linux·运维·服务器·c++
CodeMartain9 小时前
Dify Windows 原生部署(无 Docker、纯本地)
运维·docker·容器
xxx1x1x9 小时前
极客向:DLL/运行库故障的底层逻辑与自动化修复方案
运维·自动化·dll文件·dll·dll修复·dll缺失·dll一键修复
YuanDaima20489 小时前
Linux 进阶运维与 AI 环境实战:进程管理、网络排错与 GPU 监控
linux·运维·服务器·网络·人工智能