容器服务 Container Service01

Docker-容器服务 Container Service01_第1张图片

一、LXC介绍

LXC为Linux Container的简写。
Linux Container容器是一种内核虚拟化技术,可以提供轻量级的虚拟化,以便隔离进程和资源,而且不需要提供指令解释机制以及全虚拟化的其他复杂性。

1)与传统虚拟化技术相比,它的优势在于:

与宿主机使用同一个内核,性能损耗小;
不需要指令级模拟;
不需要即时(Just-in-time)编译;
容器可以在CPU核心的本地运行指令,不需要任何专门的解释机制;
避免了准虚拟化和系统调用替换中的复杂性;
轻量级隔离,在隔离的同时还提供共享机制,以实现容器与宿主机的资源共享。

总结:Linux Container是一种轻量级的虚拟化的手段。

1.1、什么是docker

    Docker是**Docker.lnc**公司开源的一个基于LXC技术之上构建的Container**容器引擎**,源代码托管在Github上,基于Go语言并遵从**Apache2.0协议**开源 
    Docker是通过**内核虚拟化**技术(namespaces及cgroups等)来提供容器的**资源隔离与安全保障**等。由于Docker通过操作系统层的虚拟化实现隔离,所以Docker容器在运行时,不需要类似虚拟机(VM)额外的操作系统开销,**提高资源利用率**;

1.2、Docker的三大理念

构建  运输  运行

1.3、Docker组成

Docker的组成部分docker类似于**CS**结构 
 Docker **C**lient 
 Docker** S**erver 

自我理解:docker的启动就像server端,我们执行命令就像client端
1)server截图
Docker-容器服务 Container Service01_第2张图片
2)client截图
Docker-容器服务 Container Service01_第3张图片
提示:目前的版本是如果docker的服务端挂了,运行在docker上的所有容器都会挂掉
1.4.1 CLI 交互模型
Docker-容器服务 Container Service01_第4张图片

Docker的C/S模式
1.4.2 RemoteAPI交互模型Docker-容器服务 Container Service01_第5张图片

Docker的C/S模式-RemoteAPI

二、Docker组件

2.1镜像(Image)

 类似于系统镜像,我们要启动docker就需要镜像,与vm组成不同,但类似;

2.2容器(Container)

容器可以理解为运行在linux上的一个进程,我们可以对容器进行增、删、改、查,有隔离性,但没有vm隔离性高

2.3仓库(Repository)

 仓库就是存放docker镜像的地方,就像github统一存储一样,docker也有dockerhub,就像官网提供的公共仓库,蛮方便;

三、docker与其他产品的区别

3.1虚拟机和docker的区别(图解)

Docker-容器服务 Container Service01_第6张图片

3.2 Docker与OpenStack区别

类别 Docker Openstack/KVM 结论
虚拟化 内核虚拟化【依赖linux操作系统】 硬件虚拟化【CPU】 docker与openstack相对的虚拟结构不同
部署难度 非常简单 组件多,部署复杂 因为平台都是在已有生产环境的情况下,进行改造,所以尽量选择侵入性比较小的容器技术
启动速度 秒级 分钟级 天下武功,为快不破
执行性能 与物理系统相近 VM会浪费资源 核心业务对服务SLA要求非常苛刻
镜像体积 容器镜像MB 虚拟机镜像GB 集群调整,体积越小,并发越大
管理效率 管理简单 相互依赖,管理复杂 方便管理,才能增加效率,可控性是企业核心竞争力
隔离性 完全隔离 隔离性可以保证环境一致性
可管理性 单进程,建议不开ssh服务 系统管理全面 VM在这方面更强
网络连接 相对弱 借助Neutron可以灵活组件各类网络架构 VM在这方便更强,docker需要借助iptables或者第三方工具flanneld

四、Docker能做什么?

Docker-容器服务 Container Service01_第7张图片

4.1 简化配置

保留了VM虚拟化的优点,在所有主机上都可以运行docker来快速部署,并且可以把配置部署与开发代码一同上线;

4.2 完善流水线(pipeline)管理

 从本地开发-测试环境-预生产环境-灰度环境-生产环境,经过多次调试,开发总会说 “在我这可以啊,怎么到线上就不行了呢”,大多数原因就是环境不统一造成,使用docker就可以解决这个问题;

4.3 提高开发效率

发开效率与两点有密切关系,1就是测试环境尽量贴近生产环境 ,2减少发开环境部署这个步骤,docker占用的资源相对低很多,所以很轻松的就可以跑几十个服务

4.4 隔离应用

 多个应用环境在一起开发时,可能会先各种坑,主要是隔离的问题

4.5 整合服务器

