Docker 学习笔记 - 在 Linux 上安装和使用 Docker
Docker 是一种近些年比较流行的一种虚拟化技术,它可以让一组软件或环境在单独的容器中运行,可以和宿主机隔绝,可避免一些软件和环境间的冲突。把一些软件或运行环境封装为 Docker 镜像,后续需要重新安装的时候,也可以很方便的安装和配置。
Docker 虽然是一种虚拟化技术,但是它是和宿主机共享同一个系统内核,性能相比传统的虚拟机,比如 VMware 之类的,性能强很多。
下载安装
我这里会在 Debian12 中安装和使用 Docker,使用的是命令行管理。
Docker 也有很多通过 Web 和 GUI 的可视化管理程序,如果嫌命令行麻烦的话,也可以用这些程序管理。
先安装基础工具:
apt update && apt install -y ca-certificates curl gnupg添加 GPG 密钥:
install -m 0755 -d /etc/apt/keyrings && curl -fsSL https://download.docker.com/linux/debian/gpg -o /etc/apt/keyrings/docker.asc && chmod a+r /etc/apt/keyrings/docker.asc设置 Docker 仓库地址:
echo "deb [arch=$(dpkg --print-architecture) signed-by=/etc/apt/keyrings/docker.asc] https://download.docker.com/linux/debian $(. /etc/os-release && echo "$VERSION_CODENAME") stable" | tee /etc/apt/sources.list.d/docker.list > /dev/null安装 Docker Engine:
apt update && apt install -y docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin安装完成后查看一下 Docker 版本,看是否成功:
docker version镜像和容器管理
在 Docker 中,有镜像 (Image) 和容器 (Container) ,镜像是封装后的一组软件和文件,容器是镜像运行后的实例。
或者说镜像就类似于编程中的 class 类,容器就类似于 object 对象,可以把镜像理解为软件的安装包,容器就是软件启动后的程序。
在下载镜像前,你可以直接访问 Docker Hub 查找你感兴趣的镜像,镜像的页面会有版本说明,下面是 MySQL 的镜像版本说明:

