docker-container


容器是独立运行的一个或一组应用,以及它们的运行态环境。对应的,虚拟机可以理解为模拟运行的一整套操作系统(提供了运行态环境和其他系统环境)和跑在上面的应用。

Docker容器

启动容器

启动容器有两种方式,一种是基于镜像新建一个容器并启动,另外一个是将在终止状态(exited)的容器重新启动。

因为 Docker 的容器实在太轻量级了,很多时候用户都是随时删除和新创建容器。

新建并启动

所需要的命令主要为 docker run

PS D:\hexoBlog> docker run ubuntu:18.04 /bin/echo 'Hello world'
Unable to find image 'ubuntu:18.04' locally
18.04: Pulling from library/ubuntu
284055322776: Pull complete
Digest: sha256:0fedbd5bd9fb72089c7bbca476949e10593cebed9b1fb9edf5b79dbbacddd7d6
Status: Downloaded newer image for ubuntu:18.04
Hello world
PS D:\hexoBlog>

下面的命令则启动一个 bash 终端,允许用户进行交互。

PS D:\hexoBlog> docker run -t -i ubuntu:18.04 /bin/bash
root@90c7e77fd36f:/# 

-t 选项让Docker分配一个伪终端(pseudo-tty)并绑定到容器的标准输入上, -i 则让容器的标准输入保持打开。

在交互模式下,用户可以通过所创建的终端来输入命令,例如

PS D:\hexoBlog> docker run -t -i ubuntu:18.04 /bin/bash
root@90c7e77fd36f:/# pwd
/

当利用 docker run 来创建容器时,Docker 在后台运行的标准操作包括:

  • 检查本地是否存在指定的镜像,不存在就从 registry 下载
  • 利用镜像创建并启动一个容器
  • 分配一个文件系统,并在只读的镜像层外面挂载一层可读写层
  • 从宿主主机配置的网桥接口中桥接一个虚拟接口到容器中去
  • 从地址池配置一个 ip 地址给容器
  • 执行用户指定的应用程序
  • 执行完毕后容器被终止

启动已终止容器

可以利用 docker start [OPTIONS] 容器 [容器2...] 命令,直接将一个已经终止(exited)的容器启动运行。

PS D:\hexoBlog> docker start 90c7e77fd36fe91b84dcf4b400ebc99b84875bcd7eb4df4646bf4b3e44e43b61
90c7e77fd36fe91b84dcf4b400ebc99b84875bcd7eb4df4646bf4b3e44e43b61
PS D:\hexoBlog> docker ps
CONTAINER ID   IMAGE          COMMAND       CREATED         STATUS         PORTS     NAMES
90c7e77fd36f   ubuntu:18.04   "/bin/bash"   6 minutes ago   Up 5 seconds             awesome_dijkstra
PS D:\hexoBlog>

守护态运行

更多的时候,需要让 Docker 在后台运行而不是直接把执行命令的结果输出在当前宿主机下。

此时,可以通过添加 -d 参数来实现。

如果不使用 -d 参数运行容器。

PS D:\hexoBlog> docker run ubuntu:18.04 /bin/bash -c "while true; do echo hello world; sleep 1; done"
hello world
hello world
hello world

容器会把输出的结果 (STDOUT) 打印到宿主机上面

如果使用了 -d 参数运行容器。

PS D:\hexoBlog> docker run -d ubuntu:18.04 /bin/bash -c  "while true; do echo hello world; sleep 1; done"
088422d392d10c33c0607f0b324d22ed77ee50e6f84b59e980d31bb8be08a146
PS D:\hexoBlog> docker container ls
CONTAINER ID   IMAGE          COMMAND                  CREATED          STATUS          PORTS     NAMES
088422d392d1   ubuntu:18.04   "/bin/bash -c 'while…"   28 seconds ago   Up 27 seconds             awesome_shirley
PS D:\hexoBlog> docker container logs 088
hello world
hello world
hello world
hello world
hello world
hello world
hello world
hello world
hello world

此时容器会在后台运行并不会把输出的结果 (STDOUT) 打印到宿主机上面(输出结果可以用 docker logs 查看)。

使用 -d 参数启动后会返回一个唯一的 id,也可以通过 docker container ls 命令来查看容器信息。

要获取容器的输出信息,可以通过 docker container logs 命令。

终止

可以使用 docker container stop 来终止一个运行中的容器。

PS D:\hexoBlog> docker container stop 088
088
PS D:\hexoBlog>

例如对于上一章节中只启动了一个终端的容器,用户通过 exit 命令或 Ctrl+d 来退出终端时,所创建的容器立刻终止。

终止状态的容器可以用 docker container ls -a 命令看到。例如

PS D:\hexoBlog> docker container ls
CONTAINER ID   IMAGE     COMMAND   CREATED   STATUS    PORTS     NAMES
PS D:\hexoBlog> docker container ls -a
CONTAINER ID   IMAGE          COMMAND                  CREATED         STATUS                        PORTS     NAMES
088422d392d1   ubuntu:18.04   "/bin/bash -c 'while…"   8 minutes ago   Exited (137) 50 seconds ago             awesome_shirley
PS D:\hexoBlog>

