Docker介绍
Docker是通过内核虚拟化技术(namespaces及cgroups等)来提供容器的资源隔离与安全保障等。由于Docker在操作系统层实现隔离,所以Docker容器在运行时,不需要类似虚拟机(VM)额外的操作系统开销,提高资源利用率。
Docker运行结构
Docker是一个C/S结构的项目,有Docker Client、RESTAPI、Docker Server、images、container、 volumes、network组成。
- Docker Client:Docker客户端命令工具。
- REST API:提供标准的RESTful接口。
- Docker Server::Docker daemon的主要组成部分,接收用户从Docker Client调用REST API发送过来的请求。
- images:docker镜像,是Docker run的原材料。
- container: Docker运行的内容,是独立存在的。
- data volumes: 通过数据挂载的方式,实现数据共享;
- network:用户容器与外部、容器之间的通信,常用的方法有端口映射、link等。
Docker的优点:
- 灵活:即使是复杂的应用程序也可封装。
- 轻量级:容器利用并共享主机内核。
- 便携式:您可以在本地构建,部署到云上并在任何地方运行。
- 可扩展性:您可以增加和自动分发容器副本。
- 可堆叠:您可以垂直堆叠服务并及时并及时堆叠服务。
主机虚拟化和容器的区别
一个容器中运行原生Linux和共享主机与其它容器的内核,它运行一个独立的进程,不占用任何其它可执行文件的内存,使其轻量化。相比之下,虚拟机(VM)运行一个完整的“客户”操作系统,通过虚拟机管理程序虚拟访问主机资源。一般来说,虚拟机提供的环境比大多数应用程序需要的资源多。
虚拟机
虚拟机(virtual machine)就是带环境安装的一种解决方案。它可以在一种操作系统里面运行另一种操作系统,比如在Windows系统里面运行Linux系统。应用程序对此毫无感知,因为虚拟机看上去跟真丝系统一模一样,而对于底层系统来说,虚拟机就是一个普通文件,不需要了就删掉,对其它部分毫无影响。
虚拟机的缺点:
- 资源占用多: 虚拟机会独占一部分内存和硬盘空间。它运行的时候,其他程序就不能使用这些资源了。哪怕虚拟机里面的应用程序,真正使用的内存只有1M,虚拟机依然需要几百MB的内容才能运行。
- 冗余步骤多: 虚拟机是完整的操作系统,一些系统级别的操作步骤,往往无法跳过,比如用户登录。
- 启动慢: 启动操作系统需要多久,启动虚拟机就需要多久。可能要等几分钟,应用陈故乡才能真正运行。
容器
由于虚拟机存在这个缺点,Linux发展出了另一种虚拟化技术:Linux容器(Linux Containers,缩写为LXC)。 Linux容器不是模拟一个完整的操作系统,而是对进程进行隔离。或者说,在正常进程的外面套了一个保护层。对于容器里面的进程来说,它接触到的各种资源都是虚拟的,从而实现与底层系统的隔离。由于容器是进程级别的,相比虚拟机又很多优势。
- 启动快: 容器里面的应用,直接就是底层系统的一个进程,而不是虚拟机内部的进程。所以,启动容器相当于启动本机的一个进程,而不是启动一个操作系统,速度就快很多。
- 资源占用少: 容器只占用需要的资源,不占用那些没有用到的资源;虚拟机由于是完整的操作系统,不可避免要占用所以资源。另外,多个容器可以共享资源,虚拟机都是独享资源。
- 体积小: 容器只要包含用到的组件即可,而虚拟机是整个操作系统的打包,所以容器文件比虚拟机文件要小很多。总之,容器有点像轻量级的虚拟机,能够提供虚拟化的环境,但是成本开销小得多。
Docker与OpenStack对比
类别 | Docker | OpenStack |
---|
部署难度 | 非常简单 | 组件多,部署复杂 |
启动速度 | 秒级 | 分钟级 |
执行性能 | 和物理系统几乎一致 | VM会占用一些资源 |
镜像体积 | 镜像是MB级别 | 虚拟机镜像GB级别 |
管理效率 | 管理简单 | 组件相互依赖,管理复杂 |
隔离性隔 | 离性高 | 彻底隔离 |
可管理性 | 单进程、不建议启动SSH | 完整的系统管理 |
网络连接 | 比较弱 | 借助Neutron可以灵活组件各类网络架构 |
Docker安装部署
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24
| # 环境准备 yum install -y yum-utils # 官方yum仓库 yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo
# 建议使用国内Yum源 cd /etc/yum.repos.d/ wget https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
# 安装docker yum list docker --show-duplicates yum install -y docker-ce
# 配置镜像加速 sudo mkdir -p /etc/docker sudo tee /etc/docker/daemon.json <<-'EOF' { "registry-mirrors": ["https://l2v84zex.mirror.aliyuncs.com"] "bip": "172.0.110.1/24" #建议docker IP与主机IP有关联。 } EOF # 启动docker sudo systemctl daemon-reload sudo systemctl enabled --now docker
|
Docker源码安装
源码下载位置:https://mirrors.tuna.tsinghua.edu.cn/docker-ce/linux/static/stable/x86_64/
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
| # 下载docker源码 mkdir /server/tools cd /server/tools wget https://mirrors.tuna.tsinghua.edu.cn/docker-ce/linux/static/stable/x86_64/docker-20.10.21.tgz tar xf docker-20.10.21.tgz -C /opt/ ln -s /opt/docker/* /bin/
# 创建systemd启动文件 cat > /usr/lib/systemd/system/docker.service <<EOF [Unit] Description=Docker Application Container Engine Documentation=https://docs.docker.com After=network-online.target firewalld.service containerd.service Wants=network-online.target
[Service] Type=notify ExecStart=/usr/bin/dockerd -H unix:///var/run/docker.sock ExecReload=/bin/kill -s HUP $MAINPID TimeoutSec=0 RestartSec=2 Restart=always StartLimitBurst=3 StartLimitInterval=60s LimitNOFILE=infinity LimitNPROC=infinity LimitCORE=infinity TasksMax=infinity Delegate=yes KillMode=process
[Install] WantedBy=multi-user.target EOF
# 配置镜像加速 sudo mkdir -p /etc/docker sudo tee /etc/docker/daemon.json <<-'EOF' { "registry-mirrors": ["https://l2v84zex.mirror.aliyuncs.com"] "bip": "172.0.110.1/24" #建议docker IP与主机IP有关联。 } EOF # 启动docker sudo systemctl daemon-reload sudo systemctl enabled --now docker
|
Docker基础命令操作
获取镜像
1 2 3 4
| docker search centos docker pull centos:6.9 docker pull centos:7.5.1804 docker pull nginx
|
查询镜像
1 2 3
| docker images docker images -q docker inspect ID/name:tag
|
删除镜像
1 2 3
| docker rmi IID docker rmi `docker images -q` docker rmi $(docker images -q)
|
导入导出镜像
1 2
| docker image save nginx >/opt/nginx.tar.gz docker image load -i /opt/nginx.tar.gz
|
容器体验
1 2 3 4 5 6 7 8 9 10 11 12
| docker run hello-world docker run -it --name="test_docker" 9f38484d220f /bin/bash docker run -d -p 8080:80 --name="discuz" nginx:1.14
--name="新容器名称" # 为容器启一个名称 -d # 后台运行容器,并返回容器ID,也就是启动守护士容器 -i # 以交互模式运行容器,通常与-t同时使用. -t # 为容器重新分配一个伪终端(tty),通过与-i同时使用 -P # 随机端口映射 [大写P] -p # 端口映射 [小写P] -v # 数据卷 加参数 ro:容器内的目录只读,不可写 # /宿主机绝对路径目录:/容器内目录[:ro] 镜像名
|
守护式启动
1 2 3 4 5 6 7 8 9
| # docker run -it --name "testnginx" nginx /bin/bash 加ctrl+p+q docker attach testnginx
# docker run --name testnginx1 -d nginx /bin/sh -c "while true ;do echo hello world; sleep 1;done"3.服务前台运行 sshd -D nginx -g ""
|
容器网络访问
1 2 3 4 5 6 7 8 9
| # -p hostPort:containerPort -p ip:hostPort:containerPort -p ip::containerPort(随机端口) -p hostPort:containerPort/udp -p 81:80 –p 443:443
# docker run -P 80(随机端口)
|
容器的其他管理
1 2 3 4 5 6 7 8 9 10 11 12 13 14
| docker ps -a -q -l docker top testxx docker inspect docker attach 容器ID|容器名称(工具类)配合ctrl+p+q,退出容器会销毁容器。 docker exec -i -t 容器ID|容器名称 /bin/bash(服务类),一般是做服务类容器调试用(类似ssh服务,退出容器不会销毁)。 docker exec -it centos6.9 /bin/bash docker logs testxx 查询日志 docker logs -t testxx docker logs -tf testxx docker logs -tf --tail 10 testxx docker logs -tf --tail 0 testxx -t # 加入的时间戳 -f # 跟随最新的日志打印 --tail 行数 # 输出最后几行的日志
|
数据卷管理
1 2 3 4 5 6 7 8
| docker run -d -p 8083:80 --name "http8083" -v /opt/Volume/httpd:/usr/local/apache2/htdocs httpd
docker run -d -p 8084:80 --name "http8084" -v /opt/Volume/httpd:/usr/local/apache2/htdocs httpd
[root@docker httpd]# curl 10.0.0.110:8083 test volume [root@docker httpd]# curl 10.0.0.110:8084 test volume
|
数据卷容器
1 2 3 4 5 6 7 8 9
| docker run -it --name "httpd_volumes" -v /opt/Volume/httpd_volume/conf:/usr/local/apache2/conf -v /opt/Volume/httpd_volume/html:/usr/local/apache2/htdocs centos:6.9 /bin/bash ctrl p q 拷贝数据到数据卷中 /opt/Volume/httpd_volume/html /opt/Volume/httpd_volume/conf docker cp DOCKERNAME:/opt/a.txt /opt 从给定容器装载所有卷 docker run -d -p 8085:80 --volumes-from httpd_volumes --name "http8085" httpd docker run -d -p 8086:80 --volumes-from httpd_volumes --name "http8086" httpd
|