docker隔离应用的能力使得Docker可以整合多个服务器以降低成本。由于没有多个操作系统的内存占用,以及能在多个实例之间共享没有使用的内存,Docker可以比虚拟机提供更好的服务器整合解决方案 

4.6 调试能力

Docker提供了很多的工具,这些工具不一定只是针对容器,但是却适用于容器。它们提供了很多的功能,包括可以为容器设置检查点、设置版本和查看两个容器之间的差别,这些特性可以帮助调试Bug。你可以在《Docker拯救世界》的文章中找到这一点的例证。

4.7 多租户环境

 另外一个Docker有意思的使用场景是在多租户的应用中,它可以避免关键应用的重写。我们一个特别的关于这个场景的 例子是为IoT(译者注:物联网)的应用开发一个快速、易用的多租户环境。这种多租户的基本代码非常复杂,很难处理,重新规划这样一个应用不但消耗时间, 也浪费金钱。
使用Docker,可以为每一个租户的应用层的多个实例创建隔离的环境,这不仅简单而且成本低廉,当然这一切得益于Docker环境的启动速度和其高效的diff命令。

4.8 快速部署 **

    在虚拟机之前,引入新的硬件资源需要消耗几天的时间。Docker的虚拟化技术将这个时间降到了几分钟,Docker只是创建一个容器进程而无需启动操作系统,这个过程只需要秒级的时间。这正是Google和Facebook都看重的特性。你可以在数据中心创建销毁资源而无需担心重新启动带来的开销。通常数据中心的资源利用率只有30%,通过使用Docker并进行有效的资源分配可以提高资源的利用率。

小结: 一句话说明docker的本质就是 低开销(系统文件、内存 共用)的虚拟机

五、Docker改变了什么?

面向产品:产品交付
面向开发:简化环境配置
面向测试:多版本测试
面向运维:环境一致
面向架构:自动化扩容(微服务)
Docker入门安装

5.1、环境

[root@linux-node1 ~]# cat /etc/redhat-release 
CentOS Linux release 7.4.1708 (Core) 
[root@linux-node1 ~]# uname -r
3.10.0-693.el7.x86_64

5.2、安装

准备说明
1、centos7 主机3台(推荐2C4g,最低1c1g)
2、关闭防火墙、SELINUX
3、做好主机名解析,即三台虚拟机能ping通彼此的主机名
hosts文件参考

10.0.0.106 linux-node1.example.com linux-node1
10.0.0.107 linux-node2.example.com linux-node2
10.0.0.108 linux-node3.example.com linux-node3

4、时间同步(很重要)

*/5 * * * * /usr/sbin/ntpdate 1.cn.pool.ntp.org  >/dev/null 2>&1

5,更新yum源,下载docker镜像

wget https://download.docker.com/linux/centos/docker-ce.repo -O /etc/yum.repos.d/docker-ce.repo
yum install docker-ce -y
yum install python-pip -y
pip install docker-compose

systemctl enable docker.service
systemctl start docker.service

docker pull centos
docker pull busybox
docker pull mysql
docker pull nginx
docker pull alpine
docker pull aclstack/mem
docker pull aclstack/cpu
docker pull progrium/consul
docker pull sebp/elk
docker pull fluent/fluentd

链接:https://pan.baidu.com/s/1eTwZHz8 密码:xg5x 下载安装包 上传至 node1 以及 node2 两台机器
Docker官网:http://www.docker.com/
最新版本我们可以去官方网站进行下载。

温馨提示:使用docker最好使用最新版,因为功能比较完善

5.3 启动docker

[root@linux-node1 ~]# systemctl start docker
启动之后我们可以查看一下docker的状态
root@node2 ~]# systemctl status docker
● docker.service - Docker Application Container Engine
   Loaded: loaded (/usr/lib/systemd/system/docker.service; enabled; vendor preset: disabled)
   Active: active (running) since 二 2018-01-23 21:45:05 CST; 5h 18min left
     Docs: https://docs.docker.com
 Main PID: 1151 (dockerd)
   CGroup: /system.slice/docker.service
           ├─1151 /usr/bin/dockerd
           ├─1236 docker-containerd --config /var/run/docker/containerd/containerd.toml
           ├─2061 docker-containerd-shim -namespace moby -workdir /var/lib/docker/containerd/daemon/io.containerd.runtime.v1.linux/moby/4af3e9997f8f29f91cb...
           └─2187 docker-containerd-shim -namespace moby -workdir /var/lib/docker/containerd/daemon/io.containerd.runtime.v1.linux/moby/9ba1a70b5765ed49e44...

