Docker是一组平台即服务(PaaS)的产品。它基于操作系统层级的虚拟化技术,将软件与其依赖项打包为容器。托管容器的软件称为 Docker 引擎。Docker能够帮助开发者在轻量级容器中自动部署应用程序,并使得不同容器中的应用程序彼此隔离,高效工作。该服务有免费和高级版本,它于 2013 年首次发布,由 Docker, Inc. 开发。
Docker 与容器
什么是 Docker ?
Docker 开源项目背景
Docker 是基于 Go 语言实现的开源容器项目,它诞生于 2013 年年初,最初发起者是 dotCloud 公司。Docker 自开源后受到业界广泛的关注和参与,目前已有 80 多个相关开源组建项目,逐渐形成了围绕 Docker 容器的完整的生态体系。目前,Docker 项目已加入 Linux 基金会,并遵循 Apache 2.0 协议,全部开源代码均在http://github.com/docker项目仓库中进行维护。
现在主流的操作系统,包括 Linux 各大发行版、macOS、Windows等都已经支持 Docker 。Docker 的构想是要实现 Build, Ship and Run Any App, Anywhere,即通过对应用的封装Packaging、分发Distribution、部署Depolyment和运行Runtime生命周期进行管理,达到应用组件级别的一次封装,到处运行。这里的应用组件,即可以是一个 Web 应用、一个编译环境,也可以是一套数据库平台服务,甚至是一个操作系统或集群。
基于 Linux 平台上的多项开源技术,Docker 提供了高效、敏捷和轻量级的容器方案,并支持部署到本地环境和多种主流云平台。可以说,Docker 首次为应用的开发、运行和部署提供了一站式的实用解决方案。
Linux 容器技术
与大部分新兴技术的诞生一样,Docker 也并非是从石头缝里面蹦出来的,而是站在前任的肩膀上。其中,最重要的就是 Linux Containers,LXC,也就是 Linux 容器技术。容器有效地将由单个操作系统管理地资源划分到孤立的组中,以更好地在孤立的组之间平衡有冲突的资源使用需求。与虚拟化相比,这样既不需要指令级模拟,也不需要即时翻译。容器可以在核心 CPU 本地运行指令,而不需要任何专门的解释机制。此外,也避免了准虚拟化和系统调用替换中的复杂性。
test@VM-0-9-ubuntu:~$ docker images REPOSITORY TAG IMAGE ID CREATED SIZE test/ubuntu dev 6bb86ec47445 4 weeks ago 125MB test/ununt 16.04 6bb86ec47445 4 weeks ago 125MB ubuntu 16.04 005d2078bdfa 4 weeks ago 125MB
其中镜像 ID 信息十分重要,它唯一标识了镜像。在使用镜像 ID 的时候,一般可以使用该 ID 的前若干个字符组成的可区分串来替代完整的 ID 。TAG 信息用于标记来自同一个仓库的不同镜像,例如 ubuntu 仓库中有多个镜像,通过 TAG 信息来区分发行版本,如 18.04、18.10 等。镜像大小信息只表示了该镜像的逻辑体积大小,实际上由相同的镜像层本地只会存储一份,物理上占用的内存空间会小于各镜像逻辑体积之和。
docker images子命令主要支持如下选项,用户可以自由组合:-a,–all=true|false,列出所有,包括临时文件镜像文件,默认为 false;--digests,可选值为 true 或 false,用于列出镜像的数字摘要值,默认值为 false;-f,–filter=[],用于过滤列出的镜像,如 dangling=true,则只显示没有被使用的镜像,也可指定带有特定标注的镜像等;--format,–format=”TEMPLATE”,控制输出格式,如 .ID 代表 ID 信息,.Repository 代表仓库信息等;--no-trunc,可选值为 true 或 false,对输出结果中太长的部分是否进行截断,如镜像 ID 信息,默认是 true;-q,–quite=true|false,仅输出 ID 信息,默认值 false。
1 2 3 4 5 6 7 8 9 10
test@VM-0-9-ubuntu:~$ docker images --help Usage: docker images [OPTIONS] [REPOSITORY[:TAG]] List images Options: -a, --all Show all images (default hides intermediate images) --digests Show digests -f, --filter filter Filter output based on conditions provided --format string Pretty-print images using a Go template --no-trunc Don't truncate output -q, --quiet Only show numeric IDs
test@VM-0-9-ubuntu:~$ docker tag ubuntu:18.04 myubuntu:18.04 test@VM-0-9-ubuntu:~$ docker images REPOSITORY TAG IMAGE ID CREATED SIZE test/ubuntu dev 6bb86ec47445 4 weeks ago 125MB test/ununt 16.04 6bb86ec47445 4 weeks ago 125MB ubuntu 16.04 005d2078bdfa 4 weeks ago 125MB myubuntu 18.04 c3c304cb4f22 4 weeks ago 64.2MB ubuntu 18.04 c3c304cb4f22 4 weeks ago 64.2MB
比较后可以发现,ubuntu:18.04和myubuntu:18.04的镜像 ID 是一致的,说明它们实际上是指向了同一个镜像文件,只是别名不同而已。docker tag 命令添加的标签实际上起到了类似链接的作用。
test@VM-0-9-ubuntu:~$ docker search --filter=is-official=true nginx NAME DESCRIPTION STARS OFFICIAL AUTOMATED nginx Official build of Nginx. 13224 [OK]
再比如,搜索所有收藏数超过 4,且关键词包括 tensorflow 的镜像:
1 2 3 4 5 6 7 8 9 10 11 12
test@VM-0-9-ubuntu:~$ docker search --filter=stars=4 tensorflow NAME DESCRIPTION STARS OFFICIAL AUTOMATED tensorflow/tensorflow Official Docker images for the machine learn… 1689 jupyter/tensorflow-notebook Jupyter Notebook Scientific Python Stack w/ … 217 tensorflow/serving Official images for TensorFlow Serving (http… 88 xblaster/tensorflow-jupyter Dockerized Jupyter with tensorflow 54 [OK] rocm/tensorflow Tensorflow with ROCm backend support 44 floydhub/tensorflow tensorflow 24 [OK] bitnami/tensorflow-serving Bitnami Docker Image for TensorFlow Serving 14 [OK] opensciencegrid/tensorflow-gpu TensorFlow GPU set up for OSG 12 ibmcom/tensorflow-ppc64le Community supported ppc64le docker images fo… 5 tensorflow/tf_grpc_test_server Testing server for GRPC-based distributed ru… 4
test@VM-0-9-ubuntu:~$ docker images REPOSITORY TAG IMAGE ID CREATED SIZE python 3 97b0518f8505 4 minutes ago 95.2MB ubuntu 16.04 d7a59f1b3c8e 33 minutes ago 505MB debian stretch-slim fa41698012c7 9 days ago 55.3MB ubuntu 18.04 c3c304cb4f22 4 weeks ago 64.2MB # 1.登录`Docker`仓库, 登录成功后, 登录信息会被记录到本地`~/.docker`目录下. test@VM-0-9-ubuntu:~$ docker login Login with your Docker ID to push and pull images from Docker Hub. If you don't have a Docker ID, head over to https://hub.docker.com to create one. Username: ------- Password: ------- WARNING! Your password will be stored unencrypted in /home/test/.docker/config.json. Configure a credential helper to remove this warning. See https://docs.docker.com/engine/reference/commandline/login/#credentials-store Login Succeeded # 2.先添加新的标签, 修改为:`USER/REPOSITORY:TAG`. test@VM-0-9-ubuntu:~$ docker tag ubuntu:18.04 albertxn97/ubuntu:18.04 # 3.使用`docker [image] push`命令上传镜像. # 第一次上传时, 会提示输入登录信息或进行注册, 之后登录信息会被记录到本地``目录下》 test@VM-0-9-ubuntu:~$ docker push albertxn97/ubuntu:18.04 The push refers to repository [docker.io/albertxn97/ubuntu] 28ba7458d04b: Mounted from library/mongo 838a37a24627: Mounted from library/mongo a6ebef4a95c3: Pushed b7f7d2967507: Pushed 18.04: digest: sha256:b58746c8a89938b8c9f5b77de3b8cf1fe78210c696ab03a1442e235eea65d84f size: 1152 # 4.登出`Docker`仓库. test@VM-0-9-ubuntu:~$ docker logout Removing login credentials for https://index.docker.io/v1/
test@VM-0-9-ubuntu:~$ docker run --name mytest -itd ubuntu:18.04 /bin/bash 5b70a3ec5da46ab783935ebf27cf4911325e8a49858b5a183bd56c8e9b95b44a test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 5b70a3ec5da4 ubuntu:18.04 "/bin/bash" 11 seconds ago Up 10 seconds mytest test@VM-0-9-ubuntu:~$ docker pause mytest mytest test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 5b70a3ec5da4 ubuntu:18.04 "/bin/bash" 11 seconds ago Up About a minute (Paused) mytest
test@VM-0-9-ubuntu:~$ docker run -itd ubuntu:18.04 b0a1eaef4d7df358e8f625bc11368ef3218b9b33d72b67a28c24ec940d370586 test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES b0a1eaef4d7d ubuntu:18.04 "/bin/bash" 9 seconds ago Up 8 seconds vigilant_zhukovsky test@VM-0-9-ubuntu:~$ docker attach b0a1eaef4d7d root@b0a1eaef4d7d:/# exit test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES b189a2a3f612 ubuntu:18.04 "/bin/bash" 7 minutes ago Up 7 minutes mystifying_torvalds test@VM-0-9-ubuntu:~$ docker rm b189a2a3f612 Error response from daemon: You cannot remove a running container b189a2a3f61244b48a93fdcbb6..... Stop the container before attempting removal or force remove test@VM-0-9-ubuntu:~$ docker rm -f b189a2a3f612 b189a2a3f612 test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
# 导出`f0bebe1a8d7b`容器. test@VM-0-9-ubuntu:~$ docker export f0bebe1a8d7b -o ubuntu_18.04.tar test@VM-0-9-ubuntu:~$ ll total 312644 drwxr-xr-x 12 test test 4096 Jun 3 10:27 ./ drwxr-xr-x 4 root root 4096 Mar 18 10:09 ../ -rw------- 1 test test 66612736 May 25 09:37 ubuntu_18.04.tar
之后,可将导出的 tar 文件传输到其他机器上,然后再通过导入命令导入到系统中,实现容器的迁移。
导入容器
导出的文件又可以使用docker import命令导入变成镜像,该命令格式为:
1 2 3 4 5 6
# Import the contents from a tarball to create a filesystem image. Usage: docker import [OPTIONS] file|URL|- [REPOSITORY[:TAG]]
Options: -c, --change list 在导入的同时执行对容器进行修改的`Dockerfile`指令. -m, --message string Set commit message for imported image
1 2 3 4 5 6 7
# 将上一节导出的`ubuntu_18.04.tar`文件导入到系统中: test@VM-0-9-ubuntu:~$ docker import ubuntu_18.04.tar albert/ubuntu:18.04 sha256:841b36a191f2c3e0e5a57ea041b7625f64d048f0fbca3eb197b9c201253d400a test@VM-0-9-ubuntu:~$ docker images REPOSITORY TAG IMAGE ID CREATED SIZE albert/ubuntu 18.04 841b36a191f2 11 seconds ago 64.2MB ubuntu 18.04 c3c304cb4f22 5 weeks ago 64.2MB
test@VM-0-9-ubuntu:~$ docker login Login with your Docker ID to push and pull images from Docker Hub. If you don't have a Docker ID, head over to https://hub.docker.com to create one. Username: albertxn Password: WARNING! Your password will be stored unencrypted in /home/test/.docker/config.json. Configure a credential helper to remove this warning. See https://docs.docker.com/engine/reference/commandline/login/#credentials-store Login Succeeded
数据卷是一个可供容器使用的特殊目录,将主机操作系统目录直接映射进容器,类似于 Linux 中的 mount 行为,数据卷可以提供很多有用的特性:
数据卷可以在容器之间共享和重用,容器间传递数据将变得高效与方便;
对数据卷内数据的修改会立马生效,无论是容器内操作还是本地操作;
对数据卷的更新不会影响镜像,解耦开应用和数据;
卷会一直存在,知道没有容器使用,可以安全地卸载它。
创建数据卷
Docker 提供了 volume 子命令来管理数据卷,如下命令可以快速在本地创建一个数据卷:
1 2 3 4 5 6 7 8 9 10
ubuntu@VM-0-9-ubuntu:~$ docker volume Usage: docker volume COMMAND Manage volumes Commands: create 创建一个数据卷 inspect 查看详细信息 ls 列出已有数据卷 prune 清理无用数据卷 rm 删除数据卷 Run 'docker volume COMMAND --help' for more information on a command.
1 2 3 4 5 6 7 8 9 10
# 快速在本地创建一个数据卷. test@VM-0-9-ubuntu:~$ docker volume create -d local test test # 此时, 查看`/var/lib/docker/volumes`路径下, 会发现所创建地数据卷位置(需要一定地权限). ubuntu@VM-0-9-ubuntu:~$ sudo ls -l /var/lib/docker/volumes total 156 drwxr-xr-x 3 root root 4096 Jun 8 12:19 1688a7a3c89a5f3783dbca32e7fd5c8e03cd4680c683f61b3dc8406684526f23 drwxr-xr-x 3 root root 4096 Apr 26 14:46 ffb8829214e3c6a151bed2574a4c67ec8433219180cfa6046596fa634ca1fb6c -rw------- 1 root root 65536 Jun 9 10:45 metadata.db drwxr-xr-x 3 root root 4096 Jun 9 10:45 test
绑定数据卷
除了使用 volume 子命令来管理数据卷之外,还可以在创建容器时将主机本地的任意路径挂载到容器内作为数据卷,这种形式创建的数据卷称为绑定数据卷。在用 docker [container] run 命令的时候,可以用 –mount 选项来使用数据卷,它支持三种类型的数据卷,包括:
vloume,普通数据卷,映射到主机 /var/lib/docker/volumes 路径下;
bind,绑定数据卷,映射到主机指定路径下;
tmpfs,临时数据卷,只存在于内存中。
下面使用 training/webapp 镜像创建一个 Web 容器,并创建一个数据卷挂载到容器的 /opt/webapp 目录:
test@VM-0-9-ubuntu:~$ docker run -it -v /dbdata --name dbdata ubuntu:18.04 root@76fde0cbb7fc:/# root@76fde0cbb7fc:/# ls bin boot dbdata dev etc home lib lib64 media mnt opt proc root run sbin srv sys tmp usr var
test@VM-0-9-ubuntu:~/webapp$ docker run --volumes-from dbdata -v $(pwd):/backup --name worker ubuntu:18.04 tar -zvcPf /backup/backup.tar /dbdata /dbdata/ /dbdata/ceshi.txt test@VM-0-9-ubuntu:~/webapp$ ll total 12 drwxrwxr-x 2 test test 4096 Jun 9 13:36 ./ drwxr-xr-x 19 test test 4096 Jun 9 11:05 ../ -rw-r--r-- 1 root root 149 Jun 9 13:36 backup.tar
# 使用`-P`随机端口. test@VM-0-9-ubuntu:~$ docker run -d -P --name web -v $HOME/webapp:/opt/webapp:ro nginx:1.19.0 a91567287b5acccc0e3a2f9e9caca50d7adcd575a0569a641a9e5b8c6c629ae4 test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES a91567287b5a nginx:1.19.0 "/docker-entrypoint.…" 4 seconds ago Up 2 seconds 0.0.0.0:32777->80/tcp web test@VM-0-9-ubuntu:~$ docker logs a91567287b5a 2020/06/09 06:26:49 [error] 28#28: *1 open() "/usr/share/nginx/html/favicon.ico" failed (2: No such file or directory), client: 59.41.66.146, server: localhost, request: "GET /favicon.ico HTTP/1.1", host: "49.235.24.68:32777", referrer: "http://49.235.24.68:32777/"
1 2 3 4 5
test@VM-0-9-ubuntu:~$ docker run -d -p 12345:80 --name web -v $HOME/webapp:/opt/webapp:ro nginx:1.19.0 6973577c4033d6c528408969cd32181c61fc70334a66e28de907318d6e510d89 test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 6973577c4033 nginx:1.19.0 "/docker-entrypoint.…" 3 seconds ago Up 2 seconds 0.0.0.0:12345->80/tcp web
映射多个接口地址
1 2 3
# 多次使用`-p`标记可以绑定多个端口. test@VM-0-9-ubuntu:~$ docker run -d -p 12345:80 -p 54321:80 --name web -v $HOME/webapp:/opt/webapp:ro nginx:1.19.0 fa43a3fb7a2a79da9c3ab73ddaa87b4678571c370ab7949f3d05e384db4a2888
映射到指定地址的指定端口
1
$ docker run -d -p 127.0.0.1:12345:80 --name web -v $HOME/webapp:/opt/webapp:ro nginx:1.19.0
映射到指定地址的任意端口
1 2 3 4
# 绑定任意端口到容器的`80`端口, 本地主机会自动分配一个端口. $ docker run -d -p 127.0.0.1::80 --name web -v $HOME/webapp:/opt/webapp:ro nginx:1.19.0 # 使用`udp`标记来指定`udp`端口. $ docker run -d -p 127.0.0.1:12345:80/udp --name web -v $HOME/webapp:/opt/webapp:ro nginx:1.19.0
查看映射端口配置
使用docker port来查看当前映射的端口配置,也可以查看到绑定的地址:
1 2 3 4 5 6 7 8
test@VM-0-9-ubuntu:~$ docker run -d -p 12345:80 -p 54321:80 --name web -v $HOME/webapp:/opt/webapp:ro nginx:1.19.0 8f51778bfd0dfba408e6042659ee7f5390727f086d0c3e8b85a3515c0223a57c test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 8f51778bfd0d nginx:1.19.0 "/docn…" 19 seconds ago Up 17 seconds 0.0.0.0:12345->80/tcp, 0.0.0.0:54321->80/tcp web test@VM-0-9-ubuntu:~$ docker port 8f51778bfd0d 80/tcp -> 0.0.0.0:54321 80/tcp -> 0.0.0.0:12345
容器有自己的内部网络和 IP 地址,使用docker [container] inspect ID可以获取容器的具体信息。
互联机制实现便捷互访
容器的互联是一种让多个容器中的应用进行快速交互的方式,它会在源和接收容器之间创建连接关系,接收容器可以通过容器名快速访问到源容器,而不用指定具体的 IP 地址。
自定义容器命名:
连接系统依据容器的名称来执行,因此,首先需要自定义一个好记的容器名,虽然当创建容器的时候,系统默认会分配一个名字,但自定义命名容器有两个好处,一是自定义的命名,比较好记,比如一个 Web 应用容器我们可以给它起名叫 web,一目了然;当要连接到其他容器的时候,即便重启,也可以使用容器名而不用改变,比如连接 web 容器到 db 容器。
使用--name标记可以为容器自定义命名:
1 2 3 4 5
test@VM-0-9-ubuntu:~$ docker run -d -p 12345:80 --name web nginx:1.19.0 0444145654cd09a973b381298de63413ccfe2d1ec1d0d095e120ad1348d5398a test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 0444145654cd nginx:1.19.0 "/docker-entrypoint.…" 7 seconds ago Up 6 seconds 0.0.0.0:12345->80/tcp web
注意:容器的名称是唯一的,如果已经命名了一个叫 web 的容器,当你要再次使用 web 这个名称的时候,需要先用docker rm命令删除之前创建的同名容器。另外,在执行docker [container] run的时候,如果添加了--rm标记,则容器在终止后立刻删除,且--rm和-d参数不能同时使用。
容器互联:
使用--link参数可以让容器之间安全地进行交互,下面先创建一个新的数据库容器:
1 2 3 4 5 6 7 8 9 10 11
# 1.创建一个`db`容器. test@VM-0-9-ubuntu:~$ docker run -d --name db training/postgres 4ac3e0aa8e65fbbd61d9774ba5d72b39b0785c37b8f2066cbabbc53daf3a6472 # 2.创建一个`web`容器, 并将它连接到`db`容器. test@VM-0-9-ubuntu:~$ docker run -d -p 12345:80 --name web --link db:db nginx:1.19.0 49a4a530d6b80b14b636bbb548d00eb3d1eaa7750596fd4eebc1a3683d9c0ae3 # 3.查看容器连接. test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 93c842299bdb nginx:1.19.0 "/docker-entry…" About a minute ago Up About a minute 0.0.0.0:12345->80/tcp web 4ac3e0aa8e65 training/postgres "su postgres -…" 3 minutes ago Up 3 minutes 5432/tcp db
--link参数地格式为--link name:alias,其中 name 是要链接的容器的名称,alias 是别名。上述代码结果可以看到自定义命名的容器:db 和 web 。Docker 相当于在两个互联的容器之间创建了一个虚拟通道,而且不用映射它们的端口到宿主主机上。在启动 db 容器的时候并没有使用 -p 和 -P 标记,从而避免了暴露数据库服务端口到外部网络上。
# 下面给出一个简单的示例: # escape=\ (backlash) # This dockerfile uses the ubuntu:xeniel image # VERSION 2 - EDITION 1 # Author: Albert丶XN # Command format: Instruction [arguments / command] ... # Base image to use, this must be set as the first line. FROM ubuntu:xeniel # Maintainer: docker_user <docker_user at email.com> (@docker_user) LABEL maintainer Albert丶XN<albertxn@126.com> # Commands to update the image RUN echo "deb http://archive.ubuntu.com/ubuntu xeniel main universe" >> /etc/apt/sources.list RUN apt-get update && apt-get install -y nginx RUN echo "\ndaemon off;" >> /etc/nginx/nginx.conf # Command when creating a new container CMD /usr/sbin/nginx
首先可以通过注释来指定解析器命令,后续通过注释说明镜像的相关信息。主体部分首先使用 FROM 指令指明所基于的镜像名称,接下来一般是使用 LABEL 指令说明维护者信息。后面则是镜像操作指令,例如,RUN 指令将对镜像执行跟随的命令,每运行一条 RUN 指令,镜像添加新的一层,并提交。最后 CMD 指令,来指定运行容器时的操作命令。
目前常用的 Linux 发行版主要包括 Debian/Ubuntu 系列和 CentOS/Fedora 系列。使用 Docker,只需要一个命令就能快速获取一个 Linux 发行版镜像,这是以往各种虚拟化技术都难以实现的。这些镜像一般都很精简,但是可以支持完整 Linux 系统的大部分功能。
BusyBox
BusyBox 是一个集成了一百多个常用 Linux 命令(如 cat、echo、grep、mount 等)的精简工具箱,它只有不到 2Mb 大小。
在 Docker Hub 中搜索 busybox 相关的镜像,如下所示:
1 2 3 4 5 6 7 8
test@VM-0-9-ubuntu:~$ docker search busybox NAME DESCRIPTION STARS OFFICIAL AUTOMATED busybox Busybox base image. 1909 [OK] progrium/busybox 71 [OK] radial/busyboxplus Full-chain, Internet enabled, busybox made f… 30 [OK] ...... trollin/busybox 0 ggtools/busybox-ubuntu Busybox ubuntu version with extra goodies 0 [OK]
从上结果可以看到,最受欢迎的镜像同时带有 OFFICIAL 标记,说明它是官方镜像。可以使用docker pull命令下载镜像 busybox:latest:
1 2 3 4 5 6 7 8
test@VM-0-9-ubuntu:~$ docker pull busybox:latest latest: Pulling from library/busybox 76df9210b28c: Pull complete Digest: sha256:95cf004f559831017cdf4628aaf1bb30133677be8702a8c5f2994629f637a209 Status: Downloaded newer image for busybox:latest test@VM-0-9-ubuntu:~$ docker images REPOSITORY TAG IMAGE ID CREATED SIZE busybox latest 1c35c4412082 17 hours ago 1.22MB
-H Add 'filename:' prefix -h Do not add 'filename:' prefix -n Add 'line_no:' prefix -l Show only names of files that match -L Show only names of files that don't match -c Show only count of matching lines ... -B N Print N lines of leading context -C N Same as '-A N -B N' -e PTRN Pattern to match -f FILE Read pattern from file
busybox 镜像虽然小巧,但包含了大量常见的 Linux 命令,读者可以用它快速熟悉 Linux 命令。
Alpine
Alpine 操作系统是一个面向安全的轻型 Linux 发行版,关注安全,性能和资源效能。Alpine 采用了 musl libc 和 BusyBox 以减少系统的体积和运行时间资源消耗,比 BusyBox 功能上更完善。Apline Docker 镜像继承了 Apline Linux 发行版的这些优势,这可以带来多个优势,如镜像下载速度加快、镜像安全性提高、主机之间的切换更方便、占用更少磁盘空间等。
test@VM-0-9-ubuntu:~$ docker search debian NAME DESCRIPTION STARS OFFICIAL AUTOMATED ubuntu Ubuntu is a Debian-based Linux operating sys… 10960 [OK] debian Debian is a Linux distribution that's compos… 3501 [OK] arm32v7/debian Debian is a Linux distribution that's compos… 66 itscaro/debian-ssh debian:jessie 28 OK] arm64v8/debian Debian is a Linux distribution that's compos… 23 ...
Ubuntu 系统简介及官方镜像使用
Ubuntu 是以桌面应用为主的 GUN/Linux 开源操作系统,每两年推出一个长期支持,Long Term Support,LTS 版本:
1 2 3 4 5 6 7
test@VM-0-9-ubuntu:~$ docker search --filter=stars=100 ubuntu NAME DESCRIPTION STARS OFFICIAL AUTOMATED ubuntu Ubuntu is a Debian-based Linux operating sys… 10960 [OK] dorowu/ubuntu-desktop-lxde-vnc Docker image to provide HTML5 VNC interface … 433 [OK] rastasheep/ubuntu-sshd Dockerized SSH service, built on top of offi… 244 [OK] consol/ubuntu-xfce-vnc Ubuntu container with "headless" VNC session… 219 [OK] ubuntu-upstart Upstart is an event-based replacement for th… 109 [OK]
# 1.下载和安装`ubuntu:16.04`. test@VM-0-9-ubuntu:~$ docker pull ubuntu:16.04 16.04: Pulling from library/ubuntu e92ed755c008: Pull complete b9fd7cb1ff8f: Pull complete ee690f2d57a1: Pull complete 53e3366ec435: Pull complete Digest: sha256:db6697a61d5679b7ca69dbde3dad6be0d17064d5b6b0e9f7be8d456ebb337209 Status: Downloaded newer image for ubuntu:16.04 # 2.运行`ubuntu:16.04`, 新建一个容器. test@VM-0-9-ubuntu:~$ docker run -it ubuntu:16.04 # 3.查看容器的版本. root@95cda544868c:/# cat /etc/lsb-release DISTRIB_ID=Ubuntu DISTRIB_RELEASE=16.04 DISTRIB_CODENAME=xenial DISTRIB_DESCRIPTION="Ubuntu 16.04.6 LTS" # 4.`apt-get update` root@95cda544868c:/# apt-get update Get:1 http://archive.ubuntu.com/ubuntu xenial InRelease [247 kB] Get:2 http://security.ubuntu.com/ubuntu xenial-security InRelease [109 kB] Get:3 http://archive.ubuntu.com/ubuntu xenial-updates InRelease [109 kB] Get:4 http://archive.ubuntu.com/ubuntu xenial-backports InRelease [107 kB] Get:5 http://archive.ubuntu.com/ubuntu xenial/main amd64 Packages [1558 kB] ... Fetched 16.5 MB in 5min 7s (53.6 kB/s) Reading package lists... Done # 5.查看`curl`, 命令不存在. root@95cda544868c:/# curl --help bash: curl: command not found # 6.安装`curl`命令. root@95cda544868c:/# apt-get install curl Reading package lists... Done Building dependency tree Reading state information... Done The following additional packages ....... After this operation, 19.0 MB of additional disk space will be used. Do you want to continue? [Y/n] y Get:1 http://archive.ubuntu.com/ubuntu xenial/main amd64 libffi6 amd64 3.2.1-4 [17.8 kB] ....... 127 added, 0 removed; done. Running hooks in /etc/ca-certificates/update.d... done. # 7.`curl`命令安装成功, 打印帮助文档. root@95cda544868c:/# curl --help Usage: curl [options...] <url> Options: (H) means HTTP/HTTPS only, (F) means FTP only --anyauth Pick "any" authentication method (H) -a, --append Append to target file when uploading (F/SFTP) --basic Use HTTP Basic Aut ......
CentOS/Fedora
CentOS 系统简介及官方镜像使用
CentOS 是基于 Redhat 的 Linux 发行版。CentOS 是目前企业级服务器的常用操作系统。Fedora 则主要面向个人桌面用户。CentOS,全称为 Community Enterprise Operatng System,社区企业操作系统,是基于 Red Hat Enterprise Linux 源代码编译而成。由于 CentOS 与 RedHat Linux 源于相同的代码基础,所以很多成本敏感且需要高稳定性的公司就使用 CentOS 来替代商业版的 RedHat 。
1 2 3 4 5 6
test@VM-0-9-ubuntu:~$ docker search --filter=stars=100 centos NAME DESCRIPTION STARS OFFICIAL AUTOMATED centos The official build of CentOS. 6029 [OK] ansible/centos7-ansible Ansible on Centos7 129 [OK] consol/centos-xfce-vnc Centos container with "headless" VNC session… 115 [OK] jdeathe/centos-ssh OpenSSH / Supervisor / EPEL/IUS/SCL Repos - … 114 [OK]
Fedora 系统简介与官方镜像使用
Fedora 是由 Fedora Project 社区开发,Red Hat 公司赞助的 Linux 发行版。它的目标是创建一套新颖、多功能并且自由和开源的操作系统。
1 2 3
test@VM-0-9-ubuntu:~$ docker search --filter=stars=100 fedora NAME DESCRIPTION STARS OFFICIAL AUTOMATED fedora Official Docker builds of Fedora 881 [OK]
test@VM-0-9-ubuntu:~$ docker pull ubuntu:18.04 18.04: Pulling from library/ubuntu Digest: sha256:3235326357dfb65f1781dbc4df3b834546d8bf914e82cce58e6e6b676e23ce8f Status: Image is up to date for ubuntu:18.04 docker.io/library/ubuntu:18.04 test@VM-0-9-ubuntu:~$ docker run -it ubuntu:18.04 /bin/bash root@7d4c8140e968:/#
# 由`ssh-keygen -t rsa`命令生成`$HOME/.ssh/id_rsa.pub`: test@VM-0-9-ubuntu:~$ ssh-keygen -t rsa Generating public/private rsa key pair. Enter file in which to save the key (/home/test/.ssh/id_rsa): Enter passphrase (empty for no passphrase): Enter same passphrase again: Your identification has been saved in /home/test/.ssh/id_rsa. Your public key has been saved in /home/test/.ssh/id_rsa.pub. The key fingerprint is: SHA256:jKAUpmP1gIJFquX6cy+nTpVQUNBVbmq0kL9Ag9OGc/4 test@VM-0-9-ubuntu The key's randomart image is: +---[RSA 2048]----+ |.o*oo=o.... | |o=..o=.. . | |=.o B.O . o | |o= . X O + | |. o * S | | . . + . | |. . E | | ...o . | | .+o=. | +----[SHA256]-----+
test@VM-0-9-ubuntu:~/sshd_ubuntu$ cd sshd_ubuntu test@VM-0-9-ubuntu:~/sshd_ubuntu$ touch Dockerfile run.sh test@VM-0-9-ubuntu:~/sshd_ubuntu$ ll total 8 drwxrwxr-x 2 test test 4096 Jun 8 09:07 ./ drwxrwxr-x 3 test test 4096 Jun 8 09:05 ../ -rw-rw-r-- 1 test test 0 Jun 8 09:07 Dockerfile -rw-rw-r-- 1 test test 0 Jun 8 09:07 run.sh
编写 run.sh 脚本和 authorized_keys 文件
1 2 3 4
# run.sh test@VM-0-9-ubuntu:~/sshd_ubuntu$ vim run.sh #!/bin/bash /usr/sbin/sshd -D
# authorized_keys # 由`ssh-keygen -t rsa`命令生成`$HOME/.ssh/id_rsa.pub`: test@VM-0-9-ubuntu:~$ ssh-keygen -t rsa Generating public/private rsa key pair. Enter file in which to save the key (/home/test/.ssh/id_rsa): Enter passphrase (empty for no passphrase): Enter same passphrase again: Your identification has been saved in /home/test/.ssh/id_rsa. Your public key has been saved in /home/test/.ssh/id_rsa.pub. The key fingerprint is: SHA256:jKAUpmP1gIJFquX6cy+nTpVQUNBVbmq0kL9Ag9OGc/4 test@VM-0-9-ubuntu The key's randomart image is: +---[RSA 2048]----+ |.o*oo=o.... | |o=..o=.. . | |=.o B.O . o | |o= . X O + | |. o * S | | . . + . | |. . E | | ...o . | | .+o=. | +----[SHA256]-----+ test@VM-0-9-ubuntu:~/sshd_ubuntu$ cat ~/.ssh/id_rsa.pub > authorized_keys
# 设置继承镜像. FROM ubuntu:18.04 # 提供一些作者的信息. MAINTAINER Albert丶XN (albertxn@126.com) # 下面开始运行命令, 此处更改 ubuntu 的源为国内 163 的源. RUN cd /etc/apt/ RUN echo "deb http://mirrors.163.com/ubuntu/ bionic main restricted universe multiverse" > sources.list RUN echo "deb http://mirrors.163.com/ubuntu/ bionic-security main restricted universe multiverse" >> sources.list RUN echo "deb http://mirrors.163.com/ubuntu/ bionic-updates main restricted universe multiverse" >> sources.list RUN echo "deb http://mirrors.163.com/ubuntu/ bionic-proposed main restricted universe multiverse" >> sources.list RUN echo "deb http://mirrors.163.com/ubuntu/ bionic-backports main restricted universe multiverse" >> sources.list RUN echo "deb-src http://mirrors.163.com/ubuntu/ bionic main restricted universe multiverse" >> sources.list RUN echo "deb-src http://mirrors.163.com/ubuntu/ bionic-security main restricted universe multiverse" >> sources.list RUN echo "deb-src http://mirrors.163.com/ubuntu/ bionic-updates main restricted universe multiverse" >> sources.list RUN echo "deb-src http://mirrors.163.com/ubuntu/ bionic-proposed main restricted universe multiverse" >> sources.list RUN echo "deb-src http://mirrors.163.com/ubuntu/ bionic-backports main restricted universe multiverse" >> sources.list RUN apt-get update # 安装`SSH`服务. RUN apt-get install -y openssh-server RUN mkdir -p /var/run/sshd RUN mkdir -p /root/.ssh # 取消`pam`限制. RUN sed -ri "s/session required pam_loginuid.so/#session required pam_loginuid.so/g" /etc/pam.d/sshd # 配置`SSH`远程登录 RUN sed -ie 's/#PermitRootLogin.*/PermitRootLogin yes/g' /etc/ssh/sshd_config RUN sed -ie 's/#PubkeyAuthentication.*/PubkeyAuthentication yes/g' /etc/ssh/sshd_config RUN sed 's/#AuthorizedKeysFile/AuthorizedKeysFile/g' /etc/ssh/sshd_config # 复制配置文件到相应位置, 并赋予脚本可执行权限. ADD authorized_keys /root/.ssh/authorized_keys ADD run.sh /run.sh RUN chmod 755 /run.sh # 开放端口 EXPOSE 22 # 设置自启动命令 CMD ["/run.sh"]
创建镜像
在 sshd_ubuntu 目录下,使用docker build命令来创建镜像:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
# `.`表示使用当前目录中的`Dockerfile`. test@VM-0-9-ubuntu:~/sshd_ubuntu$ docker build -t sshd_ubuntu:18.04 . Sending build context to Docker daemon 5.632kB Step 1/23 : FROM ubuntu:18.04 ---> c3c304cb4f22 Step 2/23 : MAINTAINER Albert丶XN (albertxn@126.com) ---> Running in a4fdb1cf6aef Removing intermediate container a4fdb1cf6aef ---> b9976500b78e Step 3/23 : RUN cd /etc/apt/ ---> Running in 004ef2e573c2 ... Step 23/23 : CMD ["/run.sh"] ---> Running in 19ba7d4241b9 Removing intermediate container 19ba7d4241b9 ---> a70ecf724414 Successfully built a70ecf724414 Successfully tagged sshd_ubuntu:18.04
1 2 3 4
test@VM-0-9-ubuntu:~/Dockrfile/sshd_ubuntu$ docker images REPOSITORY TAG IMAGE ID CREATED SIZE sshd_ubuntu 18.04 a70ecf724414 51 seconds ago 208MB ubuntu 18.04 c3c304cb4f22 6 weeks ago 64.2MB
test@VM-0-9-ubuntu:~$ docker run -p 26:22 -d sshd_ubuntu:18.04 /run.sh --restart=always af4d310f87a6747ccbe53524e16c56a8e260912adb4fe97b222c1c05728b3b4f test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES af4d310f87a6 sshd_ubuntu:18.04 "/run.sh --restart=a…" 3 seconds ago Up 2 seconds 0.0.0.0:26->22/tcp gracious_lumiere
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
# 在宿主主机或其他主机上, 可以通过 SSH 访问 26 端口来登录容器: test@VM-0-9-ubuntu:~$ ssh root@49.235.24.68 -p 26 Welcome to Ubuntu 18.04.4 LTS (GNU/Linux 4.4.0-130-generic x86_64) * Documentation: https://help.ubuntu.com * Management: https://landscape.canonical.com * Support: https://ubuntu.com/advantage This system has been minimized by removing packages and content that are not required on a system that users do not log into. To restore this content, you can run the 'unminimize' command. The programs included with the Ubuntu system are free software; the exact distribution terms for each program are described in the individual files in /usr/share/doc/*/copyright. Ubuntu comes with ABSOLUTELY NO WARRANTY, to the extent permitted by applicable law. root@af4d310f87a6:~#
# 进入一个创建好的 MySQL 容器并登录数据库, 如果未创建, 可以通过上一步进行从操作. # docker exec -it 容器ID bash test@VM-0-9-ubuntu:~$ docker exec -it 2ea42370f864 bash root@2ea42370f864:/# root@2ea42370f864:/# mysql -u root -p Enter password: Welcome to the MySQL monitor. Commands end with ; or \g. Your MySQL connection id is 3 Server version: 5.7.30 MySQL Community Server (GPL) Copyright (c) 2000, 2020, Oracle and/or its affiliates. All rights reserved. Oracle is a registered trademark of Oracle Corporation and/or its affiliates. Other names may be trademarks of their respective owners. Type 'help;' or '\h' for help. Type '\c' to clear the current input statement. mysql>
1 2 3 4 5
# 修改用户密码. mysql> ALTER USER 'root'@'localhost' IDENTIFIED BY '123456'; # 添加远程登录用户. mysql> CREATE USER 'test'@'%' IDENTIFIED WITH mysql_native_password BY '123456'; mysql> GRANT ALL PRIVILEGES ON *.* TO 'test'@'%';
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
# ERROR, Client does not support authentication protocol requested by server. # 1.进入容器: $ docker exec -it 容器ID /bin/bash # 2.进入`MySQL`: $ mysql -uroot -p # 3.授权: mysql> GRANT ALL ON *.* TO 'root'@'%'; # 4.刷新权限: mysql> flush privileges; # 5.更新加密规则: mysql> ALTER USER 'root'@'localhost' IDENTIFIED BY 'password' PASSWORD EXPIRE NEVER; # 6.更新`root`用户密码: mysql> ALTER USER 'root'@'%' IDENTIFIED WITH mysql_native_password BY '123456'; # 7.刷新权限: mysql> flush privileges;
MongoDB 是一款可扩展、高性能的开源文档数据库,是当今最流行的 NoSQL 数据库之一。它采用 C++ 开发,支持复杂的数据类型和强大的查询语言,提供了关系数据库的绝大部分功能。由于其高性能、易部署、易使用等特点,MongoDB 已经在很多领域都得到了广泛的应用。
安装和启动一个 MongoDB 数据库
1 2 3 4 5 6 7 8 9 10 11 12
# 用户可以使用官方镜像快速启动一个 MongoDB 实例: # https://hub.docker.com/_/mongo/?tab=tags test@VM-0-9-ubuntu:~$ docker run --name mymongo -d mongo:4.4.0-rc8 Unable to find image 'mongo:4.4.0-rc8' locally 4.4.0-rc8: Pulling from library/mongo ... Digest: sha256:a982894be1d5cc9479be27ec17a0f6d75b00c2bcb1c0b8ae7bf287ed695e9e66 Status: Downloaded newer image for mongo:4.4.0-rc8 382c201df5670e15fd3ce913c0adc80cebb2078e149d1ee6f427ac356044ab26 test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 382c201df567 mongo:4.4.0-rc8 "docker-entrypoint.s…" About a minute ago Up About a minute 27017/tcp mymongo
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
# 先通过`docker pull`获得镜像, 再新建一个容器: test@VM-0-9-ubuntu:~$ docker pull mongo:4.4.0-rc8 5.7: Pulling from library/mysql afb6ec6fdc1c: Pull complete .... Digest: sha256:a982894be1d5cc9479be27ec17a0f6d75b00c2bcb1c0b8ae7bf287ed695e9e66 Status: Downloaded newer image for mongo:4.4.0-rc8 docker.io/library/mysql:4.4.0-rc8 test@VM-0-9-ubuntu:~$ docker images REPOSITORY TAG IMAGE ID CREATED SIZE mongo 4.4.0-rc8 29c751d0b555 3 days ago 492MB test@VM-0-9-ubuntu:~$ docker run -p 27000:27017 -v $PWD/db:/data/db -d mongo:4.4.0-rc8 3f5f58cd1c9fb35eb471f0982903b9924342deafc473e34f6f6e19156039751f test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 3f5f58cd1c9f mongo:4.4.0-rc8 "docker-en…" 4 seconds ago Up 3 seconds 0.0.0.0:27000->27017/tcp intelligent_panini
test@VM-0-9-ubuntu:~$ docker run -it --link 3f5f58cd1c9f:db alpine:3.12.0 /bin/sh / # / # ls bin dev etc home lib media mnt opt proc root run sbin srv sys tmp usr var / # ping db PING db (172.18.0.3): 56 data bytes 64 bytes from 172.18.0.3: seq=0 ttl=64 time=0.124 ms 64 bytes from 172.18.0.3: seq=1 ttl=64 time=0.081 ms 64 bytes from 172.18.0.3: seq=2 ttl=64 time=0.085 ms 64 bytes from 172.18.0.3: seq=3 ttl=64 time=0.075 ms
test@VM-0-9-ubuntu:~$ docker run -it --link 3f5f58cd1c9f:db --entrypoint mongo mongo:4.4.0-rc8 --host db MongoDB shell version v4.4.0-rc8 connecting to: mongodb://db:27017/?compressors=disabled&gssapiServiceName=mongodb Implicit session: session { "id" : UUID("6dbf4f55-873d-4855-84f0-aaaa78315803") } MongoDB server version: 4.4.0-rc8 Welcome to the MongoDB shell. For interactive help, type "help". For more comprehensive documentation, see http://docs.mongodb.org/ Questions? Try the support group http://groups.google.com/group/mongodb-user --- .... > > db.version() 4.4.0-rc8 > > db.stats() { "db" : "test", "collections" : 0, "views" : 0, "objects" : 0, "avgObjSize" : 0, "dataSize" : 0, "storageSize" : 0, "totalSize" : 0, "indexes" : 0, "indexSize" : 0, "scaleFactor" : 1, "fileSize" : 0, "fsUsedSize" : 0, "fsTotalSize" : 0, "ok" : 1 } > > show dbs admin 0.000GB config 0.000GB local 0.000GB > > exit bye
Redis
Redis,全称 REmote DIctionary Server 是一个开源的基于内存的数据结构存储系统,可以作为数据库、缓存和消息的中间件。
安装和启动一个 Redis 数据库
1 2 3 4 5 6 7 8 9 10 11 12
# 用户可以使用官方镜像快速启动一个 Redis 实例: # https://hub.docker.com/_/redis?tab=tags test@VM-0-9-ubuntu:~$ docker run --name myredis -d redis:alpine3.12 Unable to find image 'redis:alpine3.12' locally alpine3.12: Pulling from library/redis ... Digest: sha256:50ce670996835d83e070a6b26ef168de774333cf6317cd1bad45f84da1421e24 Status: Downloaded newer image for redis:alpine3.12 94ccd00f0fd4ce1b942e2a95eeebc017bf8ffbf638a07342fb892b1bd2f10545 [xingabao@mu01 ~]$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 94ccd00f0fd4 redis:alpine3.12 "docker-entrypoint..." 20 seconds ago Up 17 seconds 6379/tcp myredis
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
# 先通过`docker pull`获得镜像, 再新建一个容器: test@VM-0-9-ubuntu:~$ docker pull redis:alpine3.12 alpine3.12: Pulling from library/redis ... Digest: sha256:50ce670996835d83e070a6b26ef168de774333cf6317cd1bad45f84da1421e24 Status: Downloaded newer image for redis:alpine3.12 docker.io/library/redis:alpine3.12 test@VM-0-9-ubuntu:~$ docker images REPOSITORY TAG IMAGE ID CREATED SIZE redis alpine3.12 e008f2ff99d0 3 days ago 31.5MB
test@VM-0-9-ubuntu:~$ docker run -itd --name redis-test -p 6379:6379 redis:alpine3.12 34a7fb8189f03ff1f18a7d1d2515fff091760d32975d6ebedf4bbd23104ba2d7 test@VM-0-9-ubuntu:~$ docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 34a7fb8189f0 redis:alpine3.12 "docker-entryp…" 5 seconds ago Up 4 seconds 0.0.0.0:6379->6379/tcp redis-test
进入一个 Redis 数据库
1 2 3 4 5 6 7 8 9 10 11 12 13 14
# docker exec -it 容器ID sh test@VM-0-9-ubuntu:~$ docker exec -it 34a7fb8189f0 sh /data # /data # uptime 07:37:13 up 1 day, 2:14, load average: 0.00, 0.01, 0.00 /data # ps -ef PID USER TIME COMMAND 1 redis 0:00 redis-server 24 root 0:00 sh 32 root 0:00 ps -ef /data # free total used free shared buff/cache available Mem: 3915340 756708 192768 40100 2965864 3165416 Swap: 0 0 0
通过端口访问 Redis 数据库
1 2 3 4 5 6 7 8 9 10
test@VM-0-9-ubuntu:~$ docker run -it --link redis-test:db alpine:3.12.0 /bin/sh / # / # ls bin dev etc home lib media mnt opt proc root run sbin srv sys tmp usr var / # ping db PING db (172.18.0.4): 56 data bytes 64 bytes from 172.18.0.4: seq=0 ttl=64 time=0.121 ms 64 bytes from 172.18.0.4: seq=1 ttl=64 time=0.108 ms 64 bytes from 172.18.0.4: seq=2 ttl=64 time=0.104 ms 64 bytes from 172.18.0.4: seq=3 ttl=64 time=0.111 ms
宿主机上直接使用 Redis 数据库
1 2 3 4 5 6 7 8 9
test@VM-0-9-ubuntu:~$ docker run -it --link redis-test:db --entrypoint redis-cli redis:alpine3.12 -h db db:6379> db:6379> ping PONG db:6379> set 1 2 OK db:6379> get 1 "2" db:6379> exit