Docker实现的两个基本理论知识

一、NameSpace:内核的实现技术,隔离机制。

●PID NameSpace:(隔离pid)每一个用户空间都有一个唯一的PID号,彼此之间不会干扰。从Linux2.6.24内核版本开始引入的,是一种最新的技术。

●Network NameSpace:真正起源于Linux2.6.29,实现与网络用户隔离的。(网络设备、网络线、端口资源隔离)

●User NameSpace:实现用户和用户组资源隔离的。Linux3.8

●IPC NameSpace: 进程间通信机制。多个用户之间的通信(信号量、消息队列和共享内存)也是隔离的。Linux 2.6.19

●UTC NameSpace: Linux 2.6.19 主机名和域名的隔离。

●Mount NameSpace: 实现挂载文件系统隔离的。Linux2.4.19


实现容器技术所需的API:

clone()克隆是实现线程的系统调用。

sents() 实现某个进程加入到某个NameSpace的。

unshare()非共享机制。进程脱离某个NameSpace。


二、CGroup: Linux Control Group  Linux2.6.24被收入到内核中去的。

内核级别,限制、控制与一个进程组群的资源;NameSpace实现上述6种隔离,CGroup实现在每个用户空间配配比资源。如每个用户空间之间的CPU个数,内存大小,以及硬件网络IO等


资源限制:CPU,内存,IO

功能:

      Resouce limitation:资源限制;

      Prioritization:优先级控制;

      Accounting:审计和统计,主要为计费;

      Control:挂起进程,恢复进程;


 yum install libcgroup-tools

lssbusys -m

[root@docker-vm ~]# lssubsys  -m
cpuset /sys/fs/cgroup/cpuset
cpu,cpuacct /sys/fs/cgroup/cpu,cpuacct
memory /sys/fs/cgroup/memory
devices /sys/fs/cgroup/devices
freezer /sys/fs/cgroup/freezer
net_cls /sys/fs/cgroup/net_cls
blkio /sys/fs/cgroup/blkio
perf_event /sys/fs/cgroup/perf_event
hugetlb /sys/fs/cgroup/hugetlb

CGroup的子系统(subsystem):

blkio:设定块设备的IO限制;(主要是磁盘)

cpu:     设定CPU的限制;

cpuacct: 报告cgroup中所使用的CPU资源;

cpuset:为cgroup中的任务分配CPU和内存资源;

memory:设定内存的使用限制;

device:控制cgroup中的任务对设备的访问;

freezer:挂起或恢复cgroup中的任务;

net_cls:(classid),使用等级级别标识符来标记网络数据包,以实现基于tc完成对不同的cgroup中产生的流量控制;

perf_event:使用后使cgroup中的任务可以进行统一的性能测试;

hugetlb:对HugeTLB系统进行限制;


CGroups中的术语:

task(任务):进程或线程

cgroup:一个独立的资源控制单位,可以包含一个或多个子系统;

subsystem:子系统

hierarchy:层级


三、AUFS: UnionFS 联合文件系统

       UnioFS:把不同的物理位置的目录合并到同一个目录中。实现机制是叠加。类似于winpe,LVM

       Another UFS.Alternative UFS,Adanced UFS (一个日本人写的)但是没有进入Linux内核中。

       Docker是基于AUFS上的,在生产环境中没有AUFS的Docker是不建议使用的。centos不支持AUFS.


Device mapper: 类似于AUFS

       Linux2.6内核引入的最重要的技术之一,用于在内核中支持逻辑卷管理的通用设备映射机制;

      Mapped Device

      Mapping Table

      Target Device

不建议在生产环境中应用。

四、Docker核心组件:

Docker:

2013,GO  Apache 2.0,dotCloud

基于C/S架构

Docker daemon

   Docker daemon是Docker最核心的后台进程,它负责响应来自Docker clinet的请求,然后将这些请求翻译成系统调用完成容器管理的操作。

DockerClinet

   Docker clinet是一个返泛称,用来向指定的Docker daemon发起请求,执行相应的容器管理操作。

Graph

   graph组件负责维护已下载的镜像信息及他们之前的关系。

GraphDB

   Docker daemon通过GraphDB记录它维护的所有容器(节点)以及它们之间的link关系(边),这也就是为什么这里采用了一个图结构来保存这些数据。

Driver

Docker daemon负责将用户请求转译成系统调用,进而创建和管理容器的核心进程。而在具体事项过程中,为了将这些系统调用抽象成容器管理驱动、网络管理驱动、文件存储驱动3种,分别对应为execdriver、networkdriver和graphdriver

centos6.5还是使用的是lxc:linux containers,