下面拉取 MySQL8.0-bookworm 的 Docker 镜像:
docker pull mysql:8.0-bookwormDocker 镜像内已经包含了部分操作系统,你也可以选择其它版本,不一定要和系统对应。
如果拉取镜像的时候不带版本,默认使用最新版。
查看本地镜像:
docker images会显示已下载的镜像:
IMAGE ID DISK USAGE CONTENT SIZE EXTRA
dpanel/dpanel:lite 324c4b22b86d 280MB 72.7MB U
dpanel/explorer:latest 3285f3d1782e 16.6MB 8.09MB
mysql:8.0-bookworm bb21c581c013 816MB 188MB可以看到刚才下载的 mysql。
下面运行容器,就使用 mysql8:
docker run --name mysql8 -e MYSQL_ROOT_PASSWORD=123456 -p 3306:3306 -d mysql:8.0-bookworm下面是参数说明:
--name容器名称,设置一个容器名称,方便管理,我这里设置的容器名称是mysql8-e设置容器内的环境变量,其中的MYSQL_ROOT_PASSWORD=123456就是把 MySQL root 密码设置为 123456-p设置端口号-d在后台运行mysql:8.0-bookworm就是镜像名称
上面 -p 的端口号包含两个,第一个是宿主机的端口,第二个是容器内 MySQL 监听的端口。这是一个端口映射,宿主机端口不一定要和容器端口一致,如果把上面的端口改为 -p 3307:3306,通过 3307 连接 MySQL,也能被转发到容器的 3306 端口。
有些 Docker 镜像第一次启动时,需要传入环境变量之类的来初始化,在启动时可以先查看镜像页面说明。
下面查看一下正在运行的容器:
docker ps输出如下:
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
9a0cdd2017cd mysql:8.0-bookworm "docker-entrypoint.s…" 19 minutes ago Up 19 minutes 0.0.0.0:3306->3306/tcp, [::]:3306->3306/tcp, 33060/tcp mysql8
0496e87d46fb dpanel/dpanel:lite "sh -c '/app/server/…" 2 days ago Up 29 minutes 0.0.0.0:8807->8080/tcp, [::]:8807->8080/tcp dpanel上面运行了两个容器,一个是 dpanel Docker 可视化管理工具,另一个就是刚才运行的 mysql8 。
下面尝试连接一下 MySQL:
mysql -uroot -p123456 -h 127.0.0.1 -P 3306成功输出:
Welcome to the MariaDB monitor. Commands end with ; or \g.
Your MySQL connection id is 8
Server version: 8.0.44 MySQL Community Server - GPL
Copyright (c) 2000, 2018, Oracle, MariaDB Corporation Ab and others.
Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.我的宿主机上已经安装了 MySQL 客户端,所以可以直接使用 mysql 命令,如果没有安装的话,需要进入容器操作。
下面进入刚才启动的 mysql8 容器:
docker exec -it mysql8 bash容器就像是一个独立的系统,你在容器内可以正常使用 ls 之类的操作文件,容器内的文件和宿主机是隔离的,你在容器内操作文件,宿主机不会受到影响。
在 mysql8 容器内使用:
mysql -uroot -p123456也能直接连接容器内的 MySQL。
如果要离开容器,回到宿主机,可以使用:
exit下面停止正在运行的 mysql8 容器:
docker stop mysql8停止后通过 docker ps 就看不到了。
如果要查看所有容器,无论停止还是运行,可以使用:
docker ps -a输出如下:
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
9a0cdd2017cd mysql:8.0-bookworm "docker-entrypoint.s…" 59 minutes ago Exited (0) 2 minutes ago mysql8
0496e87d46fb dpanel/dpanel:lite "sh -c '/app/server/…" 2 days ago Up About an hour 0.0.0.0:8807->8080/tcp, [::]:8807->8080/tcp dpanel在 STATUS 可以查看容器是否运行。
下面再次运行 mysql8 容器:
docker start mysql8第一次使用 docker run 是启动和初始化容器,后续就可以直接使用 docker start 来启动容器。
下面删除 mysql8 容器:
docker rm -f mysql8我上面初始化容器的时候没有挂载数据卷,也没有挂载宿主机目录,删除容器后数据库也会被删除。
上面删除了 mysql8 容器,但是 mysql:8.0-bookworm 这个镜像还在,你还可以使用这个镜像重新启动和初始化容器。
同一个 Docker 镜像可以启动多个不同名称和端口的容器,比如上面的 mysql:8.0-bookworm 镜像,也可以启动多个容器:
docker run --name mysql8-1 -e MYSQL_ROOT_PASSWORD=123456 -p 3306:3306 -d mysql:8.0-bookworm
docker run --name mysql8-2 -e MYSQL_ROOT_PASSWORD=123456 -p 3307:3306 -d mysql:8.0-bookworm
docker run --name mysql8-3 -e MYSQL_ROOT_PASSWORD=123456 -p 3308:3306 -d mysql:8.0-bookworm上面使用了 mysql8-1 、mysql8-2 、mysql8-3 三个名称来启动了三个容器,这三个数据库容器使用不同的端口,不会发生冲突。
容器内的网络是隔离的,上面容器内虽然都是 3306 端口,但不会冲突。
下面直接删除 mysql:8.0-bookworm 镜像:
docker rmi mysql:8.0-bookworm注意,删除镜像前需要先删除对应的容器,比如上面使用 mysql:8.0-bookworm 启动了 mysql8-1 、mysql8-2 、mysql8-3 ,我需要先删除这三个容器后才能删除 mysql:8.0-bookworm 镜像。
镜像和容器管理常用命令
下面是一些镜像和容器管理的常用命令:
docker pull 镜像名: 下载镜像docker images: 查看已下载的镜像docker run -d -p 宿主机端口:容器端口 镜像名: 运行一个容器,如果镜像不存在会自动下载镜像docker ps: 查看正在运行的容器docker ps -a: 查看所有容器,无论是否运行docker logs 容器名: 查看容器日志,可用于排查问题docker exec -it 容器名 bash: 进入容器,进入后可以操作容器内的文件和使用容器内的软件exit: 离开容器,进入容器后可使用exit回到宿主机docker rm -f 容器名: 删除容器docker rmi 镜像名: 删除镜像,需要先删除对应的容器docker start 容器名: 启动一个停止运行的容器docker stop 容器名: 停止一个正在运行的容器docker restart 容器名: 重启容器
注意,不是所有的 Docker 容器都可以用 docker exec -it 容器名 bash 进入容器,有的镜像不包含 bash。
宿主机和容器之间的文件拷贝
有时候可能需要在容器和宿主机之间拷贝文件,下面是互相拷贝文件的方式。
我这里有一个名为 nginx-test 的容器,下面把当前目录下的 index.html 文件拷贝到容器内的 /usr/share/nginx/html 目录:
docker cp index.html nginx-test:/usr/share/nginx/html/index.html其中的 docker cp 就是拷贝命令,nginx-test 是容器名称,容器名称和目录之间用冒号 : 分隔。
下面把当前目录下的 web 目录拷贝到 nginx-test 容器内的 /usr/share/nginx/html 目录:
docker cp web nginx-test:/usr/share/nginx/html/Docker 会自动判断目录和文件,不需要加 -r 参数。
下面把 nginx-test 容器内的 /usr/share/nginx/html/index.html 拷贝到宿主机的 /downloads 目录:
docker cp nginx-test:/usr/share/nginx/html/index.html /downloads/index.html从容器内拷贝文件到宿主机不需要进入容器,如果你已经进入了容器,可以使用 exit 退出容器后拷贝。
下面把 nginx-test 容器内的 /usr/share/nginx/html/web 目录拷贝到宿主机的 /downloads 目录:
docker cp nginx-test:/usr/share/nginx/html/web /downloads/Docker 没有提供 mv 命令来移动文件,宿主机和容器之间无法直接移动文件,只能拷贝后删除。
上面只是简单演示,实际使用的时候不建议把文件拷贝到 Web 服务器的容器内使用,可以把宿主机的目录挂载到容器内使用。
挂载目录
在实际开发中,最方便的还是挂载目录,把宿主机目录挂载到容器内,直接修改宿主机的文件就能看到效果。
挂载目录需要在创建容器的时候挂载,如果你创建容器的时候没有挂载目录,后面也无法挂载。
下面使用 nginx 镜像来创建 nginx-test 容器,然后把宿主机的 /www 目录挂载到容器内作为网站目录:
docker run -d --name nginx-test -p 80:80 -v /www:/usr/share/nginx/html nginx上面创建了 nginx-test 容器,然后把 /www 目录挂载到容器内的 /usr/share/nginx/html 目录。
挂载目录使用 -v 宿主机目录:容器内目录 。
现在如果在 /www 目录里操作文件,在容器内的 /usr/share/nginx/html 目录也会同步改变。
卷映射
当你用 Docker 安装了 nginx 之类的 Web 服务器时,配置文件是在容器里的,也就是说你每次修改服务器配置都需要进入容器内操作,比较繁琐。
通过映射的方式可以直接把容器内的文件和目录映射到宿主机目录,你可以直接更改宿主机的文件,容器内对应的文件也会改变。
映射卷也需要在创建容器的时候配置,下面创建一个 nginx-test 容器,把容器内的 /etc/nginx 映射到宿主机的 nginx_conf,把宿主机的 /www 挂载到容器内的 /usr/share/nginx/html 作为网站目录:
docker run -d --name nginx-test -p 80:80 -v nginx_conf:/etc/nginx -v /www:/usr/share/nginx/html nginx映射卷和挂载目录一样,都是用 -v 来配置,挂载目录的左侧是要挂载的宿主机目录,映射卷的左侧是卷名称,这个卷名称并不是宿主机上的某个目录或文件。
上面映射卷指向了容器内的 /etc/nginx 目录,这也是 nginx 的配置文件目录,容器运行后,nginx 如果没有检测到配置文件就会自动生成默认的配置文件。
在宿主机上如果要查看卷的位置可以使用:
docker inspect nginx_conf其中的 nginx_conf 就是上面设置的卷名称,Docker 会输出一段 JSON:
[
{
"CreatedAt": "2025-12-27T17:21:31+08:00",
"Driver": "local",
"Labels": null,
"Mountpoint": "/var/lib/docker/volumes/nginx_conf/_data",
"Name": "nginx_conf",
"Options": null,
"Scope": "local"
}
]Mountpoint 的值就是卷位置。
上面的 nginx 配置文件会生成到 /var/lib/docker/volumes/nginx_conf/_data ,进入这个目录就可以更改 nginx 配置。
关于挂载目录和映射卷
挂载目录主要的文件管理是通过宿主机,适合需要在宿主机上频繁修改文件的情况,比如开发环境,需要在宿主机上的指定目录存放代码,修改完文件需要立即看到效果。
映射卷主要的文件管理是通过容器,文件主要由容器内的程序来管理,适合用于数据库文件和服务器日志之类的,文件主要由容器内的程序生成和修改。
使用 Docker 管理工具管理
如果你不太习惯使用命令行,或者需要随时随地管理 Docker 容器和镜像,也可以考虑使用管理工具。
目前有很多第三方的 Docker 管理工具,这些管理工具都提供了 Web 面板,可以很方便的管理容器和镜像。
下面是一些常用的管理工具:
Portainer 和 DPanel 可以直接通过 Docker 安装,1Panel 更接近于宝塔这种类型的服务器管理面板,除了 Docker 管理外,还包含一些服务器相关的管理。
版权声明:本文为原创文章,版权归 Changbin's Blog 所有,转载请联系博主获得授权。
本文地址:https://www.misterma.com/archives/963/
如果对本文有什么问题或疑问都可以在评论区留言,我看到后会尽量解答。