处于终止状态的容器,可以通过 docker container start 命令来重新启动。

此外,docker container restart 命令会将一个运行态的容器终止,然后再重新启动它。

PS D:\hexoBlog> docker container ls
CONTAINER ID   IMAGE          COMMAND                  CREATED         STATUS         PORTS     NAMES
088422d392d1   ubuntu:18.04   "/bin/bash -c 'while…"   6 minutes ago   Up 6 minutes             awesome_shirley
PS D:\hexoBlog> docker container restart 088
088

进入容器

exec 命令

-i -t 参数

docker exec 后边可以跟多个参数,这里主要说明 -i -t 参数。

只用 -i 参数时,由于没有分配伪终端,界面没有我们熟悉的 Linux 命令提示符,但命令执行结果仍然可以返回。

-i -t 参数一起使用时,则可以看到我们熟悉的 Linux 命令提示符。

PS D:\hexoBlog> docker exec -it 088 /bin/bash
root@088422d392d1:/# exit
exit

docker exec 无法进入容器问题解决

docker run -d -P --name web --mount source=my-vol,target=/usr/share/nginx/html nginx:alpine

PS C:\Users\wang> docker exec -it f9f /bin/bash
OCI runtime exec failed: exec failed: unable to start container process: exec: "/bin/bash": stat /bin/bash: no such file or directory: unknown

经过各种求教,得到的答案,nginx:alpine精简版,在做镜像的时候,只装了sh,没有装bash,所以用不了bash。shell类型有很多种,但是sh类型的shell是最基础的,所以大部分镜像都支持。这就不难理解为什么docker exec -it 可以使用 /bin/sh进入镜像内部了。

docker exec使用小技巧:后面的/bin/或者/usr/bin/可以省略掉,直接写sh 或者 bash。

导入和导出

导出容器

PS C:\Users\wang> docker export 088 > dead.tar
PS C:\Users\wang> docker import dead.tar test20210608ubuntu:v3
Error response from daemon: Error processing tar file(exit status 1): archive/tar: invalid tar header

windows下会导出到当前D:\hexoBlog路径下

>“符号仅在linux下使用 windows中只能用-o导出

导入容器快照

PS C:\Users\wang> docker export 088 -o dead.tar
PS C:\Users\wang> docker import dead.tar test20210ntu:v3
sha256:1888c816f59ea7288cfd82be6922e493f67f05e5fbbc754a4046efb541c83197
PS C:\Users\wang>

删除

可以使用 docker container rm 来删除一个处于终止状态的容器。

如果要删除一个运行中的容器,可以添加 -f 参数。Docker 会发送 SIGKILL 信号给容器。

PS C:\Users\wang> docker container ls
CONTAINER ID   IMAGE          COMMAND                  CREATED          STATUS         PORTS     NAMES
088422d392d1   ubuntu:18.04   "/bin/bash -c 'while…"   47 minutes ago   Up 6 minutes             awesome_shirley
PS C:\Users\wang> docker container rm -f 088
088
PS C:\Users\wang> docker container ls
CONTAINER ID   IMAGE     COMMAND   CREATED   STATUS    PORTS     NAMES
PS C:\Users\wang> docker container ls -a
CONTAINER ID   IMAGE     COMMAND   CREATED   STATUS    PORTS     NAMES
PS C:\Users\wang>

清理所有处于终止状态的容器

docker container ls -a 命令可以查看所有已经创建的包括终止状态的容器,如果数量太多要一个个删除可能会很麻烦,用下面的命令可以清理掉所有处于终止状态的容器。

docker container prune

容器自启动

新建容器时自启动

# 新建容器时 --restart=always
docker run -d --restart=always --name mynginx -p 8080:80 nginx 

已有容器设置自启动

PS C:\Users\wang> docker update --restart=always portainer
portainer
PS C:\Users\wang>

如果docker本身不是开机自启动,请先设置docker开机自启
systemctl enable docker

查看日志

PS C:\Users\wang> docker logs -f portainer
2023/04/13 16:07:19 Warning: the --template-file flag is deprecated and will likely be removed in a future version of Portainer.
2023/04/13 16:07:23 [ERROR] [http,client] [message: unexpected status code] [status_code: 403]

从容器内拷贝文件到主机上

docker cp 容器id:容器内路径 目的主机路径

文章作者: WangQingLei
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 WangQingLei !
 上一篇
docker-volumes docker-volumes
如何在 Docker 内部以及容器之间管理数据,在容器中管理数据主要有两种方式:数据卷(Volumes)和 挂载主机目录 (Bind mounts)
2023-04-03
下一篇 
docker-image docker-image
Docker 运行容器前需要本地存在对应的镜像,如果本地不存在该镜像,Docker 会从镜像仓库下载该镜像。
2023-03-31
  目录