Docker概述

Docker 是一个开源的应用容器引擎,让开发者可以打包他们的应用以及依赖包到一个可移植的容器中,然后发布到任何流行的Linux机器或Windows 机器上,也可以实现虚拟化,容器是完全使用沙箱机制,相互之间不会有任何接口。

Docker为什么出现

一款产品:开发–上线 两套环境,配置环境非常麻烦。

传统:开发jar,运维部署上线

现在:开发打包部署上线,一套流程做完!

Docker的思想来自集装箱:打包隔离,每个箱子是相互隔离的!

Docker的历史

2010年,几个年轻人,在美国成立了一家公司dotCloud,做一些 pass 的云计算服务,LXC有关的容器技术。

2013年,Docker开源,于是越来越多的人发现它的优点!

2014年4月9日,Docker1.0发布!

Docker能干嘛?

虚拟化技术

虚拟化技术结构图

虚拟机技术缺点:

1、资源占用多

2、冗余步骤多

3、启动慢

容器化技术

容器化技术结构图

比较Docker和虚拟机技术的不同:

  • 传统虚拟机虚拟处一个硬件,运行一个完整的操作系统,在系统上安装和运行软件
  • 容器内的应用直接运行在宿主主机的内容,容器是没有自己的内核的,也没有虚拟出硬件,所以就轻便了
  • 每个容器间是相互隔离,每个容器内都有一个属于自己的文件系统,互不影响

DevOps(开发、运维)

应用更快速的交付和部署

传统:一堆帮助文档、安装程序

Docker:打包镜像发布测试,一键运行

更便捷的升级和扩缩容

更简单的系统运维

更高效的计算资源利用

Docker的安装

Docker基本组成

image-20200723210803208

  • 镜像(image):一个模板,可以通过模板来创建容器服务,Tomcat镜像===>run===>Tomcat01容器(提供服务),通过这个镜像可以创建多个容器(最终项目运行在容器中)

  • 容器(container):利用容器技术,独立运行一个或一组应用,通过镜像来创建。

    启动、停止、删除、基本命令!

  • 仓库(repository):仓库就是存放镜像的地方!仓库分为公有和私有!

安装Docker

环境准备

  1. 一点linux基础
  2. centos7
  3. Xshell远程连接

环境查看

1
2
3
#系统内核是3.10以上
[root@localhost /]# uname -r
3.10.0-862.14.4.el7.x86_64
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#系统版本
[root@localhost /]# cat /etc/os-release
NAME="CentOS Linux"
VERSION="7 (Core)"
ID="centos"
ID_LIKE="rhel fedora"
VERSION_ID="7"
PRETTY_NAME="CentOS Linux 7 (Core)"
ANSI_COLOR="0;31"
CPE_NAME="cpe:/o:centos:centos:7"
HOME_URL="https://www.centos.org/"
BUG_REPORT_URL="https://bugs.centos.org/"

CENTOS_MANTISBT_PROJECT="CentOS-7"
CENTOS_MANTISBT_PROJECT_VERSION="7"
REDHAT_SUPPORT_PRODUCT="centos"
REDHAT_SUPPORT_PRODUCT_VERSION="7"

安装

帮助文档:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
#1、卸载旧版本
yum remove docker \
docker-client \
docker-client-latest \
docker-common \
docker-latest \
docker-latest-logrotate \
docker-logrotate \
docker-engine

#2、需要的安装包
yum install -y yum-utils

#3、设置镜像的仓库
yum-config-manager \
--add-repo \
https://download.docker.com/linux/centos/docker-ce.repo #(国外地址,速度慢)

yum-config-manager \
--add-repo \
https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo

#更新yum软件包索引
yum makecache fast

#4、安装docker
yum install docker-ce docker-ce-cli containerd.io

#5、启动docker
systemctl start docker

#6、判断是否安装成功
docker version

#7、hello-world
docker run hello-world

#8、查看hello-world镜像
docker images

了解:卸载docker

1
2
3
4
5
6
7
#1、卸载依赖
yum remove docker-ce docker-ce-cli containerd.io

#2、删除资源
rm -rf /var/lib/docker

#/var/lib/docker (docker的默认工作路径)

阿里云镜像加速

image-20200723222951013

配置文件:

1
2
3
4
5
6
7
8
9
10
11
sudo mkdir -p /etc/docker

sudo tee /etc/docker/daemon.json <<-'EOF'
{
"registry-mirrors": ["https://cn12gl5r.mirror.aliyuncs.com"]
}
EOF

sudo systemctl daemon-reload

sudo systemctl restart docker

hello-world的流程

image-20200723222951013

底层原理

Docker是怎么工作的?、

Docker是一个client-Server结构的系统,Docker的守护进程运行在主机上,通过Socket从客户端访问!

