Docker入门
一直听说虚拟化、Docker这些概念,但是一直没有机会,刚好公司项目要使用Docker部署,公司也没有这方面的人员了解,花几天时间突击一下这方面知识。
Docker简介
Docker 是一个开源的应用容器引擎,基于 Go 语言 并遵从Apache2.0协议开源。
Docker 可以让开发者打包他们的应用以及依赖包到一个轻量级、可移植的容器中,然后发布到任何流行的 Linux 机器上,也可以实现虚拟化。
容器是完全使用沙箱机制,相互之间不会有任何接口(类似 iPhone 的 app),更重要的是容器性能开销极低。
Docker的主要目标是“Build,Ship and Run Any App, Anywhere”,即通过对应用组件的封装(Packaging)、分发(Distribution)、部署(Deployment)、运行(Runtime)等生命周期的管理,达到应用组件级别的“一次封装,到处运行”(有点类似于java)。这里的应用组件,即可以是一个Web应用,也可以是一套数据库服务,甚至是一个操作系统或者编译器。
Docker的应用场景
- Web 应用的自动化打包和发布。
- 自动化测试和持续集成、发布
- 在服务型环境中部署和调整数据库或其他的后台应用
- 从头编译或者扩展现有的OpenShift或Cloud Foundry平台来搭建自己的PaaS环境
Docker的优点
- 简化程序
Docker让开发者可以打包他们的应用以及依赖包到一个可移植的容器中,然后发布到任何流行的Linux机器上,便可以实现虚拟化。Docker改变了虚拟化的方式,使开发者可以直接将自己的成果放入Docker中进行管理。过去需要数天乃至数周的任务,在Docker容器的处理下,只需要数秒就能完成。
- 避免选择恐惧症
Docker镜像中包含了运行环境和配置,所以Docker可以简化部署多种应用实例工作。比如Web应用、后台应用、数据库应用、大数据应用比如Hadoop集群、消息队列等等都可以打包成一个镜像部署。
- 节省开支
云计算时代的到来,使开发者不必为了追求效果而配置高额的硬件,Docker改变了高性能必然高价格的思维定势。Docker与云的结合,让云空间得到更充分的利用,不仅解决了硬件管理的问题,也改变了虚拟化的方式。
Centos的Docker安装与启动
- 检查Linux版本
[docker@localhost ~]$ uname -r
Docker要求Centos系统的内核版本高于3.10
- 安装Docker
切换到root用户,更新系统
[root@localhost ~]# yum update
安装Docker
[root@localhost ~]# yum -y install docker
Docker软件包和依赖包已经包含在默认的Centos-Extras软件源里了。
如果这种方式不能安装,也可使用下面的命令进行安装
[root@localhost ~]# curl -fsSL https://get.docker.com/ | sh
执行这个脚本后会添加docker.repo源并安装Docker
注:若安装失败,重新使用上面命令安装时有时会报错,只需要去家目录下的.docker目录中将docker的相关文件删除,然后重新执行命令下载即可。
- 启动Docker服务
[root@localhost ~]# service docker start
- 测试
[docker@localhost ~]$ docker run hello-world
由于本地没有hello-world这个镜像,所以会下载一个hello-world的镜像,并在容器中运行
Docker的基本使用
- 查看Docker常用命令
[docker@localhost ~]$ docker
或者
[docker@localhost ~]$ docker --help
如我们需要查看其中某个命令的使用方法,可使用以下命令
[docker@localhost ~]$ docker run --help
- 运行一个web应用
我们在Docker容器中运行一个Python Flask应用来运行一个web应用
[docker@localhost ~]$ docker run -d -P training/webapp python app.py
我们先来看看之前执行docker run --help命令后的结果吧
docker run [OPTIONS] IMAGE [COMMAND] [ARG...]
OPTIONS: 代表run命令的一些参数
IMAGE: 镜像名
COMMAND: 运行镜像之后要执行的命令
ARG...: 命令需要的一些参数
好了,我们现在来看看刚刚我们运行一个web应用的命令
-d, --detach=false Run container in background and print container ID
让容器在后台运行,默认是关闭的
-P, --publish-all=false Publish all exposed ports to random ports
让容器内部使用的网络端口映射到我们使用的主机上,默认是关闭的
注意: 我们这里用的是大写的-P
小写的-p手动将容器端口映射到宿主机上的端口,如
[docker@localhost ~]$ docker run -d -p 5000:5000 training/webapp python app.py
查看WEB应用容器
查看正在运行的容器
[docker@localhost ~]$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
f5d5071807a8 training/webapp "python app.py" 13 seconds ago Up 12 seconds 0.0.0.0:32768->5000/tcp prickly_davinci
查看所有已构建的容器
docker ps -a
包括正在运行,已停止的等多个容器。
结果中有容器ID,镜像名,端口,容器名等信息,其中端口显示了prickly_davinci容器端口的映射情况,此时映射的端口是容器自动做的映射,如果我们运行时没使用-P,而是使用-p手动映射,此处则显示手动指定的端口。其次容器名称此处为容器自动指定的,我们可以通过--name来手动指定,如
[docker@localhost ~]$ docker run -d -p 5000:5000 --name webapp training/webapp python app.py
上面默认都是绑定tcp端口,如果要绑定UDP端口,可以在端口后面加上/udp
[docker@localhost ~]$ docker run -d -p 5000:5000/udp --name webapp training/webapp python app.py
查看容器端口映射
- 使用容器ID查看容器端口映射情况
[docker@localhost ~]$ docker port f5d5071807a8
5000/tcp -> 0.0.0.0:32768
- 使用容器名称查看端口映射情况
[docker@localhost ~]$ docker port prickly_davinci
5000/tcp -> 0.0.0.0:32768
- 查看具体某个端口的映射情况
[docker@localhost docker]$ docker port tomcat 8080
0.0.0.0:8080
接下来凡是使用容器标识操作的都使用容器名称,并且容器ID也支持相同的命令操
查看WEB应用程序日志
[docker@localhost ~]$ docker logs -f modest_banach
-f: 让docker logs像使用tail -f一样来输出容器内部的标准输出
查看WEB应用程序容器的进程
[docker@localhost ~]$ docker top modest_banach
检查WEB应用程序
[docker@localhost ~]$ docker inspect modest_banach
停止WEB应用程序
[docker@localhost ~]$ docker stop modest_banach
启动WEB应用容器
[docker@localhost ~]$ docker start modest_banach
重启WEB应用容器
[docker@localhost ~]$ docker restart modest_banach
注:正在运行的容器我们可以使用restart来重启
移除WEB应用容器
[docker@localhost ~]$ docker rm modest_banach
注:移除容器时,容器必须是停止状态。
Docker镜像的使用
查看本地镜像列表
[docker@localhost ~]$ docker images
REPOSITORY TAG IMAGE ID CREATED VIRTUAL SIZE
各个选项说明:
- REPOSITORY: 表示镜像的仓库源
- TAG: 镜像的标签
- IMAGE ID: 镜像ID
- CREATED: 镜像创建时间
- SIZE: 镜像大小
同一个仓库源可以有多个TAG,代表这个仓库源的不同个版本,如ubuntu仓库源里,有15.10,14.04等多个不同的版本,我们可以使用REPOSITORY:TAG来定义不同的镜像,如
[docker@localhost ~]$ docker run -t -i ubuntu:15.10 /bin/bash
如果不指定镜像的版本标签,docker将默认使用latest镜像
获取一个新的镜像
[docker@localhost ~]$ docker pull ubuntu:15.10
查找镜像
[docker@localhost ~]$ docker search httpd
NAME DESCRIPTION STARS OFFICIAL AUTOMATED
NAME: 镜像仓库源的名称
DESCRIPTION: 镜像的描述
OFFICIAL: 是否是docker官方发布
拖取镜像
[docker@localhost ~]$ docker pull httpd
运行镜像
[docker@localhost ~]$ docker run httpd
自定义镜像
创建镜像
当我们从docker镜像仓库中下载的镜像不能满足我们的需求时,我们可以通过以下两种方式对镜像进行更改:
1、从已经创建的容器中更新镜像,并且提交这个镜像
2、使用Dockerfile指令来创建一个新的镜像
更新镜像
在更新镜像之前,我们先用以下命令启动容器,在容器中使用apt-get update命令更新,完成操作后使用exit退出容器。
[docker@localhost ~]$ docker run -t -i ubuntu:15.10 /bin/bash
root@2d60a31b8bdf:/# apt-get update
提交容器副本
[docker@localhost ~]$ docker commit -m="has update" -a="ubuntu/update" 2d60a31b8bdf ubuntu:v2
ea547a1aa6de52e24092ff3ca13ae7ae58cd35123e2e58e6f3d784208af7ef5e
-m: 提交的描述信息
-a: 指定镜像作者
2d60a31b8bdf: 容器ID
runoob/ubuntu:v2: 指定要创建的目标镜像名
构建镜像
创建Dockerfile,使用docker build命令来创建一个新的镜像
[docker@localhost docker]$ cat Dockerfile
FROM centos:6.7
MAINTAINER Fisher "artislong@haha.com"
RUN /bin/echo 'root:123456' |chpasswd
RUN useradd docker
RUN /bin/echo 'docker:123456' |chpasswd
RUN /bin/echo -e "LANG=\"en_US.UTF-8\"" >/etc/default/local
EXPOSE 22
EXPOSE 80
CMD /usr/sbin/sshd -D
Dockerfile是一个文本格式的配置文件,它由一行行命令语句(指令)组成,并且支持以#开头的注释行
每个指令都会在镜像上创建一个新的层,每个指令的前缀都必须大写。
第一条FROM,指定使用哪个镜像源
RUN指令告诉docker在镜像内执行命令,安装了什么。。。
然后我们通过Dockerfile文件来构建一个镜像
[docker@localhost docker]$ docker build -t runoob/centos:6.7 .
千万不要忽略最后面的 “.”,它表示使用当前目录下的Dockerfile文件
-t: 指定要创建的目标镜像名
我们可以使用新的镜像来创建容器
[docker@localhost docker]$ docker run -t -i runoob/centos:6.7 /bin/bash
[root@ebd742bf9af0 /]# id docker
uid=500(docker) gid=500(docker) groups=500(docker)
从上面看到新镜像已经包含了我们创建的用户docker
设置镜像标签
[docker@localhost docker]$ docker tag f38a8f197ee4 runoob/centos:dev
docker tag 镜像ID,镜像源名和新的标签名
Docker安装Nginx
创建Nginx目录,用于存放后面相关文件
[docker@localhost ~]$ mkdir -p ~/nginx/www ~/nginx/logs ~/nginx/conf
www目录将映射为nginx容器配置的虚拟目录
logs目录将映射为nginx容器的日志目录
conf目录里的配置文件将映射为nginx容器的配置文件
查找Docker Hub上的nginx镜像
[docker@localhost nginx]$ docker search nginx
拉取官方nginx镜像
[docker@localhost nginx]$ docker pull nginx
查看nginx本地镜像
[docker@localhost nginx]$ docker images nginx
使用nginx镜像
运行容器
[docker@localhost nginx]$ docker run -i -t -d -p 80:8081 --name nginx -v $PWD/www:/www -v $PWD/conf/nginx.conf:/etc/nginx/nginx.conf -v $PWD/logs:/wwwlogs -d nginx
-p 80:8081: 将容器的80端口映射到宿主机的8081端口
-name nginx: 将容器命名为nginx
-v $PWD/www:/www: 将主机中当前目录下的www目录挂载到容器的/www
-v $PWD/conf/nginx.conf:/etc/nginx/nginx.conf: 将主机中当前目录下的nginx.conf挂载到容器的/etc/nginx/nginx.conf
-v $PWD/logs:/wwwlogs: 将主机中当前目录下的logs挂载到容器的/wwwlogs
查看容器启动情况
[docker@localhost nginx]$ docker ps
通过浏览器访问
访问路径为: http://主机ip:8081/ ,就可访问nginx
Docker安装Tomcat
创建tomcat的相关目录
[docker@localhost ~]$ mkdir -p ~/tomcat/webapps ~/tomcat/logs ~/tomcat/conf
查找Docker Hub上的tomcat镜像
[docker@localhost ~]$ docker search tomcat
拉取官方tomcat镜像
[docker@localhost ~]$ docker pull tomcat
创建测试文件
-
在~/tomcat/webapps目录下创建test目录
[docker@localhost webapps]$ mkdir test
-
进入test目录,编写测试页面
[docker@localhost test]$ vi index.html
index.html文件内容:
<html> <head> <meta charset="utf-8"> <title>docker中的tomcat测试</title> </head> <body> Hello, World! <br> 哈哈哈哈,运行成功啦啦啦啦啦 </body> </html>
-
运行tomcat容器
[docker@localhost tomcat]$ docker run --name tomcat -p 8080:8080 -v $PWD/webapps/test:/usr/local/tomcat/webapps/test -d tomcat
命令说明:
-v $PWD/webapps/test:/usr/local/tomcat/webapps/test: 将主机中当前目录下的test挂载到容器的/test
启动成功后,在浏览器访问:http://主机ip:8080/test/index.html即可访问刚才编写的测试页面