1月 23 23:53:20 linux-node1.example.com dockerd[1151]: time="2018-01-23T23:53:20+08:00" level=info msg="shim docker-containerd-shim started" addre...pid=2420
1月 23 23:53:20 linux-node1.example.com dockerd[1151]: time="2018-01-23T23:53:20.740949762+08:00" level=warning msg="unknown container" container=...ins.moby
1月 23 23:53:20 linux-node1.example.com dockerd[1151]: time="2018-01-23T23:53:20.758216585+08:00" level=warning msg="unknown container" container=...ins.moby

5.4 添加tcp支持及socket

[root@linux-node1 ~]# cat /usr/lib/systemd/system/docker.service|grep ExecStart
ExecStart=/usr/bin/dockerd -H tcp://10.0.0.106 -H unix:///var/run/docker.sock
-开放端口-内网端口比较安全
-还要添加socket支持

5.4.1启动docker进程

systemctl daemon-reload
systemctl restart docker.service

5.5 查看网络 (注意是否存在docker0网卡)

[root@node2 ~]# ifconfig
docker0: flags=4163  mtu 1500
        inet 172.17.0.1  netmask 255.255.0.0  broadcast 172.17.255.255
        inet6 fe80::42:60ff:fe6f:9fff  prefixlen 64  scopeid 0x20
        ether 02:42:60:6f:9f:ff  txqueuelen 0  (Ethernet)
        RX packets 3472  bytes 142272 (138.9 KiB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 5444  bytes 12160631 (11.5 MiB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

ens33: flags=4163  mtu 1500
        inet 10.0.0.106  netmask 255.255.255.0  broadcast 10.0.0.255
        inet6 fe80::20c:29ff:feeb:19f5  prefixlen 64  scopeid 0x20
        ether 00:0c:29:eb:19:f5  txqueuelen 1000  (Ethernet)
        RX packets 20684  bytes 20823776 (19.8 MiB)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 10527  bytes 1276715 (1.2 MiB)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

lo: flags=73  mtu 65536
        inet 127.0.0.1  netmask 255.0.0.0
        inet6 ::1  prefixlen 128  scopeid 0x10
        loop  txqueuelen 1  (Local Loopback)
        RX packets 0  bytes 0 (0.0 B)
        RX errors 0  dropped 0  overruns 0  frame 0
        TX packets 0  bytes 0 (0.0 B)
        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0

提示: 我们启动docker的时候,docker会帮我们创建一个docker 0的网桥

六、Docker基础命令

6.1查看当前镜像

[root@linux-node1 ~]# docker images
REPOSITORY          TAG                 IMAGE ID            CREATED             SIZE
fluent/fluentd      latest              5174335bf8fc        5 days ago          35.6MB
busybox             latest              f9b6f7f7b9d3        7 days ago          1.14MB
mysql               latest              f008d8ff927d        7 days ago          409MB
alpine              latest              3fd9065eaf02        13 days ago         4.15MB
centos              latest              ff426288ea90        2 weeks ago         207MB
nginx               latest              3f8a4339aadd        3 weeks ago         108MB
sebp/elk            latest              b0dc4bffd033        4 weeks ago         1.07GB
aclstack/mem        latest              61eec139308f        4 months ago        21.9MB
progrium/consul     latest              09ea64205e55        2 years ago         69.4MB

6.2搜索镜像

执行docker search centos 会从dockerhub上搜索镜像

[root@linux-node1 ~]# docker  search centos 
##docker search [镜像名字] 

6.3 下载镜像

 我们可以使用docker pull centos / docker pull nginx来安装centos和nginx的镜像
导出镜像

docker save -o [镜像名称] [镜像]
[root@linux-node1 ~]# docker  save -o nginx.tar nginx 
[root@linux-node1 ~]# ls
10  anaconda-ks.cfg  nginx.tar
需要将docker导出为tar,后面为镜像名称,默认保存在当前路径

6.4 导入镜像

    [root@linux-node1 ~]# docker load < nginx.tar 

Docker-容器服务 Container Service01_第8张图片

6.5删除镜像

[root@linux-node1 ~]# docker rmi 3f8a4339aadd

Docker-容器服务 Container Service01_第9张图片
提示:如果镜像已经创建了一个容器,那么将无法进行删除

6.6 删除容器

1)正常删除镜像
[root@linux-node1 ~]# docker rm 4af3e9997f8f
2)强制删除(如果有容器在运行,并使用这个镜像)
[root@linux-node1 ~]# docker rm -f  4af3e9997f8f

6.7 运行容器

启动有2中方式:
docker run [镜像]
docker run [镜像] [命令参数]

            [root@linux-node1 ~]# docker run centos
    centos是镜像的名称,镜像的名称必须在选项的后面

