Docker 概述
Docker 是一个用于开发、传送和运行应用程序的开放平台。使应用和基础设施隔离。像管理应用一样管理设施。
Docker 容器:打包和运行应用的隔离环境。
Docker提供的服务:
- 开发应用的支持性组件可以在容器中运行
- 容器可当作发布和测试单元
- 当要部署应用时,可以为应用编排服务部署到生产环境的容器中。
Docker 架构
使用客户端-服务端的架构。客户端与服务端可在同一系统,也可以客户端连接远程服务端(Docker Host)。客户端发送命令,服务端接受命令后操作,比如构建、运行和发布等。
还一种客户端是 Docker Compose ,使用它让一组容器来组成的应用程序,就是所谓的服务编排。
- Docker Daemon - 监听 Docker API 请求和管理 Docker 对象 如:镜像images,容器containers,网络networks,数据卷volumes
- Docker Client - 与 Docker 交互的主要工具,当运行
docker run
时,客户端把命令发送 给dockerd
并执行 - Docker registries - 存储 Docker 镜像。Docker Hub 是官方镜像站点。使用
docker pull
从仓库获取镜像。docker push
来上传镜像 - Docker objects
-
images - 用于创建容器说明的只读模版。
docker images
可查看已拉取的镜像 -
containers - 正在运行的镜像实例。docker ps可查看运行中的容器
-
- Docker Desktop - 包含了 Docker Daemon、Docker Client 和 Docker Compose等组件 在 Windows 和 Mac 下运行的桌面应用
Docker 安装
在 Linux 上的安装。Linux 的发行版是 CentOS 7。
|
|
最终显示:
Docker version 20.10.11, build dea9396
常用命令
docker daemon 管理
|
|
镜像管理
|
|
容器管理
|
|
|
|
- -i - 保持容器运行。容器创建后,运行,再退出,不会删除容器。它可与d和t连用
- -d - 后台运行容器
- -t - 分配一个伪终端
- –name - 为容器命名
- -p - 端口映射,容器与宿主机隔离的,要想从宿主机访问容器,需要做端口映射,前者是宿主端口,后者才是容器端口。使用数据卷也是先宿主后容器。
- -v - 使用数据卷,宿主机的目录与容器目录绑定。用于数据交互和持久化。如果宿主机目录未指定,就使用默认生成的目录。
- -e - 定义容器使用的环境变量。这里指定 MySQL root 用户密码。
- –volumes-from - 继承其他容器的数据卷。
|
|
数据卷就是宿主机下的目录或文件,可以被多个容器挂载。容器可以挂载多个数据卷
Docker 镜像原理
Docker镜像本质是一个分层的文件系统。
它基于 Linux 文件系统,Linux包括了bootfs和rootfs。最底层bootfs包含引导加载程序和内核,但镜像的bootfs使用的是宿主机的。这就是镜像文件比Linux某些发行版如 CentOS 的 ISO 镜像 的尺寸还有小的原因。
往上层的rootfs就是 Linux 的 root 文件系统,称作基础镜像。然后再往上叠加其他镜像。使用统一文件系统技术把多层文件系统虚拟化成一个文件系统。
一个子镜像还可以放在一个父镜像上面,如 Tomcat 镜像依赖于父镜像 OpenJDK 和基础镜像。
当镜像启动容器时,会在最顶层加载一个可读写的文件系统作为容器。
镜像制作
将现有容器制作成镜像
|
|
用Dockerfile制作镜像
Dockerfile 是文本文件,包含构建镜像说明。当执行 docker build
会读取这个文件的指令来帮助构建镜像。Dockerfile的默认文件名就是"Dockerfile"。
如果不使用默认名,则可命名为 Dockerfile.<something>/ <something>.Dockerfile
,命令执行时用 –file(-f)指定它。项目的主Dockerfile建议使用默认的。
按照官方的教程的构建第一个Java 应用镜像如下
由于是在Linux下使用docker,运行 docker build
设置环境变量来启用 BuildKit,例如:
|
|
可以配置文件来默认启用
|
|
然后重启 docker
从github克隆一个demo
|
|
可以去测试一下这个demo是否能正常运行
|
|
用浏览器打开 http://localhost:8080,如果使用虚拟机 Linux 并从宿主机访问,localhost 要改成虚拟机的ip即可。
接着创建一个Dockerfile
|
|
第1行:告诉 docker 构建器所使用dockerfile的版本1语法。
第3行:使用openjdk的镜像,它包含 Java JDK ,就能够运行 Java 程序
第5行:设置镜像的工作目录。后续指令将在这个目录下进行。方便我们后续使用相对路径而非绝对路径
第7、8行:为了后续执行 ./mvnw dependency
命令,需要将 Maven Wrapper 和 pom.xml文件放入镜像内。COPY指令有两个参数,第一个是要复制的文件,可以多个文件,第二个是复制到的目标。第7行目标是文件,第8行的目标是目录。注:最后空格后的肯定是第二个参数。
第9行:RUN 像在shell运行命令,这里会下载maven项目的依赖项到镜像
第11行:将源代码复制到镜像
第13行:CMD 指定当制作的镜像在容器内执行时,将会执行的操作。
RUN是构建时执行的命令,而CMD运行时执行的命令。
它由一些列命令构成。每个指令基于基础镜像构成一层文件系统,最终形成镜像。
再接着,创建 .dockeringnore 文件让 docker 构建时要忽略的文件或目录,以提高构建性能。这里 maven 测试这个 demo 会生成一个输出目录 target,可以忽略掉。
.dockerignore的内容如下:
target
最后构建镜像
|
|
--tag
- 给镜像打标签 格式是 “名号:版本标签”,如:java-docker:v1.0.0。如果没指定标签,默认使用 latest.
- 命令最后的 . 是构建镜像的上下文。它是指定了路径所在文件集合,这里表示当前路径下的文件集。构建过程将会处理这些文件
可以通过 docker images 查看所制作的镜像。还可以创建新的标签如: docker tag java-docker:latest docker:v1.0.0
Dockerfile 的优点:
- 保证开发人员可以为团队提供完全一致的开发环境
- 保证测试人员可以直接使用开发人员的构建的镜像或使用Dockerfile构建新镜像进行测试
- 为运维人员,部署应用时无须担心环境迁移的问题。可以无缝移植。
运行制作好的镜像为容器
|
|
输出:
{"status":"UP"}
在开发应用时,可能需要其他容器作为支持,比如 Spring Boot 应用容器需要 MySQL 数据库容器支持
首先在容器中创建 MySQL 数据库,使用数据卷让多个容器共享数据和配置
|
|
创建 network 让应用和数据库共享此网络以互相通信。这里的 network 为用户定义的桥接网络。为了在后面的定义 jdbc url 的时候可以作为用服务名当作连接字符串来使用。
如:jdbc:mysql://mysqlserver/petclinic
|
|
运行mysql容器
|
|
上一节中的 springboot-server 容器想要使用 MySQL ,就要修改 Dockerfile 文件,将 CMD 的修改为:
CMD ["./mvnw", "spring-boot:run", "-Dspring-boot.run.profiles=mysql", "-Dmaven.test.skip"]
使这个 demo 从 H2 内存数据库切换为 MySQL 数据库,重新新构建一次。然后启动容器连接 mysqlserver。
|
|
Docker Compose 借助容器开发应用
编写第一个compose文件
|
|
启动应用前安装 docker compose
|
|
接着编译镜像并运行
|
|
Dockerfile和docker-compose.yml区别
前者是制作自定义镜像的说明,后者是容器集群做快速编排,用于部署分布式应用。