一、全虚拟化、半虚拟化及容器各自的特点二、docker容器
1、docker介绍2、Docker的使用场景3、Docker 引擎(Docker Engine)4、Docker的架构(Docker architecture)5、docker原理6、名称空间(Namespaces)7、控制组(Control groups) 三、container和vm不同点四、扩展内容仓库五、部署20版的docker六、docker镜像操作七、docker容器网络
1、docker容器网通信过程2、docker容器网络模式
2.1 Host网络模式2.2 container网络模式2.3 None 网络模式(该模式关闭了容器的网络功能)2.4 Bridge网络模式2.5 小结:2.6 查看网络模式列表2.7 自定义网络IP(创建一个docker0,可以给它任意指定IP地址网段)2.8 暴露docker容器端口 八、将宿主机里的文件传到docker容器中九、将docker容器内的文件传到宿主机十、授权给容器使用宿主机的命令十一、如何给已经运行的容器添加端口十二、数据卷和数据卷容器
1、数据卷2、数据卷容器 十三、容器互联十四、容器挂载的实验
一、全虚拟化、半虚拟化及容器各自的特点[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ZVD4CbpD-1642349143323)(D:桌面容器图片Snipaste_2022-01-10_15-25-45.png)]
全虚拟化:基于操作系统,用kernel+kvm组件分割内核资源,vmm+qemu抽象层调度管理,上面的vm1、vm2对应各自的接口,去使用内核资源(每个vm1、vm2都是使用vcpu)
半虚拟化:不基于操作系统,硬件服务器完全是裸金属,没有操作系统。半虚拟化直接用软件模拟硬件功能,所以有自己的内核
容器:基于linux操作系统,容器共享内核、内存等资源,一个容器对应一个进程,所以可以有多个容器。容器引擎类似插件(相当于管理虚拟机的软件vmeare)-----容器共享宿主机内核
二、docker容器 1、docker介绍Docker是一个用于开发,交付和运行应用程序的开放平台。Docker使您能够将应用程序与基础架构分开,从而可以快速交付软件。是一个开源的应用容器引擎,让开发者可以打包大门的应用以及依赖包到一个可移植的镜像中,然后发布到任何流行的Linux或者Windows机器上,也可以实现虚拟化。容器是完全使用沙箱机制,相互之间不会有任何接口
沙箱(Sandbox):在计算机安全领域,沙箱是一种程序的隔离运行机制Docker在2013年一炮而红,直到现在,已经成为容器技术的代名词。Docker 从一开始就以提供标准化的运行时环境为目标,真正做到“build once,run anywhere",可以将同一个构建版本用于开发、测试、预发布、生产等任何环境,并且做到了与底层操作系统的解耦。在此基础上还进一步发展出了CaaS(容器即服务)技术。
2013年发布了docker
把容器化技术做成了标准化平台
使用docker有什么意义
docker引擎统一了基础设施环境-docker容器环境(引擎)
docker引擎统一了程序打包(装箱)方式-docker镜像
docker引擎统一了程序部署(运行)方式-docker容器
镜像————》封装的某一个时刻的服务/应用状态
容器————》应用跑起来的状态(正常提供服务的状态-运行时)
打包应用程序简单部署
可脱离底层硬件任意迁移(实现了应用的隔离,将应用拆分并进行解耦),例如:服务器从腾讯云迁移到阿里云
持续集成和持续交付(CI/CD):开发到测试发布
·
部署微服务
提供PAAS产品(平台即服务){OpenStack的云主机类似于阿里云的ECs,属于IAAS、Docker (K8S)属于PAAS}
lAAS:基础设施即服务(基础设施指裸金属,cpu、磁盘、内存、网络、i/o等)
SAAS :应用即服务(应用:例如,lnmp)
PAAS:平台即服务(平台:docker)
Docker Engine是具有以下主要组件的客户端-服务器应用程序(C/s端):
服务器是一种长期运行的程序,称为守护程序进程( dockerd
命令)。
REST API,它指定程序可以用来与守护程序进行通信并指示其操作的
接口。
命令行界面(CLI))客户端(docker命令)。
客户端-----REST API----服务端之间交互过程
1、客户端使用命令传入的方式与rest API交互,例如
docker images (作用:传入命令和展示docker-server返回的结果)
2、rest API再交于服务端
3、服务端daemon整合docker images返回
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-qixRqH0J-1642349143324)(D:桌面容器图片Snipaste_2022-01-10_19-37-06.png)]
4、Docker的架构(Docker architecture)Docker使用客户端-服务器架构。Docker 客户端与Docker守护进程进行对话,该守护进程完成了构建,运行和分发Docker容器的繁重工作。
Docker 区别于传统的虚拟化,不需要虚拟硬件资源,直接使用容器引擎、所以速度快
Docker Client:客户端
Docker客户端(docker)是许多Docker用户与Docker交互的主要方式。当您使用诸如之类的命令时docker run,客户端会将这些命令发送到dockerd,以执行这些命令。该docker命令使用Docker APlo Docker客户端可以与多个守护程序通信。
Docker daemon:守护进程
Docker守护程序( dockerd)侦听Docker API请求并管理Docker对象,例如图像,容器,网络和卷。守护程序还可以与其他守护程序通信以管理Docker服务。
Docker images:镜像
Docker container:容器
Docker registry:镜像仓库
存储镜像的地方,默认在公共的Docker Hub 上查找,可以搞个人仓库。
5、docker原理[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-dVbu5NGH-1642349143325)(D:桌面容器图片Snipaste_2022-01-10_19-53-31.png)]
原理:
命令由客户端传入到docker daemon,然后
搜所本地images,如果没有去registry公共仓库找
找到后返回本地images,然后解析成容器containers
6、名称空间(Namespaces)Docker使用一种称为namespaces提供容器的隔离工作区的技术。运
行容器时,Docker会为该容器创建一组名称空间。
这些名称空间提供了一层隔离。容器的每个方面都在单独的名称空间中运行,并且其访问仅限于该名称空间。
Docker Engine在 Linux上使用以下名称空间:
cgroup资源控制与namespaces结合控制管理了6个名称空间资源:
(1)mount文件系统,挂载点
一个文件系统内,不能重复挂载一个指定目录,例如:/mnt
(2)user:操作进程的用户和用户组
(3)pid:进程编号
(4)uts:主机名和主机域
(5)ipc:信号量、消息队列,共享内存(理解:不同的应用调用内存资源的时候应该使用不同的内存空间)
(6)net:网络设备、网络协议栈、端口等
Linux上的 Docker引擎还依赖于另一种称为控制组(cgroups)的技术。cgroup将应用程序限制为一组特定的资源。控制组允许Docker Engine将可用的硬件资源共享给容器,并有选择地实施限制和约束。例如,您可以限制特定容器可用的内存。
注意:cgroup资源控制和namespaces名称空间两者构成了docker底层原理
总结:基于操作系统,要想两个应用之间完全隔离,必须将6个名称空间隔离
Dcoker是基于容器技术的轻量级虚拟化解决方案docker把linux的cgroup、namespaces等容器底层技术进行完美的封装、并抽象为用户提供创建和管理容器的便捷界面(命令行cli、api等) c/ s
企业中,开发——》运维整体流程 1、首先由开发进行代码研发,研发好之后进行编译、打包 PS:打包:一般会使用maven工具打war包或者jar包 2、打完包之后,放置对应的运行时环境中,进行试运行 PS:这里的运行时环境指:例如tomcat (java环境) php (php环境)等 3、中间会加上一些测试过程,测试代码的有效性、可用性和可执行性 4、以上测试完成,运维会将这个软件包拉过来,运行在实际生产的运行时环境中 问题:在以上的第2点中,不同开发语言的运行时环境混淆在一起运行会有很大的隐患,以及不便 传统中,所谓的运行时环境,例如tomcat (java环境) php (php环境)等 容器中,所谓的运行时环境,指的试"容器"内部 在此之前,容器—》是一个运行时环境,构成容器的组件是image镜像(一个运行时环境的模板)三、container和vm不同点
| 不同点 | container | VM |
|---|---|---|
| 启动速度 | 秒级 | 分钟级 |
| 运行性能 | 接近原生(直接在内核中运行) | 50%左右损失 |
| 磁盘占用 | MB | GB |
| 数量 | 成百上千 | 一般几十台 |
| 隔离性 | 进程级别 | 系统级别(更彻底) |
| 操作系统 | 主要支持Linux | 几乎所有 |
| 封装程度 | 只打包项目代码和依赖关系,共享宿主机内核 | 完整的操作系统,与宿主机隔离 |
高阶重要三个内容:名称空间、隔离、资源分配
拓展的内容:
yum仓库 rpm包
包括:公共仓库和本地yum仓库
docker仓库同yum类似:
公共仓库:docker hub :lnmp lnmp-nginx docker 镜像
本地仓库:docker-harbor 上传下载方便、安全
公共代码仓库:github: github 网络404延迟
以下是本地代码仓库:
gitlab
svn
gitee
码云
语雀
五、部署20版的docker#环境配置
systemctl stop firewalld
systemctl disable firewalld
setenforce 0
vim /etc/selinux/config
SELINUX=disabled
安装依赖包
yum install -y yum-utils device-mapper-persistent-data lvm2
设置阿里云镜像源
cd /etc/yum.repos.d/
以下两种下载源都可以使用:
yum-config-manager --add-repo https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
wget -O /etc/yum.repos.d/CentOS-base.repo http://mirrors.aliyun.com/repo/Centos-7.repo
docker-1.13(统一版本、开源)——》分类型1.15-1.17过程种分成两种,(1)开源社区docker-ce (2)企业版(收钱)docker-ee
#安装docker-ce社区版
yum install -y docker-ce
systemctl start docker
systemctl enable docker
---设置镜像加速--
tee /etc/docker/daemon.json <<-'EOF'
{
"registry-mirrors": ["https://ckexajko.mirror.aliyuncs.com"]
}
EOF
systemctl daemon-reload 重新加载配置文件
systemctl restart docker
##控制docker server端的配置文件是 daemon.json
cat /etc/docker/daemon.json
#镜像加速注册地址
https://help.aliyun.com/ document_detail/60750.html
----------—―网络优化--------
vim /etc/sysctl.conf
net.ipv4.ip_forward=1
sysctl -p
意义:这里的网络优化在于加速流量转发
面试题(生产经验)
#docker-server端配置文件daemon .json
{
"graph" : " /data/ docker" , 数据目录/var/ lib/ docker
"storage-driver" : "overlay2 ", 存储引擎
早期的时候存储引擎使用的是aufs—》overlay2存储引擎
"insecure-registries": [ "registry.access.redhat.com" , "quary.io"] 私有仓库
"registry-mirrors" :[ "https:llq"] 镜像加速
"bip": "172.7.5.1/24", ☆☆☆ ☆ docker网络
"exec-opts":["native.cgroupdriver=systemd"],启动时候的额外参数(驱动,k8s使用)
"live-restore" : true
当docker容器引擎挂掉的时候,使用docker跑起来的容器还能运行(分离)
}
以上是建议的配置项
docker容器网络生产经验
docker 的网络建议和宿主机的iP"对照”
比如宿主机10.2.5.6容器的地址就可以修改为172.5.6.1,这样方便在故障发生时,更容易定位故障节点位置
六、docker镜像操作
docker ps 查看已经运行的docker容器 docker ps -a 查看所有的docker容器及状态 docker images 查看拥有的镜像 docker info 会显示容器统计信息,可以用shell脚本去过滤统计有用信息 docker version 查看docker客户端server端等版本信息 systemctl status docker docker run hello-world run : pull docker hub仓库中项目/库/镜像start hello-world-image 1、docker client 客户端连接到了服务端(服务端是以一个守护进程的形式跑在操作系统里面的) restful api典型的c/s架构 2、由docker服务端的守护进程从docker hub上下载了镜像(PS:服务端会先检查本地系统是否有这个镜像) 3、服务端创建了一个新的容器,然后从拉去的这个镜像启动了一个容器, 容器执行了脚本/可执行程序让我们可以 查看/使用( client ) 4、docker服务端把这些信息流(传递)返回到客户端并展示出来,(展示在终端上) docker client可以是多种形式,比如"docker"命令工具所在的终端 yum仓库,如何开启缓存,软件包保存在哪 linux系统中的命令记10条(cd ls pwd mv cp )docker 十条管理命令(运维常用的命令) #查询docker 版本 docker version && docker info docker search 镜像名 在仓库里搜索镜像 #下载镜像(默认是从docker hub) docker pull 镜像名 docker pull nginx 下载镜像
docker inspect nginx:latest 查看镜像详细信息
镜像名称:版本
docker inspect 605c77e624dd
镜像ID
[
{
"Id": "sha256:605c77e624ddb75e6110f997c58876baa13f8754486b461117934b24a9dc3a85",
"RepoTags": [
"nginx:latest"
],
"RepoDigests": [
"nginx@sha256:0d17b565c37bcbd895e9d92315a05c1c3c9a29f762b011a10c54a66cd53c9b31"
],
"Parent": "",
"Comment": "",
"Created": "2021-12-29T19:28:29.892199479Z",
"Container": "ca3e48389f7160bc9d9a892d316fcbba459344ee3679998739b1c3cd8e56f7da", ##容器层的ID
#容器配置文件 "ContainerConfig": {
#容器名称 "Hostname": "ca3e48389f71",
#域名 "Domainname": "",
"User": "",
#标准输入关闭 "AttachStdin": false,
#标准输出关闭 "AttachStdout": false,
#标准错误输出关闭 "AttachStderr": false,
#暴露端口 "ExposedPorts": {
#映射出80端口 这里还映射出(空的) "80/tcp": {}
},
#终端关闭(无法登陆容器) "Tty": false,
#标准打开关闭 "OpenStdin": false,
#临时打开关闭 "StdinOnce": false,
#坏境 "Env": [
#坏境变量 "PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin",
#nginx版本 "NGINX_VERSION=1.21.5",
"NJS_VERSION=0.7.1",
"PKG_RELEASE=1~bullseye"
],
#传入命令 "Cmd": [
#开启进程 "/bin/sh",
#command命令 "-c",
"#(nop) ",
#传入命令启动nginx "CMD ["nginx" "-g" "daemon off;"]"
],
"Image":"sha256:82941edee2f4d17c55563bb926387c3ae39fa1a99777f088bc9d3db885192209",
#挂载 没有 "Volumes": null,
#指定工作目录 "WorkingDir": "",
#启动系统 "Entrypoint": [
"/docker-entrypoint.sh"
],
"OnBuild": null,
#标签 "Labels": {
"maintainer": "NGINX Docker Maintainers "
},
#发送信息号停止 "StopSignal": "SIGQUIT"
},
#docker版本 "DockerVersion": "20.10.7",
"Author": "",
"Config": {
"Hostname": "",
"Domainname": "",
"User": "",
"AttachStdin": false,
"AttachStdout": false,
"AttachStderr": false,
"ExposedPorts": {
"80/tcp": {}
},
"Tty": false,
"OpenStdin": false,
"StdinOnce": false,
"Env": [
"PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin",
"NGINX_VERSION=1.21.5",
"NJS_VERSION=0.7.1",
"PKG_RELEASE=1~bullseye"
],
"Cmd": [
"nginx",
"-g",
"daemon off;"
],
"Image": "sha256:82941edee2f4d17c55563bb926387c3ae39fa1a99777f088bc9d3db885192209",
"Volumes": null,
"WorkingDir": "",
"Entrypoint": [
"/docker-entrypoint.sh"
],
"OnBuild": null,
"Labels": {
"maintainer": "NGINX Docker Maintainers "
},
"StopSignal": "SIGQUIT"
},
#64位 "Architecture": "amd64",
#操作系统 "Os": "linux",
#大小 "Size": 141479488,
#虚拟大小 "VirtualSize": 141479488,
#数据引擎 "GraphDriver": {
#数据 "Data": {
#数据保存四种类型 "LowerDir": "/var/lib/docker/overlay2/ce125c15a240b0782f686cfe578b55b02237fedc0be80c6cadf6b18bfc240fb8/diff:/var/lib/docker/overlay2/fd1c4bb501718725be4f3a091f1e0b2dbac14aeccb050498336c369a2be3b9df/diff:/var/lib/docker/overlay2/e2c5eda4323d3c65caac95d757725c8ffe6ab760ed92449ce343e03461ff92a7/diff:/var/lib/docker/overlay2/6542522d629751fade707de2d884212a02d54aeb8526f2d7430355280e839f8c/diff:/var/lib/docker/overlay2/e49a563b8ceb1d538c587e9773db538c4d0d75e28b54b7a07c8891082c1a3fda/diff",
"MergedDir": "/var/lib/docker/overlay2/726c03d40d29a7359fd70b796e0e49ac57371d3f09676c8a3ccdec925ef80a06/merged",
"UpperDir": "/var/lib/docker/overlay2/726c03d40d29a7359fd70b796e0e49ac57371d3f09676c8a3ccdec925ef80a06/diff",
"WorkDir": "/var/lib/docker/overlay2/726c03d40d29a7359fd70b796e0e49ac57371d3f09676c8a3ccdec925ef80a06/work"
},
"Name": "overlay2"
},
#系统里唯一的格式 "RootFS": {
"Type": "layers",
"Layers": [
"sha256:2edcec3590a4ec7f40cf0743c15d78fb39d8326bc029073b41ef9727da6c851f",
"sha256:e379e8aedd4d72bb4c529a4ca07a4e4d230b5a1d3f7a61bc80179e8f02421ad8",
"sha256:b8d6e692a25e11b0d32c5c3dd544b71b1085ddc1fddad08e68cbd7fda7f70221",
"sha256:f1db227348d0a5e0b99b15a096d930d1a69db7474a1847acbc31f05e4ef8df8c",
"sha256:32ce5f6a5106cc637d09a98289782edf47c32cb082dc475dd47cbf19a4f866da",
"sha256:d874fd2bc83bb3322b566df739681fbd2248c58d3369cb25908d68e7ed6040a6"
]
},
"metadata": {
"LastTagTime": "0001-01-01T00:00:00Z"
}
}
]
###overlay2 存储引擎
镜像包括四层:LowerDir
MergedDir
UpperDir
WorkDir
#添加镜像标签 //添加的镜像标签类似于软连接,共用同一个镜像数据
docker tag nginx:latest nginx:lnmp
需要加标签的镜像 加标签后的镜像名
[root@docker ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
nginx latest 605c77e624dd 2 weeks ago 141MB
[root@docker ~]# docker tag nginx:latest nginx:lnmp
[root@docker ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
nginx latest 605c77e624dd 2 weeks ago 141MB
nginx lnmp 605c77e624dd 2 weeks ago 141MB
##加标签后,镜像ID跟原来的一样
#删除镜像 docker rmi 镜像名称:镜像标签 docker rmi 镜像ID [root@docker ~]# docker images REPOSITORY TAG IMAGE ID CREATED SIZE nginx latest 605c77e624dd 2 weeks ago 141MB nginx lnmp 605c77e624dd 2 weeks ago 141MB [root@docker ~]# docker rmi nginx:lnmp Untagged: nginx:lnmp [root@docker ~]# docker images REPOSITORY TAG IMAGE ID CREATED SIZE nginx latest 605c77e624dd 2 weeks ago 141MB ##Untagged: nginx:lnmp 信息显示只删除了标签,验证上面的添加镜像标签 ##添加的镜像标签,因为跟原来的镜像有同样的镜像ID,所以不能用镜像ID删除,要用镜像标签 docker images -q 查看所有镜像ID docker rmi `docker images -q` 基于镜像ID删除,所以用来批量删除镜像
#镜像导出 docker save -o 文件名 镜像名 示例: docker save -o nginx_docker nginx:latest #镜像导入 docker load < nginx 使用场景,有的生产环境,企业不直接使用docker私有仓库,而是存放在一个ftp服务器中,按需上传下载
#查询容器
docker ps -a
#创建容器
docker create -it nginx:latest /bin/bash
-i 让容器的标准输入保持打开
-t 分配一个伪终端
-d 后台守护进程的方式运行
-i 跟前面的标准输入对应,用于打开容器进行输入
-t 同样的代表终端Tty,用于给予一个伪终端,进行登录容器
/bin/bash 用于创建一个/bin/bash坏境去运行容器
##开启创建的容器
docker start 243d4571f78c
容器ID
#停止容器
docker stop 容器ID
[root@docker ~]# docker ps -a
ConTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
[root@docker ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
nginx latest 605c77e624dd 2 weeks ago 141MB
centos 7 eeb6ee3f44bd 4 months ago 204MB
[root@docker ~]# docker create -it nginx:latest /bin/bash
243d4571f78ce2fe4b95b116962c859a4336faa918d6cb7066ae3d97c30f8285
[root@docker ~]# docker ps -a
ConTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
243d4571f78c nginx:latest "/docker-entrypoint.…" 14 seconds ago Created sleepy_johnson
##status状态信息显示创建create代表创建成功
##开启创建的容器
docker start 243d4571f78c
[root@docker ~]# docker start 243d4571f78c
243d4571f78c
[root@docker ~]# docker ps -a
ConTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
243d4571f78c nginx:latest "/docker-entrypoint.…" 8 minutes ago Up about a minute 80/tcp sleepy_johnson
##status显示Up about a minute说明容器开启成功,也代表在运行
#创建并启动容器(一次性执行)
docker run centos:7 /usr/bin/bash -c ls /
指定命令 根目录
[root@docker ~]# docker run centos:7 /usr/bin/bash -c ls /
anaconda-post.log
bin
dev
etc
home
lib
lib64
media
mnt
opt
proc
root
run
sbin
srv
sys
tmp
usr
var
[root@docker ~]# docker ps -a
ConTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
a617a6f76e72 centos:7 "/usr/bin/bash -c ls…" about a minute ago Exited (0) about a minute ago suspicious_einstein
##status显示容器是Exited (0) about退出状态,说明只是一次性启动,退出后就关闭了,此时容器并没有运行
##进入容器
docker run -it centos:7 /bin/bash
##每一秒执行一次“docker ps -a”并输出到终端上
watch -n 1 docker ps -a
周期
##退出容器
exit
Ctrl+d
##查看容器信息
docker inspect 容器名/容器ID
##进入容器(已经运行的容器),跟上面的区别在于退出后,容器还在运行
docker exec -it dccfdf64fca9 /bin/bash
exec(容器必须为开启状态)
Ps:
docker run -it 会创建前台进程,但是会在输入exit后终止进程。
docker attach 会通过连接stdin,连接到容器内输入输出流,会在输入exit后终止容器进程.
docker exec -it 会连接到容器,可以像sSH一样进入容器内部,进行操作,可以通过exit退出容器,不影响容器运行。
##持续后台运行
docker run -d centos:7 /bin/bash -c "while true;do echo hello;done"
##不加死循环不能持续后台运行,必须有一个任务,才能持续后台运行
docker run -d --name test centos:7 /bin/bash
后台 命名 指定的名字
#容器导出 docker export 容器ID >文件名 示例: docker export 容器工D > nginx_a #容器导入(生成镜像) docker import 导出的文件名(容器) 指定镜像名称 示例: docker import nginx_a nginx:latest
##删除容器
docker rm 容器ID
##强制删除运行的容器
docker rm -f 容器ID
##批量删除容器
docker rm `docker ps -aq`
##强制批量删除容器
docker rm -f `docker ps -aq`
##查看运行的容器ID
docker ps -q
##查看所有容器ID
docker ps -aq
#批量册删除容器(正则匹配)
docker ps -a | awk '{print "docker rm" $1}' | bash
#批量删除"exit"状态(指定状态)的容器
for i in `docker ps -a | grep -i exit | awk '{print $1}'`; do docker rm -f $i; done
##查询所有运行容器资源消耗信息 docker stats ConTAINER ID NAME CPU % MEM USAGE / LIMIT MEM % NET I/O BLOCK I/O c612adcbb85f inspiring_austin 0.00% 652KiB / 1.938GiB 0.03% 648B / 0B 549kB/0B 42221a1a55c7 unruffled_einstein 0.00% 496KiB / 1.938GiB 0.02% 648B / 0B 0B/0B PIDS 1 1 ##MEM USAGE / LIMIT 已使用内存量/内存剩余最大使用上限 ##MEM % 内存使用占比 ##NET I/O 网络速率/I/O输入输出 ##docker stats 主要用于查看资源使用情况和监控 ##调用docker资源使用的一个组件cadvisor七、docker容器网络 1、docker容器网通信过程
docker0 类似于一个容器,网卡名docker0 ens33 宿主机网卡 lo 环回网卡 veth1cf9842 veth对,是一对虚拟接口/端口,用于连接容器和docker0(用于连接两个不同名称空间) virbr0 虚拟网卡 bridge 网桥,用于连接不同的名称空间 网桥在容器中 用于连接宿主机跟docker0
单网桥容器间通信:
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-8qc6Ttka-1642349143326)(D:桌面容器图片Snipaste_2022-01-15_19-53-23.png)]
双网桥或多个网桥之间通信模式:
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-6KhElj1g-1642349143326)(D:桌面容器图片Snipaste_2022-01-15_20-09-41.png)]
docker容器的IP地址是由docker0分配的,同时也会承担作为一组docker容器的网关
docker0会以映射的方式映射出容器内nginx的端口80-----8080
默认是docker0
如果想自定义容器网段及IP,手动创建一个docker1(网桥),就可以自定义创建容器网段及IP
网桥与网桥之间通过物理网卡连接通信
docker inspect 镜像ID 可以查看到容器IP地址2、docker容器网络模式
##几种网络模式 bridge: 网桥 host: 主机 ipvlan: ip方式划分vlan macvlan: mac二层划分vlan null: 没有 overlay: 叠加2.1 Host网络模式
Host :与宿主机共享网络名称空间/网络协议栈,IP共享、端口范围共享 host容器将不会虚拟出自己的网卡,配置自己的IP等,而是使用宿主机的IP和端口如果启动容器的时候使用host模式,那么这个容器将不会获得一个独立的Network Namespace,而是和宿主机共用一个Network Namespace。容器将不会虚拟出自己的网卡,配置自己的IP等,而是使用宿主机的IP和端口。但是,容器的其他方面,如文件系统、进程列表等还是和宿主机隔离的。 使用host模式的容器可以直接使用宿主机的IP地址与外界通信,容器内部的服务端口也可以使用宿主机的端口,不需要进行NAT,host最大的优势就是网络性能比较好,但是 docker host上已经使用的端口就不能再用了,网络的隔离性不好。2.2 container网络模式
Container:多个容器之间共享一个network namespaces,多个容器公用一个IP和端口范围 二、container创建的容器不会创建自己的网卡、设置IP等,而是和一个指定地容器共享IP、端口范围 这个模式指定新创建的容器和已经存在的一个容器共享一个network namespace,而不是和宿主机共享,新创建的容器不会创建自己的网卡,配置自己的Ip,而是和一个指定地容器共享IP、端口范围等。同样,两个容器除了网络方面,其他的如文件系统、进程列表还是隔离的。(★☆两个容器的进程可以通过 loo网卡设备通信)
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-pN4OuEV7-1642349143327)(D:桌面容器图片Snipaste_2022-01-15_22-24-55.png)]
2.3 None 网络模式(该模式关闭了容器的网络功能)none没有任何网络连接 none模式可以在容器创建时通过 -network=none参数指定 这种类型的网络无法联网,但是封闭的网络能很好的保证容器的安全性 ##none网络模式有两种用法: 1、可以当做一个私有仓库,存储镜像。 2、当作一个存储空间,挂载到另一个有网容器上,例如,将这种none封闭模式的容器挂载到nginx服务器。2.4 Bridge网络模式
Bridge:此模式会为每一个容器分配、设置IP等,并将容器连接到一个docker0虚拟网桥,通过docker0 网桥及iptables.的 nat表配置与宿主机通信 当Docker进程启动时,会在主机上创建一个名为dockero的虚拟网桥,此主机上启动的Docker容器会连接到这个虚拟网桥上。虚拟网桥的工作方式和物理交换机类似,这样主机上的所有容器就通过交换机连在了一个二层网络中。 从dockerO子网中分配一个IP给容器使用,并设置docker0的地址为容器的默认网关。在主机上创建一对虚拟网卡veth pair 设备,Docker将 veth pair 设备的一端放在新创建的容器中,并命名为etho(容器的网卡),另一端放在主机中,以vethxxx这样类似的名字命名,并将这个网络设备加入到dockero 网桥中。可以通过 brctl show命令查看。 总结:容器通过veth对跟docker0连接,docker0内通过iptables的规则,将ip及端口以映射的方式,映射给宿主机网卡,再通过宿主机网卡连接外网2.5 小结:
注意:host模式和container模式,在k8s中也有对应的模式(原理相同)
docker 0 :容器的网关,绑定物理网卡,负责做NAT地址转换、端口映射
docker 0:本身也是一种容器
容器内的网卡是eth0,就是veth对
四种网络模式 --host模式 -net=host 容器和宿主机共享Network namespace。 container模式 -net=container:NAME or ID 多个谷器共旱一个Network namespaceo none模式 -net=none 容器有独立的Network namespace,但并没有对其进行任何网络设置,如分配veth pair 和网桥连接,配置IP等。 bridge模式 -net=bridge (默认为i该模式) 以上不需要动手配置,真正需要配置的是自定义网络2.6 查看网络模式列表
[root@docker ~]# docker network ls NETWORK ID NAME DRIVER SCOPE 4baec400f197 bridge bridge local af302cfc44e3 host host local 1a4fe24e8198 none null local2.7 自定义网络IP(创建一个docker0,可以给它任意指定IP地址网段)
##创建docker0,自定义ip命令 [root@docker ~]# docker network create --subnet=172.18.0.0/16 mynetwork b0bd26fc40988b99a92e1e84fc713058f3c38963d480beab9466163151be9efe ##docker默认是bridge模式,所以这条命令里面可以加上 --network bridge ##创建docker0网卡成功后,用下列命令可以查看到 [root@docker ~]# docker network ls NETWORK ID NAME DRIVER SCOPE 4baec400f197 bridge bridge local af302cfc44e3 host host local b0bd26fc4098 mynetwork bridge local 1a4fe24e8198 none null local ##用ifconfig可以看到创建的新的容器网卡 [root@docker ~]# ifconfig br-b0bd26fc4098: flags=4099mtu 1500 inet 172.18.0.1 netmask 255.255.0.0 broadcast 172.18.255.255 ether 02:42:e1:41:e5:b9 txqueuelen 0 (Ethernet) RX packets 0 bytes 0 (0.0 B) RX errors 0 dropped 0 overruns 0 frame 0 TX packets 8 bytes 648 (648.0 B) TX errors 0 dropped 0 overruns 0 carrier 0 collisions 0
##网卡创建成功后,用此网卡运行一个容器
[root@docker ~]# docker run -itd --name test01 --net mynetwork --ip 172.18.0.100 centos:7 /bin/bash 指定容器名称 指定容器网卡 指定容器ip
0f53832249563491495af3619082089841d7ae855665251727b939a897310c52
##查看是否创建成功
[root@docker ~]# docker ps -a
ConTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
0f5383224956 centos:7 "/bin/bash" 13 seconds ago Up 12 seconds test01
##查看test01这个容器,IP地址是不是自定义的
[root@docker ~]# docker inspect test01
........省略部分内容......
"Gateway": "172.18.0.1",
"IPAddress": "172.18.0.100",
"IPPrefixLen": 16,
"IPv6Gateway": "",
"GlobalIPv6Address": "",
"GlobalIPv6PrefixLen": 0,
"MacAddress": "02:42:ac:12:00:64",
"DriverOpts": null
2.8 暴露docker容器端口
#暴露端口 -p 自定义端口 (宿主机端口:容器内端口) -P随机端口 ( -P 49153起始49153到65535) docker run -itd -p 333:80 nginx /bin/bash 用的是(docker 0)网卡 docker run -itd -P nginx /bin/bash #在宿主机环境执行容器内命令 docker exec -it 容器ID /bin/bash -c 'nginx'
自定义端口
##以映射的方式(333:80),将nginx的80端口暴露出去
[root@docker ~]# docker run -itd -p 333:80 nginx:latest /bin/bash
自定义端口
e34d2fe38f34ba9252d76dba987b2556f1bee329a91e0a5517c340178bc87103
##查看端口态(0.0.0.0:333->80/tctcp)
[root@docker ~]# docker ps -a
ConTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
e34d2fe38f34 nginx:latest "/docker-entrypoint.…" 40 seconds ago Up 40 seconds 0.0.0.0:333->80/tctcp practical_nobel
0f5383224956 centos:7 "/bin/bash" 29 minutes ago Up 29 minutes test01
##尝试访问nginx80端口映射暴露出的宿主机端口333
[root@docker ~]# curl 192.168.111.51:333
curl: (7) Failed connect to 192.168.111.51:333; 拒绝连接
##拒绝连接说明nginx进程没开启,nginx是一个命令,可以不进入容器开启nginx进程
##不进入容器开启nginx进程
[root@docker ~]# docker exec -it e34d2fe38f34 /bin/bash -c nginx
2022/01/15 16:27:55 [notice] 7#7: using the "epoll" event method
2022/01/15 16:27:55 [notice] 7#7: nginx/1.21.5
2022/01/15 16:27:55 [notice] 7#7: built by gcc 10.2.1 20210110 (Debian 10.2.1-6)
2022/01/15 16:27:55 [notice] 7#7: OS: Linux 3.10.0-693.el7.x86_64
2022/01/15 16:27:55 [notice] 7#7: getrlimit(RLIMIT_NOFILE): 1048576:1048576
2022/01/15 16:27:55 [notice] 13#13: start worker processes
2022/01/15 16:27:55 [notice] 13#13: start worker process 14
2022/01/15 16:27:55 [notice] 13#13: start worker process 15
##再次访问宿主机333端口(实质上是访问nginx80端口)
[root@docker ~]# curl 192.168.111.51:333
Welcome to nginx!
Welcome to nginx!
If you see this page, the nginx web server is successfully installed and
working. Further configuration is required.
For online documentation and support please refer to
nginx.org.
Commercial support is available at
nginx.com.
Thank you for using nginx.
随机端口
##使用-P暴露映射nginx80端口----随机的一个映射端口
[root@docker ~]# docker run -itd -P --name nginx01 nginx:latest /bin/bash
480a1175100a92b488550530c4e497824cf52bf887b5abaff098719eecbbdc19
[root@docker ~]# docker ps -a
ConTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
480a1175100a nginx:latest "/docker-entrypoint.…" 16 seconds ago Up 16 seconds 0.0.0.0:49153->80/tcp, :::49153->80/tcp nginx01
e34d2fe38f34 nginx:latest "/docker-entrypoint.…" 32 minutes ago Up 32 minutes 0.0.0.0:333->80/tcp, :::333->80/tcp practical_nobel
0f5383224956 centos:7 "/bin/bash" about an hour ago Up about an hour test01
八、将宿主机里的文件传到docker容器中
[root@docker opt]# docker cp /opt/1.txt 0f5383224956:/opt/
宿主机目录路径 容器ID 容器目录路径
##在容器里查看,是否复制成功
[root@0f5383224956 opt]# ls
1.txt
九、将docker容器内的文件传到宿主机
[root@docker opt]# docker cp 0f5383224956:/opt/2.txt /opt/
容器ID 容器目录路径 宿主机目录路径
##查看宿主机/opt目录
[root@docker opt]# ls
2.txt containerd rh
注意:宿主机与容器传输文件,命令是输入在宿主机上
十、授权给容器使用宿主机的命令
##授权容器使用宿主机的命令
[root@docker opt]# docker run -itd --name centos01 --privileged=true centos:7 /sbin/init
授权 使用的镜像 init初始化
31dac396556d53e5998322a47d1cd3e5cf4098f52f8a129135263a9583e7ff14
##查看
[root@docker opt]# docker ps -a
ConTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
31dac396556d centos:7 "/sbin/init" 14 seconds ago Up 13 seconds centos01
##进入容器
[root@docker opt]# docker exec -it 31dac396556d /bin/bash
##安装http
[root@31dac396556d /]# yum install -y httpd
##验证用systemctl开启http
[root@31dac396556d /]# systemctl start httpd
十一、如何给已经运行的容器添加端口
#面试题:
docker中,假设,我运行了一个业务容器,需要暴露3个端口,启动之后发现自己少加了一个端口,那么,如何动态添加端口(如何对己运行的容器,添加/修改端口):
我们可以修改/var/lib/docker/container/[container_id]/中的两个文件
第一个文件:hostconfig.json portbinding:{}修改端口或添加端口
第二个文件:修改config.v2.json 文件,修改对应的Ports{} 来添加/修改端口
最后,重载守护进程
十二、数据卷和数据卷容器
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-wEMueOOD-1642349143328)(D:桌面容器图片Snipaste_2022-01-16_19-26-32.png)]
1、数据卷数据卷:将宿主机的目录与容器内的指定目录进行挂载
作用:
(1)方便在宿主机上直接修改容器内的服务的配置文件(不用进入容器,就可以在宿主机上修改)
(2)可以将容器内数据将进行备份,在容器挂掉后,进行恢复
(3)传入变量挂载到宿主机在宿主机上添加变量内容,将变量放入共享目录,在容器中/etc/profile直接加载就可以export xxdir=/data/ data1/ xx.
##将宿主机目录与容器的目录进行挂载
[root@docker opt]# docker run -it -v /var/www:/data1 --name centos02 centos:7 /bin/bash
挂载 宿主机目录 容器目录
##验证(宿主机)
[root@docker ~]# cd /var/www/
[root@docker www]# ls
[root@docker www]# touch 1.txt
[root@docker www]# ls
1.txt
##在宿主机上创建文件容器内也会有
[root@c64d9925b03b /]# cd /data1
[root@c64d9925b03b data1]# ls
[root@c64d9925b03b data1]# ls
1.txt
2、数据卷容器
数据卷容器:将两个容器互相进行挂载,实现通讯
##新创建一个容器,暴露两个挂载点,使得另一个容器能够挂载连接
[root@docker ~]# docker run -it --name centos01 -v /data1 -v data2 centos:7 /bin/bash
暴露挂载点 暴露挂载点
##查看
[root@eb34b8a27116 /]# ls
anaconda-post.log data1 dev home lib64 mnt proc run srv tmp var
bin data2 etc lib media opt root sbin sys usr
##连接上面暴露出来的两个挂载点
[root@docker ~]# docker run -it --volumes-from centos01 --name centos02 centos:7 /bin/bash 指定挂载点来自centos01
##查看
[root@eb23dc8b2afe /]# ls
anaconda-post.log data1 dev home lib64 mnt proc run srv tmp var
bin data2 etc lib media opt root sbin sys usr
注意:只有挂载的目录,才能实现互相通讯
十三、容器互联--容器互联(使用centos镜像) docker run -itd -P --name web1 centos /bin/bash //创建并运行容器取名web1,端口号自动映射 docker run -itd -P --name web2 --link web1:web1 centos /bin/bash //创建并运行容器取名web2,链接到web1和其通信 进web2容器ping web1 哨兵—》监控redis 哨兵和redis包括哨兵和哨兵之间相互监控,会使用ping命令十四、容器挂载的实验
##小实验: 使用自定义配置启动redis mkdir -p / data/redismkdir /etc/ redis cd /data/redis/ && echo "appendonly yes" >>/data/redis/redis.conf 需求1:自定义挂载配置文件、自定义配置数据目录 docker run -v /data/redis/redis.conf:/etc/redis/redis.conf -v / data/redis / data : / data -d --name myredis l -p 6379:6379 l redis:latest redis-server letc/redis/redis.conf 使用redisDesktop Manager测试redis 连接 登陆——》connect to redis server ##配置账号密码 echo "requirepass abc123" >> letc/redis/redis.conf ##重启docker docker restart myredis #重新使用工具连接redis———》测试auth ##Redis desktop是redis可视化的一个windows工具