启动镜像,输入Hello,并关闭

[root@linux-node1 ~]# docker run centos /bin/echo 'Hello Word'
Hello Word

6.8 查看启动镜像

ps是显示正在运行的容器 -a是显示不运行的 -q显示ID

[root@linux-node1 ~]# docker ps -a
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS                     PORTS               NAMES
0a64ea5e0666        centos              "/bin/bash"         4 seconds ago       Exited (0) 3 seconds ago                       vigorous_bhabha

 我们可以看到,现在容器并没有启动。因为docker启动需要在前台启动一个进程。容器的名称可以我们指定或自动生成

提示: 管理docker容器可以通过名称也可以通过ID
Docker-容器服务 Container Service01

6.9 docker默认端口(2379)需启动daemon模式

[root@linux-node1 ~]# netstat -lntup|grep dockerd
tcp        0      0 10.0.0.106:2375         0.0.0.0:*               LISTEN      3714/dockerd 

查看docker默认信息

[root@linux-node1 ~]# docker -H 10.0.0.106 info
Docker-容器服务 Container Service01_第10张图片

七、Docker登陆及nsente工具介绍

 例如:我要新建一个qiuyuetao的容器,它的镜像是centos.他有三个参数,第一个是给容器起一个名称,-t 分配一个伪终端(tty)-i标准输入打开,我要在里面输入命令

 [root@linux-node1 ~]# docker run -it --name qiuyuetao centos /bin/bash
[root@d89fb8a7957b /]# 现在已经等了到容器里呢
--name  容器的名称
-t       让docker分配一个伪终端
-i       让docker的标准输入打开{input}
##此时不能使用exit 退出,否则容器会退出,可以使用Ctrl+p+q快捷键进行退出

温馨提示:容器不是一个虚拟机,因为他就是一个进程,如果我们退出,这个进程就退出了,不能exit,使用Ctrl +p+q 组合键即可退出。
  如果我们执行创建容器的时候,里面没有我们指定的镜像,那么他会从dockerhub上进行下载然后在启动

7.1 exec 主要解决不进入docker,但能在docker中执行命令

    ##exec 也能进入docekr
    [root@linux-node1 ~]# docker exec -it d89fb8a7957b bash   ##容器ID

提示:生产场景是不使用docker attach的,需要我们使用nsenter这个工具,这个工具包含在util-linux软件包里面

yum install util-linux                      ##安装nsenter工具

通过docker inspect来获取到第一个进程的pid

[root@linux-node1 ~]# docker inspect -f "{{ .State.Pid }}" qiuyuetao
3996

7.2 使用nsenter工具连接容器

[root@linux-node1 ~]# nsenter -t 3996 -m -u -i -n -p
[root@d89fb8a7957b /]# 
[root@d89fb8a7957b /]# ps -aux
USER        PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
root          1  0.0  0.0  11776  1888 pts/0    Ss+  09:25   0:00 /bin/bash
root         15  0.0  0.0  15180  1900 ?        S    09:30   0:00 -bash
root         28  0.0  0.0  50852  1700 ?        R+   09:30   0:00 ps -aux

nsenter --target上面查到的进程id --mount --uts --ipc --net --pid #输入该命令便进入到容器中

解释nsenter指令中进程id之后的参数的含义:

* –mount参数是进去到mount namespace中 
* –uts参数是进入到uts namespace中 
* –ipc参数是进入到System V IPC namaspace中 
* –net参数是进入到network namespace中 
* –pid参数是进入到pid namespace中 
* –user参数是进入到user namespace中

保证容器中有多个进程存在,不会因为exit造成容器暂停

7.3 nsenter工具脚本登陆【自动化docker】

脚本内容如下:

[root@linux-node1 ~]# cat docker_in.sh

#!/bin/bash
# Use nsenter to access docker
docker_in(){
  NAME_ID=$1
  PID=$(docker inspect -f "{{ .State.Pid }}" $NAME_ID)
  nsenter -t $PID -m -u -i -n -p
}
docker_in $1

执行结果如下:

[root@linux-node1 ~]# chmod +x docker_nsenter.sh 
[root@linux-node1 ~]# ./docker_nsenter.sh qiuyuetao

[root@d89fb8a7957b /]# #使用脚本登陆到容器内

7.4 当然使用exec 也可以不进入容器去看

[root@linux-node1 ~]# docker exec -it d89fb8a7957b  ps aux
USER        PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
root          1  0.0  0.0  11776  1888 pts/0    Ss+  09:25   0:00 /bin/bash
root         73  0.0  0.0  47448  1664 pts/1    Rs+  09:41   0:00 ps aux

基础内容就先介绍到这,后续会在使用方面更深入的了解