Docker实战10|实现volum数据卷

上一篇文章中,仔细讲解了Docker是如何改变当前的root文件系统以及mount等操作。

本文继续讲解Docker是如何实现Volum数据卷的。

实现Volume数据卷

获取代码

复制代码
git clone https://gitee.com/mjreams/docker.git

上一小节介绍了如何使用AUFS包装busybox,从而实现容器和镜像的分离。但是一旦容器退出,容器可写层的所有内容都会被删除。那么,如果用户需要持久化容器里的部分数据该怎么办呢?volume就是用来解决这个问题的。

本节将会介绍如何实现将宿主机的目录作为数据卷挂载到容器中,井且在容器退出后,数据卷中的内容仍然能够保存在宿主机上。

使用 AUFS 创建容器文件系统的实现过程如下。

启动容器的时候:

    1. 创建只读层(busybox);
    1. 创建容器读写层(writeLayer);
    1. 创建挂载点(mnt),并把只读层和读写层挂载到挂载点;
    1. 将挂载点作为容器的根目录。

    容器退出的时候

    1. 卸载挂载点(mnt)的文件系统;
    1. 删除挂载点;
    1. 删除读写层(writeLayer)

本篇内容就是要在这个文件基础上添加绑定宿主机文件夹到饿容器数据卷的功能。

首先,在main_command.go文件的runCommand命令中添加-v标签

复制代码
cli.StringFlag{
            Name:  "v",
            Usage: "volume",
        },

在Run函数中,把volume传给创建容器的NewParentProcess函数和删除容器文件系统的Delete WorkSpace函数。

见run.go

在NewWorkSpace函数中,继续把volume值传给创建容器文件系统的NewWorkSpace方法。

见container/container_process.go

创建容器文件系统的过程如下

    1. 创建只读层。
    1. 创建容器读写层
    1. 创建挂载点并把只读层和读写层挂载到挂载点上。
    1. 接下来,首先要判断Volume是否为空,如果是,就表示用户并没有使用挂载标签,结束创建过程。
    1. 如果不为空,则解析volume字符串
    1. 当解析volume字符串返回的字符数组长度为2,并且数据元素均不为空的时候,则执行MountVolume函数来挂载数据卷。
    1. 否则,提示用户创建数据卷输入值不对。

见container/volume.go

挂载数据卷的过程如下

    1. 首先,读取宿主机文件目录URL,创建宿主机文件目录(/root/${parentUrl})。
    1. 然后,读取容器挂载点URL,在容器文件系统里创建挂载点C/root/mnt/${containerUrl})。
    1. 最后,把宿主机文件目录挂载到容器挂载点。这样启动容器的过程,对数据卷的处理也就完成了。

见container/volume.go

删除容器文件系统的过程如下

    1. 只有在volume不为空,并且解析volume字符串返回的字符数组长度为2,数据元素均不为空的时候,才执行DeleteVolume函数来处理。
    1. 其余的情况仍然使用前面的DeleteMountPoint函数。

DeleteVolume 处理逻辑

    1. 首先,卸载volume挂载点的文件系统(/root/mnt/${containerUrl}),保证整个容器的挂载点没有被使用。
    1. 然后,再卸载整个容器文件系统的挂载点C/root/mnt)。
    1. 最后,删除容器文件系统挂载点。整个容器退出过程中的文件系统处理就结束了。

流程图

验证测试

启动一个容器,把宿主机的/root/volume挂载到容器的/containerVolume目录下。

可以看到/root下多了一个volume文件

容器里执行ls,可以看到多了一个containerVolume

复制代码
sh-5.1# ls
containerVolume
sh-5.1# 

由于源代码使用的是aufs文件系统,而本地机器是overlay文件系统,因此后续测试流程不再演示,后续本文将会把代码修改成overlay文件系统

相关推荐
qianyuqiye119 分钟前
K8s 命名空间与 Pod 入门:从概念到实战
java·docker·kubernetes
fengkai454514 小时前
3、Kubernetes的Namespace&Contexts&Pod&YAML格式
运维·容器·kubernetes·k8s·namespace·yaml·pod
IOT那些事儿14 小时前
Git报错:Could not get HEAD hash
git·hash·head
容器魔方15 小时前
Volcano v1.16 发布:新增 NamespaceQueue 与 fairshare,拓展 HyperNode 生态
人工智能·云原生·容器·华为云·云计算
秦jh_17 小时前
【Docker】镜像、卷原理
运维·docker·容器
小马同学-17 小时前
K8s 命名空间与上下文:Namespace 资源隔离与多集群切换实战
云原生·容器·kubernetes
程序员老赵17 小时前
Docker 部署 XWiki:轻松搭建企业知识库与协作 Wiki
前端·docker·开源
杜哥无敌17 小时前
Git Bash + acme.sh 实现 SSL 证书自动续签(完整指南)
git·bash·ssl
I'mChloe17 小时前
飞牛NAS部署flatnotes实战:Docker、8080端口、Markdown笔记与固定地址访问
笔记·docker·容器
许知珩18 小时前
Kubernetes 存储与配置管理 ——Volume、ConfigMap 与 Secret 实战详解
云原生·容器·kubernetes