centos7已经全部替换成了libcontainer

几个核心组件概念:

p_w_picpath:镜像文件是只读的,用来创建container,一个镜像可以运行多个container;镜像文件可以通过Dockfile文件创建,也可以从docker hub/registry下载

repository

公共仓库:Docker hub/registry

私有仓库:docker registry

docker contanier:docker的运行实例。容器是一个隔离环境;

另外两个组件:

docker link:        容器网络等。

docker volume:  容器实现数据持久机制。


五、docker安装

本文直接使用centos7来安装

Docker 软件包已经包括在默认的 CentOS-Extras 软件源里。因此想要安装 docker,只需要运行下面的 yum 命令:

[root@localhost ~]# yum install docker

启动 Docker 服务

[root@localhost ~]# systemctl start docker.service
[root@localhost ~]# systemctl enable docker.service

docker search:查找docker centos官方镜像。

[root@docker-vm ~]# docker search centos
INDEX       NAME                                             DESCRIPTION                                     STARS     OFFICIAL   AUTOMATED
docker.io   docker.io/centos                                 The official build of CentOS.                   2777      [OK]
docker.io   docker.io/ansible/centos7-ansible                Ansible on Centos7                              90                   [OK]
docker.io   docker.io/jdeathe/centos-ssh                     CentOS-6 6.8 x86_64 / CentOS-7 7.2.1511 x8...   43                   [OK]
docker.io   docker.io/jdeathe/centos-ssh-apache-php          CentOS-6 6.8 x86_64 - Apache / PHP / PHP M...   22                   [OK]
docker.io   docker.io/nimmis/java-centos                     This is docker p_w_picpaths of CentOS 7 with dif...   17                   [OK]
docker.io   docker.io/consol/centos-xfce-vnc                 Centos container with "headless" VNC sessi...   14                   [OK]
docker.io   docker.io/gluster/gluster-centos                 Official GlusterFS Image [ CentOS7 +  Glus...   13                   [OK]
docker.io   docker.io/million12/centos-supervisor            Base CentOS-7 with supervisord launcher, h...   12                   [OK]
docker.io   docker.io/nickistre/centos-lamp                  LAMP on centos setup                            8                    [OK]
docker.io   docker.io/torusware/speedus-centos               Always updated official CentOS docker imag...   8                    [OK]
docker.io   docker.io/kinogmt/centos-ssh                     CentOS with SSH                                 6                    [OK]
docker.io   docker.io/egyptianbman/docker-centos-nginx-php   A simple and highly configurable docker co...   5                    [OK]
docker.io   docker.io/nathonfowlie/centos-jre                Latest CentOS p_w_picpath with the JRE pre-insta...   4                    [OK]
docker.io   docker.io/centos/mariadb55-centos7                                                               3                    [OK]
docker.io   docker.io/centos/tools                           Docker p_w_picpath that has systems administrati...   3                    [OK]
docker.io   docker.io/consol/sakuli-centos-xfce              Sakuli JavaScript based end-2-end testing ...   2                    [OK]
docker.io   docker.io/blacklabelops/centos                   CentOS Base Image! Built and Updates Daily!     1                    [OK]
docker.io   docker.io/darksheer/centos                       Base Centos Image -- Updated hourly             1                    [OK]
docker.io   docker.io/harisekhon/centos-java                 Java on CentOS (OpenJDK, tags jre/jdk7-8)       1                    [OK]
docker.io   docker.io/harisekhon/centos-scala                Scala + CentOS (OpenJDK tags 2.10-jre7 - 2...   1                    [OK]
docker.io   docker.io/timhughes/centos                       Centos with systemd installed and running       1                    [OK]
docker.io   docker.io/januswel/centos                        yum update-ed CentOS p_w_picpath                      0                    [OK]
docker.io   docker.io/repositoryjp/centos                    Docker Image for CentOS.                        0                    [OK]
docker.io   docker.io/smartentry/centos                      centos with smartentry                          0                    [OK]
docker.io   docker.io/ustclug/centos                          USTC centos                                    0                    [OK]

douker pull 拉取镜像文件到本地

下载一个busybox镜像到本地,默认版本是latest

[root@docker-vm ~]# docker pull busybox
Using default tag: latest
Trying to pull repository docker.io/library/busybox ...
latest: Pulling from docker.io/library/busybox
56bec22e3559: Pull complete
Digest: sha256:29f5d56d12684887bdfa50dcd29fc31eea4aaf4ad3bec43daf19026a7ce69912
Status: Downloaded newer p_w_picpath for docker.io/busybox:latest

下载一个centos镜像到本地,默认版本是latest

[root@docker-vm ~]# docker pull centos
Using default tag: latest
Trying to pull repository docker.io/library/centos ...
latest: Pulling from docker.io/library/centos
8d30e94188e7: Pull complete
Digest: sha256:2ae0d2c881c7123870114fb9cc7afabd1e31f9888dac8286884f6cf59373ed9b
Status: Downloaded newer p_w_picpath for docker.io/centos:latest

docker p_w_picpaths:列出本地镜像

[root@docker-vm ~]# docker p_w_picpaths
REPOSITORY          TAG                 IMAGE ID            CREATED             SIZE
docker.io/busybox   latest              e02e811dd08f        3 weeks ago         1.093 MB
docker.io/centos    latest              980e0e4c79ec        7 weeks ago         196.7 MB

docker run:运行一个容器在交互模式下

[root@docker-vm ~]# docker run -it busybox:latest /bin/sh
/ # ls
bin   dev   etc   home  proc  root  run   sys   tmp   usr   var
/ #

docker run:运行一个hello world程序,可以看到运行完成后,容器就终止了。应用结束了,容器就结束了。使命就完成了。

[root@docker-vm ~]# docker run busybox:latest /bin/echo "hello world"
hello world
[root@docker-vm ~]# docker ps
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS              PORTS               NAMES
[root@docker-vm ~]# docker ps -a
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS                      PORTS               NAMES
7b6f1bb9540c        busybox:latest      "/bin/echo 'hello wor"   21 seconds ago      Exited (0) 20 seconds ago                       trusting_swanson

run其他参数用法

docker run --name 给容器启用一个名字

                  -i,--interactive=false Keep STDIN open even if not attached 启动交互式模式

                  -t, tty=false  启动一个伪终端

                 -d --detach=false 以守护进程后台运行程序

  例子:启动一个名字叫做busybox,镜像为busybox:latest的终端

[root@docker-vm ~]# docker run -it --name=busybox busybox:latest /bin/sh
/ #

例子停止容器:

[root@docker-vm ~]# docker stop busybox
busybox
root@docker-vm ~]# docker ps -a
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS                        PORTS               NAMES
73f8bba68272        busybox:latest      "/bin/sh"           3 minutes ago       Exited (137) 28 seconds ago                       busybox

 启动容器,并进入一个启动的容器中

attach:关联和附加至一个运行中的容器

[root@docker-vm ~]# docker start 73f8bba68272
73f8bba68272
[root@docker-vm ~]# docker attach 73f8bba68272 或者用
[root@docker-vm ~]# docker start -i 73f8bba68272 
/ # ifconfig
eth0      Link encap:Ethernet  HWaddr 02:42:AC:11:00:02
          inet addr:172.17.0.2  Bcast:0.0.0.0  Mask:255.255.0.0
          inet6 addr: fe80::42:acff:fe11:2/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          RX packets:8 errors:0 dropped:0 overruns:0 frame:0
          TX packets:8 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:0
          RX bytes:648 (648.0 B)  TX bytes:648 (648.0 B)
lo        Link encap:Local Loopback
          inet addr:127.0.0.1  Mask:255.0.0.0
          inet6 addr: ::1/128 Scope:Host
          UP LOOPBACK RUNNING  MTU:65536  Metric:1
          RX packets:0 errors:0 dropped:0 overruns:0 frame:0
          TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:0
          RX bytes:0 (0.0 B)  TX bytes:0 (0.0 B)

            

总结run使用过程:

1、检查本地是否存在指定的镜像,不存在则从registry下载;

2、利用镜像启动容器

3、分配一个文件系统,并且在只读的镜像层之外挂载一个可读写层;

4、从宿主机配置的网络接口桥接一个虚拟接口

5、从地址池中分配一个地址给容器;

6、执行用户指定的应用程序;

7、程序执行完成后,容器即终止;

对于交互式模式启动的容器,终止可使用exit命令或者crtl+d

logs命令:获取一个容器的日志,获取其输出信息;

[root@docker-vm ~]# docker logs 73f8bba68272
/ # ifconfig
eth0      Link encap:Ethernet  HWaddr 02:42:AC:11:00:02
          inet addr:172.17.0.2  Bcast:0.0.0.0  Mask:255.255.0.0
          inet6 addr: fe80::42:acff:fe11:2/64 Scope:Link
          UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1
          RX packets:8 errors:0 dropped:0 overruns:0 frame:0
          TX packets:8 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:0
          RX bytes:648 (648.0 B)  TX bytes:648 (648.0 B)
lo        Link encap:Local Loopback
          inet addr:127.0.0.1  Mask:255.0.0.0
          inet6 addr: ::1/128 Scope:Host
          UP LOOPBACK RUNNING  MTU:65536  Metric:1
          RX packets:0 errors:0 dropped:0 overruns:0 frame:0
          TX packets:0 errors:0 dropped:0 overruns:0 carrier:0
          collisions:0 txqueuelen:0
          RX bytes:0 (0.0 B)  TX bytes:0 (0.0 B)
/ # ps
PID   USER     TIME   COMMAND
    1 root       0:00 /bin/sh
    7 root       0:00 ps


docker ps:列出当前宿主机中运行的容器

[root@docker-vm ~]# docker ps
CONTAINER ID        IMAGE               COMMAND             CREATED              STATUS              PORTS               NAMES
731525df2a5d        busybox:latest      "/bin/sh"           About a minute ago   Up About a minute                       goofy_mcclintock

docker 常用命令:

环境相关info,version

[root@docker-vm ~]# docker info
Containers: 1
 Running: 0
 Paused: 0
 Stopped: 1
Images: 1
Server Version: 1.10.3               #docker版本号
Storage Driver: devicemapper               
 Pool Name: docker-253:0-135130169-pool
 Pool Blocksize: 65.54 kB
 Base Device Size: 10.74 GB
 Backing Filesystem: xfs
 Data file: /dev/loop0
 Metadata file: /dev/loop1
 Data Space Used: 22.48 MB
 Data Space Total: 107.4 GB
 Data Space Available: 52.49 GB
 Metadata Space Used: 593.9 kB
 Metadata Space Total: 2.147 GB
 Metadata Space Available: 2.147 GB
 Udev Sync Supported: true
 Deferred Removal Enabled: false
 Deferred Deletion Enabled: false
 Deferred Deleted Device Count: 0
 Data loop file: /var/lib/docker/devicemapper/devicemapper/data
 WARNING: Usage of loopback devices is strongly discouraged for production use. Either use `--storage-opt dm.thinpooldev` or use `--storage-opt dm.no_warn_on_loop_devices=true` to suppress this warning.
 Metadata loop file: /var/lib/docker/devicemapper/devicemapper/metadata
 Library Version: 1.02.107-RHEL7 (2015-10-14)
Execution Driver: native-0.2
Logging Driver: journald
Plugins:
 Volume: local
 Network: null host bridge
Kernel Version: 3.10.0-327.el7.x86_64    #kernel版本信息
Operating System: CentOS Linux 7 (Core)
OSType: linux
Architecture: x86_64
Number of Docker Hooks: 2
CPUs: 24                       #cpu核心数
Total Memory: 125.7 GiB        #主机内存大小
Name: docker-vm
ID: Z4Q6:MROS:ES5N:SYVJ:HOKQ:BOMI:DXRZ:PX7L:AMF4:OMO4:3YMC:TBLC
WARNING: bridge-nf-call-iptables is disabled
WARNING: bridge-nf-call-ip6tables is disabled
Registries: docker.io (secure)

docker version列出版本相关信息

[root@docker-vm ~]# docker version
Client:
 Version:         1.10.3
 API version:     1.22
 Package version: docker-common-1.10.3-46.el7.centos.14.x86_64
 Go version:      go1.6.3
 Git commit:      cb079f6-unsupported
 Built:           Fri Sep 16 13:24:25 2016
 OS/Arch:         linux/amd64
Server:
 Version:         1.10.3
 API version:     1.22
 Package version: docker-common-1.10.3-46.el7.centos.14.x86_64
 Go version:      go1.6.3
 Git commit:      cb079f6-unsupported
 Built:           Fri Sep 16 13:24:25 2016
 OS/Arch:         linux/amd64

系统维护相关:p_w_picpaths,inspect,bulid,commit,pause/unpause,ps,rm,rmi,run,start/stop/restart,top,kill

日志信息相关:event,history,logs

Docker hub服务相关:login,logout,pull,push.search

例子:docker kill 一个容器

[root@docker-vm ~]# docker ps
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS              PORTS               NAMES
cfe1c1f31d40        centos:latest       "/bin/bash"         3 minutes ago       Up 3 minutes                            admiring_almeida
[root@docker-vm ~]# docker kill  cfe1c1f31d40
cfe1c1f31d40
[root@docker-vm ~]# docker ps
CONTAINER ID        IMAGE

例子:docker ps -a 列出所有镜像文件,包括已退出的镜像

root@docker-vm ~]# docker ps -a
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS                       PORTS               NAMES
cfe1c1f31d40        centos:latest       "/bin/bash"         9 minutes ago       Exited (137) 6 minutes ago                       admiring_almeida
731525df2a5d        busybox:latest      "/bin/sh"           23 minutes ago      Exited (0) 31 minutes ago                        goofy_mcclintock