DockerServer接收到DockerClient的指令,就会执行这个命令。

image-20200723224028879

Docker为什么比vm块

  1. Docker有比虚拟机更少的抽象层
  2. Docker利用的是宿主主机的内核,vm需要Guest-OS

image-20200723225148222

所以,新建一个容器的时候,Docker不需要像虚拟机一样重新加载操作系统内核,避免引导,虚拟机是加载GuestOS,

Docker的常用命令

帮助命令

1
2
3
docker version      #显示docker的版本信息
docker info #显示docker的系统信息,包括镜像和容器的数量
docker 命令 --help #帮助命令

帮助文档地址:https://docs.docker.com/reference/

镜像命令

docker images 查看所有本地主机的镜像

1
2
3
4
5
6
7
8
[root@localhost ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
hello-world latest bf756fb1ae65 6 months ago 13.3kB
#仓库源 标签 id 创建时间 大小

#可选项
-a, --all #列出所有镜像
-q, --quiet #只显示镜像的id

docker search 搜索镜像

1
2
3
4
5
6
7
[root@localhost ~]# docker search mysql
NAME DESCRIPTION STARS OFFICIAL AUTOMATED
mysql MySQL is a widely used, open-source relation… 9760 [OK]
mariadb MariaDB is a community-developed fork of MyS… 3564 [OK]
#可选项,通过搜索过滤
--filter=STARS=3000 #过滤STARS=3000以上的

docker pull 下载镜像

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
#docker pull mysql [:tag]
[root@localhost ~]# docker pull mysql
Using default tag: latest #如果不写,默认latest
latest: Pulling from library/mysql
6ec8c9369e08: Pull complete #分层下载,docker image的核心,联合文件系统
177e5de89054: Pull complete
ab6ccb86eb40: Pull complete
e1ee78841235: Pull complete
09cd86ccee56: Pull complete
78bea0594a44: Pull complete
caf5f529ae89: Pull complete
cf0fc09f046d: Pull complete
4ccd5b05a8f6: Pull complete
76d29d8de5d4: Pull complete
8077a91f5d16: Pull complete
922753e827ec: Pull complete
Digest: sha256:fb6a6a26111ba75f9e8487db639bc5721d4431beba4cd668a4e922b8f8b14acc
Status: Downloaded newer image for mysql:latest
docker.io/library/mysql:latest

docker rmi 删除镜像

1
2
3
[root@localhost ~]# docker rmi -f 8679ced16d20  #删除指定的镜像
[root@localhost ~]# docker rmi -f id1 id2 id3 id4 #批量删除镜像
[root@localhost ~]# docker rmi -f $(docker images -aq) #删除全部镜像

容器命令

说明:有了镜像才可以创建爱你容器,下载一个centos测试学习

1
docker pull centos

新建容器并启动

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
docker run [可选参数] image

#参数说明
--name="Name" 容器名字 ,用于区分容器
-d 后台方式运行
-it 使用交互方式运行,进入容器查看内容
-p 指定容器的端口
-p ip:主机端口:容器端口
-p 主机端口:容器端口
-p 容器端口
容器端口
-P 随机指定端口

#测试、启动并进入容器
[root@localhost ~]# docker run -it centos /bin/bash
[root@0d7b4443e40f /]# ls
bin dev etc home lib lib64 lost+found media mnt opt proc root run sbin srv sys tmp usr var

#从容器返回主机
[root@0d7b4443e40f /]# exit
exit
[root@localhost /]# ls
bin boot dev etc home lib lib64 media mnt opt proc root run sbin srv sys tmp usr var

列出所有运行的容器

1
2
3
4
5
6
7
8
9
10
11
#docker ps
#列出当前正在运行的容器
-a #列出所有容器,包括运行和停止的
-n=? #显示最近创建的容器
-q #只显示容器编号
[root@localhost /]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
[root@localhost /]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
0d7b4443e40f centos "/bin/bash" 3 minutes ago Exited (0) 3 minutes ago funny_brown
488f714c3556 bf756fb1ae65 "/hello" 3 days ago Exited (0) 3 days ago boring_antonelli

退出容器

1
2
exit    #直接停止容器并退出
Ctrl + P + Q #容器不停止直接退出

删除容器

1
2
3
docker rm  容器id               #删除指定的容器,不能删除正在运行的容器
docker rm -f $(docker ps -aq) #删除所有容器
docker ps -a -qixargs docker rm #删除所有容器

启动和停止容器的操作

1
2
3
4
docker start  容器id     #启动容器
docker restart 容器id #重启容器
docker stop 容器id #停止当前正在运行的容器
docker kill 容器id #强制停止当前容器

常用其他命令

后台启动容器

1
2
3
4
5
#命令 docker run -d 镜像名
[root@localhost /]# docker run -d centos

#问题:docker ps ,发现centos停止了
#docker 容器使用后台运行,就必须有一个前台进程,docker发现没有前台应用,就会停止

查看日志

1
2
3
4
5
6
7
8
9
docker logs -f -t --tail 数量 容器id

#自己写一点shell脚本
[root@localhost /]# docker run -d centos /bin/sh -c "while true;do echo sen;sleep 1;done"

#显示日志
-tf #显示日志
--tail number #要显示日志条数
[root@localhost /]# docker logs -tf --tail 10 5b6

查看容器中进程信息

1
2
3
4
5
#docker top 容器id
[root@localhost /]# docker top 5b6
UID PID PPID C STIME
root 5028 5011 0 23:34
root 5414 5028 0 23:39

查看镜像的元数据

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
#docker inspect 容器id

[root@localhost /]# docker inspect 5b6
[
{
"Id": "5b6bb141ff8dbd7b2d4b23179cf776cd8655869ddce3a66718ff4f48dbf04a48",
"Created": "2020-07-26T15:34:32.646214144Z",
"Path": "/bin/sh",
"Args": [
"-c",
"while true;do echo sen;sleep 1;done"
],
"State": {
"Status": "running",
"Running": true,
"Paused": false,
"Restarting": false,
"OOMKilled": false,
"Dead": false,
"Pid": 5028,
"ExitCode": 0,
"Error": "",
"StartedAt": "2020-07-26T15:34:34.106610567Z",
"FinishedAt": "0001-01-01T00:00:00Z"
},
"Image": "sha256:831691599b88ad6cc2a4abbd0e89661a121aff14cfa289ad840fd3946f274f1f",
"ResolvConfPath": "/var/lib/docker/containers/5b6bb141ff8dbd7b2d4b23179cf776cd8655869ddce3a66718ff4f48dbf04a48/resolv.conf",
"HostnamePath": "/var/lib/docker/containers/5b6bb141ff8dbd7b2d4b23179cf776cd8655869ddce3a66718ff4f48dbf04a48/hostname",
"HostsPath": "/var/lib/docker/containers/5b6bb141ff8dbd7b2d4b23179cf776cd8655869ddce3a66718ff4f48dbf04a48/hosts",
"LogPath": "/var/lib/docker/containers/5b6bb141ff8dbd7b2d4b23179cf776cd8655869ddce3a66718ff4f48dbf04a48/5b6bb141ff8dbd7b2d4b23179cf776cd8655869ddce3a66718ff4f48dbf04a48-json.log",
"Name": "/hardcore_wu",
"RestartCount": 0,
"Driver": "overlay2",
"Platform": "linux",
"MountLabel": "",
"ProcessLabel": "",
"AppArmorProfile": "",
"ExecIDs": null,
"HostConfig": {
"Binds": null,
"ContainerIDFile": "",
"LogConfig": {
"Type": "json-file",
"Config": {}
},
"NetworkMode": "default",
"PortBindings": {},
"RestartPolicy": {
"Name": "no",
"MaximumRetryCount": 0
},
"AutoRemove": false,
"VolumeDriver": "",
"VolumesFrom": null,
"CapAdd": null,
"CapDrop": null,
"Capabilities": null,
"Dns": [],
"DnsOptions": [],
"DnsSearch": [],
"ExtraHosts": null,
"GroupAdd": null,
"IpcMode": "private",
"Cgroup": "",
"Links": null,
"OomScoreAdj": 0,
"PidMode": "",
"Privileged": false,
"PublishAllPorts": false,
"ReadonlyRootfs": false,
"SecurityOpt": null,
"UTSMode": "",
"UsernsMode": "",
"ShmSize": 67108864,
"Runtime": "runc",
"ConsoleSize": [
0,
0
],
"Isolation": "",
"CpuShares": 0,
"Memory": 0,
"NanoCpus": 0,
"CgroupParent": "",
"BlkioWeight": 0,
"BlkioWeightDevice": [],
"BlkioDeviceReadBps": null,
"BlkioDeviceWriteBps": null,
"BlkioDeviceReadIOps": null,
"BlkioDeviceWriteIOps": null,
"CpuPeriod": 0,
"CpuQuota": 0,
"CpuRealtimePeriod": 0,
"CpuRealtimeRuntime": 0,
"CpusetCpus": "",
"CpusetMems": "",
"Devices": [],
"DeviceCgroupRules": null,
"DeviceRequests": null,
"KernelMemory": 0,
"KernelMemoryTCP": 0,
"MemoryReservation": 0,
"MemorySwap": 0,
"MemorySwappiness": null,
"OomKillDisable": false,
"PidsLimit": null,
"Ulimits": null,
"CpuCount": 0,
"CpuPercent": 0,
"IOMaximumIOps": 0,
"IOMaximumBandwidth": 0,
"MaskedPaths": [
"/proc/asound",
"/proc/acpi",
"/proc/kcore",
"/proc/keys",
"/proc/latency_stats",
"/proc/timer_list",
"/proc/timer_stats",
"/proc/sched_debug",
"/proc/scsi",
"/sys/firmware"
],
"ReadonlyPaths": [
"/proc/bus",
"/proc/fs",
"/proc/irq",
"/proc/sys",
"/proc/sysrq-trigger"
]
},
"GraphDriver": {
"Data": {
"LowerDir": "/var/lib/docker/overlay2/c843700f0413b2c16dd5b8ef5b92c198a93ae988f16bd76893987a478fc2fcd8-init/diff:/var/lib/docker/overlay2/d19e4335d150c3ac104d757d8a08c503acd7a9785c0312184fd0a6c40ad20c0d/diff",
"MergedDir": "/var/lib/docker/overlay2/c843700f0413b2c16dd5b8ef5b92c198a93ae988f16bd76893987a478fc2fcd8/merged",
"UpperDir": "/var/lib/docker/overlay2/c843700f0413b2c16dd5b8ef5b92c198a93ae988f16bd76893987a478fc2fcd8/diff",
"WorkDir": "/var/lib/docker/overlay2/c843700f0413b2c16dd5b8ef5b92c198a93ae988f16bd76893987a478fc2fcd8/work"
},
"Name": "overlay2"
},
"Mounts": [],
"Config": {
"Hostname": "5b6bb141ff8d",
"Domainname": "",
"User": "",
"AttachStdin": false,
"AttachStdout": false,
"AttachStderr": false,
"Tty": false,
"OpenStdin": false,
"StdinOnce": false,
"Env": [
"PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
],
"Cmd": [
"/bin/sh",
"-c",
"while true;do echo sen;sleep 1;done"
],
"Image": "centos",
"Volumes": null,
"WorkingDir": "",
"Entrypoint": null,
"OnBuild": null,
"Labels": {
"org.label-schema.build-date": "20200611",
"org.label-schema.license": "GPLv2",
"org.label-schema.name": "CentOS Base Image",
"org.label-schema.schema-version": "1.0",
"org.label-schema.vendor": "CentOS"
}
},
"NetworkSettings": {
"Bridge": "",
"SandboxID": "7235922c0b4e7cdb5882da90036c0549af0996234d1d071ae5d877059642dcc5",
"HairpinMode": false,
"LinkLocalIPv6Address": "",
"LinkLocalIPv6PrefixLen": 0,
"Ports": {},
"SandboxKey": "/var/run/docker/netns/7235922c0b4e",
"SecondaryIPAddresses": null,
"SecondaryIPv6Addresses": null,
"EndpointID": "f0bbfc96cd4bea48f9168cb2aa3fc5e47f788711579116c633245d7f9e8c69f8",
"Gateway": "172.17.0.1",
"GlobalIPv6Address": "",
"GlobalIPv6PrefixLen": 0,
"IPAddress": "172.17.0.2",
"IPPrefixLen": 16,
"IPv6Gateway": "",
"MacAddress": "02:42:ac:11:00:02",
"Networks": {
"bridge": {
"IPAMConfig": null,
"Links": null,
"Aliases": null,
"NetworkID": "b1a5cb7bce7dabc316af738756e70532ce2f4a3a244007b6a483309b4b2f0723",
"EndpointID": "f0bbfc96cd4bea48f9168cb2aa3fc5e47f788711579116c633245d7f9e8c69f8",
"Gateway": "172.17.0.1",
"IPAddress": "172.17.0.2",
"IPPrefixLen": 16,
"IPv6Gateway": "",
"GlobalIPv6Address": "",
"GlobalIPv6PrefixLen": 0,
"MacAddress": "02:42:ac:11:00:02",
"DriverOpts": null
}
}
}
}
]

进入当前正在运行的容器

1
2
3
4
5
6
7
8
9
#方式1:docker exec -it 容器id bashshell

[root@localhost ~]# docker exec -it 30f /bin/bash

#方式2:docker attach 容器id
[root@localhost ~]# docker attach 30f

#docker exec 进入容器后开启一个新的终端,可以在里面操作(常用)
#docker attach 进入容器正在执行的终端,不会启动新的进程

从容器内复制文件到主机上

1
2
3
4
5
6
7
#docker cp 容器id:容器内路径  目的的主机路径
[root@localhost /]# docker cp 211:/home/test.java /home
[root@localhost /]# cd home
[root@localhost home]# ls
sen sen.java test.java transmission

#复制是一个手动过程,未来使用-v卷技术,可以实现自动同步数据

小结

image-20200727162953284