Project source code:Click to view the project source code
image
We used it in front
namespace
andcgroup
A simple container is built, but we can find that the directory in the container is still the directory of the currently running program. Here, an important feature such as image is missing. Here, we first use docker to pull the most compact imagebusybox
, it is a box of many UNIX tools, providing a very complete and compact system.
#Pull busybox
docker pull busybox
#Run
docker run -d busybox top -b
#View container ID
docker ps
#Export container
docker export -o busybox.tar
You can see that we have successfully exported the contents of the container. Let me unzip it, and then use this folder as the read-only layer of the container.
mkdir busybox && tar -xvf busybox.tar -C busybox/
be careful:Later, for convenience, we put busybox Put tar under the / root path
When docker starts the container, it will create two new layers, write layer and container layer. Write layer is the only read-write layer of the container, and container layer is the new read-only layer for the container. Here, we take busybox as this layer, the read-write layer, and we create one
writeLayer
Folder as this layer, then mount the two folders under the same folder, and then take this folder as the startup directory of the container. This folder is namedmnt
Linux mount folder
Here we have three folders,
mnt
writeLayer
busybox
, we willwriteLayer
busybox
These two folders are mounted tomnt
Under the folder, you can seemnt
andwriteLayer
All folders are empty, onlybusybox
There’s something under the folder. Let’s have a look after we mount it
#Mount
mount -t aufs -o dirs=/root/writeLayer:/root/busybox none /root/mnt
As you can see,
mnt
Already appearedbusybox
What’s in the folder, and we’re herewriteLayer
Create a new folder under the folder and see what happens
It can be clearly seen that we are right
writeLayer
What you do is mapped tomnt
Under the folder, docker is also implemented in this way. Every time you modify something in the container, it will not affect the image, because all the operations you do arewriteLayer
Layer, and the mirror is inbusybox
, that iscontainer-init
Layer.
Go implementation mount
func NewWorkSpace(rootPath string, mntPath string, volume string) error {
// 1. Create read-only layer
err := createReadOnlyLayer(rootPath)
if err != nil {
logrus.Errorf("create read only layer, err: %v", err)
return err
}
// 2. Create a read-write layer
err = createWriteLayer(rootPath)
if err != nil {
logrus.Errorf("create write layer, err: %v", err)
return err
}
// 3. Create a mount point to mount the read-only layer and read-write layer to the specified location
err = CreateMountPoint(rootPath, mntPath)
if err != nil {
logrus.Errorf("create mount point, err: %v", err)
return err
}
return nil
}
In short, there are three steps. The first step is to create a read-only layer, the second step is to create a read-write layer, and the third step is to mount them in the same folder. The specific implementation is also relatively simple, that is, to create a folder. Here’s how to mount them
func CreateMountPoint(rootPath string, mntPath string) error {
_, err := os.Stat(mntPath)
if err != nil && os.IsNotExist(err) {
err := os.MkdirAll(mntPath, os.ModePerm)
if err != nil {
logrus.Errorf("mkdir mnt path, err: %v", err)
return err
}
}
dirs := fmt.Sprintf("dirs=%s%s:%s%s", rootPath, common.WriteLayer, rootPath, common.BusyBox)
cmd := exec.Command("mount", "-t", "aufs", "-o", dirs, "none", mntPath)
if err := cmd.Run(); err != nil {
logrus.Errorf("mnt cmd run, err: %v", err)
return err
}
return nil
}
The article will start on my WeChat official account, scan code attention, and get the latest content in time.
This work adoptsCC agreement, reprint must indicate the author and the link to this article