docker run --rm 当容器退出时自动删除此容器

[root@docker-vm ~]# docker ps -a
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS                       PORTS               NAMES
cfe1c1f31d40        centos:latest       "/bin/bash"         9 minutes ago       Exited (137) 6 minutes ago                       admiring_almeida
731525df2a5d        busybox:latest      "/bin/sh"           23 minutes ago      Exited (0) 31 minutes ago                        goofy_mcclintock
[root@docker-vm ~]# docker rm 731525df2a5d
731525df2a5d
[root@docker-vm ~]# docker ps -a
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS                       PORTS               NAMES
cfe1c1f31d40        centos:latest       "/bin/bash"         13 minutes ago      Exited (137) 9 minutes ago                       admiring_almeida

docker commit创建一个修改后的容器镜像。创建一个用户

[root@docker-vm ~]# docker run -it centos:latest /bin/bash
[root@7cef59f68ead /]# useradd bjia
[root@7cef59f68ead /]# id bjia
uid=1000(bjia) gid=1000(bjia) groups=1000(bjia)
[root@docker-vm ~]# docker ps     #查看这个镜像的ID
CONTAINER ID        IMAGE               COMMAND             CREATED             STATUS              PORTS               NAMES
7cef59f68ead        centos:latest       "/bin/bash"         9 minutes ago       Up 8 minutes                            grave_pike
[root@docker-vm ~]# docker commit  7cef59f68ead centos:newuser  #创建一个名叫centos:newuser的容器镜像。
sha256:8c65e1448eb970ee1173a4b2f67ac31164ac94109e8b3ba1c2cef2addc4188fb
[root@docker-vm ~]# docker p_w_picpaths   #查看后已经创建了新的newuser的镜像。
REPOSITORY          TAG                 IMAGE ID            CREATED             SIZE
centos              newuser             8c65e1448eb9        9 seconds ago       196.7 MB
docker.io/busybox   latest              e02e811dd08f        3 weeks ago         1.093 MB
docker.io/centos    latest              980e0e4c79ec        7 weeks ago         196.7 MB

停止和删除之前的centos容器

[root@docker-vm ~]# docker kill 7cef59f68ead
7cef59f68ead
[root@docker-vm ~]# docker rm 7cef59f68ead

创建一个刚刚建立id=bjia的centos容器。可以看到bjia这个用户存在的。这就是commit的作用

[root@docker-vm ~]# docker run -it --rm centos:newuser /bin/bash
[root@4bf44b9af9dc /]# id bjia
uid=1000(bjia) gid=1000(bjia) groups=1000(bjia)


六、docker私有仓库

在另外一台机器上安装docker-registry

[root@node2 ~]# yum -y install docker-registry
#启动服务
[root@node2 ~]# systemctl start docker-registry.service
默认监听在5000端口上。
State      Recv-Q Send-Q                                                                                          Local Address:Port                                                                                                         Peer Address:Port
LISTEN     0      128                                                                                                         *:5000                                                                                                                    *:*
LISTEN     0      128

对一个本地的镜像打一个TAG,名字叫busybox:1.2.1

[root@node1 ~]# docker p_w_picpaths;
REPOSITORY           TAG                 IMAGE ID            CREATED             SIZE
docker.io/registry   latest              c9bd19d022f6        2 weeks ago         33.27 MB
docker.io/busybox    latest              e02e811dd08f        4 weeks ago         1.093 MB
[root@node1 ~]# docker tag e02e811dd08f 192.168.254.17:5000/busybox:1.2.1

push一个镜像到私有仓库,直接push会报错,如下:

[root@node1 ~]# docker push 192.168.254.17:5000/busybox:1.2.1
The push refers to a repository [192.168.254.17:5000/busybox]
unable to ping registry endpoint https://192.168.254.17:5000/v0/
v2 ping attempt failed with error: Get https://192.168.254.17:5000/v2/: dial tcp 192.168.254.17:5000: getsockopt: no route to host
 v1 ping attempt failed with error: Get https://192.168.254.17:5000/v1/_ping: dial tcp 192.168.254.17:5000: getsockopt: no route to host

因为默认使用https协议进行连接。如果不想用https访问可以如下修改

vim /etc/sysconfig/docker
ADD_REGISTRY='--add-registry 192.168.254.17:5000'  #添加一个仓库IP地址和端口
INSECURE_REGISTRY='--insecure-registry 192.168.254.17:5000' #启用非安全方式连接
[root@node1 ~]# systemctl restart docker  #重启服务生