Linux-容器(一)

容器-容器架构(一)

一、Iaas Paas Saas

Iaas:基础设施即服务 Infrastructure-as-a-Service

Paas:平台即服务 Platform-as-a-Service

Saas:软件即服务 Software-as-a-Service

Caas:容器即服务 介于IAAS和PAAS

IAAS,PAAS,SAAS这些服务,用于帮助人们更快实现目标(搭建环境,使用产品)

从左到右,人们需要管理与维护的地方越来越少,人们可以把重点关注在使用/应用上

IAAS平台:基础设施,阿里云,云厂商.

PAAS平台:服务/运行环境是ok,公有云,负载均衡SLB

SAAS平台:服务已经准备好,您直接用,具体产品,processon,wps,亿图.

image

二、什么是容器

容器是隔离的环境中运行的一个进程,如果进程结束,容器就会停止.

容器的隔离环境,拥有自己的ip地址,系统文件,主机名,进程管理,相当于一个mini的系统.

三、容器vs虚拟机

虚拟机 容器
优点 1. 使用简单
2. 也有成熟管理工具,vmware esxi,KVM,Openstack
3. 可以随意定制.
4. 启动虚拟机要经历完整的Linux启动流程
1. 快速部署(扩容,弹性伸缩)
2. 大部分环境都有现成镜像
3. 让我们不再关注系统基础设施,把关注点放在配置,升级,优化
4. 不依赖硬件
5. 启动容器秒级.
6. 相当于一个进程
缺点 1. 需要硬件支持虚拟化技术(VT-X)
2. 资源利用率不高
3. 同一台虚拟跑多个服务,可能有冲突
4. 占用资源较多.
5. 不满足目前升级,快速扩容,快速部署,回滚不方便.
1. 使用较为复杂
2. 共享linux系统内核,推荐使用较新linux内核.

四、Docker极速上手指南

温馨提示:

Linux内核:3.10以上,如果是旧的内核,需要升级内核才能使用

docker分为docker-ce(开源),docker-ee(企业版)

从1.13开始改成年-月版本命名方式

docker环境 ip 配置
docker01 10.0.0.81/172.16.1.81 2核4G
docker02 10.0.0.82/172.16.1.82 2核4G

1.配置docker源

#安装相关依赖
[root@docker01 ~]# yum install -y yum-utils device-mapper-persistent-data lvm2
#下载官方的docker yum源
[root@docker01 ~]# yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo
#替换yum源地址
[root@docker01 ~]# sed -i 's+download.docker.com+mirrors.tuna.tsinghua.edu.cn/docker-ce+' /etc/yum.repos.d/docker-ce.repo
#安装docker-ce
[root@docker01 ~]# yum install -y docker-ce
#启动docker
[root@docker01 ~]# systemctl enable --now docker 
#检查
[root@docker01 ~]# docker version

2.docker下载镜像加速的配置

#配置docker下载镜像加速
[root@docker01 ~]# mkdir -p /etc/docker
[root@docker01 ~]# cat /etc/docker/daemon.json
{
    "registry-mirrors": [ "https://*******" ]
}
#这个地址是每个人都不一样的
[root@docker01 ~]# systemctl daemon-reload 
[root@docker01 ~]# systemctl restart docker

image

3.安装命令补齐工具,方便补齐docker命令

yum install -y bash-completion bash-completion-extras

五、Docker C/S架构

cs client/server 客户端/服务端

Docker 服务端:docker daemon 叫dockerd

Docker 客户端:docker命令(下载镜像,运行容器)

docker 说明
镜像 存放各种环境或服务
容器 进程,运行起来的镜像
仓库(存放镜像) 远程仓库,本地仓库

image

image

image

docker pull nginx 下载nginx镜像到本地仓库.
如果本地仓库有则提示镜像已经下载.
如果本地出仓库没有,则docker服务端访问远程仓库,下载镜像

docker run -d -p 80:80 nginx 启动容器
-d容器后台运行
-p端口映射
nginx镜像名字

#启动之前80不能开,开了的话,关了80重启,把run改成restart
[root@docker01 ~]# docker run  -d -p 80:80   --name "first_docker_nginx"    nginx:alpine
# 提示你本地没有nginx镜像 nginx:alpine
Unable to find image 'nginx:alpine' locally  
#找远程仓库下载
alpine: Pulling from library/nginx
63b65145d645: Pull complete 
8c7e1fd96380: Pull complete 
86c5246c96db: Pull complete 
b874033c43fb: Pull complete 
dbe1551bd73f: Pull complete 
0d4f6b3f3de6: Pull complete 
2a41f256c40f: Pull complete 
#运行镜像,成为docker容器.
Digest: sha256:207332a7d1d17b884b5a0e94bcf7c0f67f1a518b9bf8da6c2ea72c83eec889b8
Status: Downloaded newer image for nginx:alpine
f60d3eb4dae69812e216005d61a5780529f2fad9c59fb60a37fe06b6d71f60c8
#查看镜像
[root@docker01 ~]# docker images
REPOSITORY   TAG             IMAGE ID       CREATED        SIZE
nginx        alpine          2bc7edbc3cf2   2 weeks ago    40.7MB
#查看容器
[root@docker01 ~]# docker ps
#测试
访问10.0.0.81:80

注意事项:

此处使用到了docker -p端口映射公共,需要使用iptables的nat功能,需要开启系统的内核转发功能.

[root@docker01 ~]# cat /etc/sysctl.conf 
net.ipv4.ip_forward = 1

[root@docker01 ~]# sysctl -p
net.ipv4.ip_forward = 1

六、Docker的镜像管理

镜像管理核心指令

docker images == docker image ls
docker search 搜索镜像, 优先选官方,stars数量多
docker pull   拉取镜像(下载镜像),注意版本
docker push   推送镜像(上传镜像)
docker load   导入镜像
例子: docker load  -i docker_nginx.tar.gz
docker save   导出镜像
例子:docker save centos:7 -o
docker_centos7.tar.gz
docker images   查看镜像列表
docker rmi     删除镜像
docker tag     给镜像打标签

1.案例:下载nginx:alpine镜像并查看

[root@docker01 ~]# docker pull nginx:1.22-alpine
1.22-alpine: Pulling from library/nginx
ef5531b6e74e: Pull complete 
a58af6dacd0d: Pull complete 
973e47049cf2: Pull complete 
d0264186e749: Pull complete 
90ac7e527cb7: Pull complete 
0c63f9db0dba: Pull complete 
Digest: sha256:db81e6644d4896391d83b92e6cb7ff7f9f0cfa5a14d2c7a621d682be99d90f43
Status: Downloaded newer image for nginx:1.22-alpine
docker.io/library/nginx:1.22-alpine
[root@docker01 ~]#  docker images
REPOSITORY   TAG           IMAGE ID       CREATED       SIZE
nginx        1.22-alpine   652309d09131   3 weeks ago   23.5MB

#可以查看系统中所有镜像,包含隐藏镜像
[root@docker01 ~]# docker images -a
REPOSITORY   TAG           IMAGE ID       CREATED       SIZE
nginx        1.22-alpine   652309d09131   3 weeks ago   23.5MB



#查找镜像,一般都从hub.docker查找
[root@docker01 ~]# docker search nginx
NAME          DESCRIPTION                              STARS     OFFICIAL   AUTOMATED
nginx         Official build of Nginx.                 18182     [OK]       
bitnami/nginx Bitnami nginx Docker Image                 151                  [OK]
镜像命名:
#指定版本
只写服务名字一般下载服务的最新版本.
nginx 下载ngx最新版本   nginx:latest
下载ngx最新稳定的版本    nginx:stable
下载指定的版本           nginx:1.20.2

#指定系统
nginx镜像默认的系统是Debian系统
docker pull nginx:1.20.2-alpine 使用alpine系统更加节约空间
docker镜像使用的系统
ubuntu 都可以做镜像的系统.
debian 都可以做镜像的系统. bullseye ,bluster
centos 都可以做镜像的系统
alpine 镜像非常小(命令,依赖精简) linux内核+busybox

2.案例:sl大法

保存docker镜像(save),其他节点上导入(load).
#docker01保存
[root@docker01 ~]# docker save nginx:alpine -o nginx_alpine.tar
[root@docker01 ~]# ll
total 155536
-rw-------. 1 root root      1340 Jan  9 09:09 anaconda-ks.cfg
-rw-r--r--  1 root root 116684757 Mar  3 10:38 docker.tar.gz
-rw-------  1 root root  42570240 Mar  3 12:06 nginx_alpine.tar
#docker02导入
[root@docker02 ~]# docker load -i nginx_alpine.tar 
7cd52847ad77: Loading layer [==================================================>]  7.338MB/7.338MB
d8a5a02a8c2d: Loading layer [==================================================>]   5.32MB/5.32MB
5e59460a18a3: Loading layer [==================================================>]  3.584kB/3.584kB
152a948bab3b: Loading layer [==================================================>]  4.608kB/4.608kB
c4d67a5827ca: Loading layer [==================================================>]  3.584kB/3.584kB
f1bee861c2ba: Loading layer [==================================================>]  7.168kB/7.168kB
042cd3f87f43: Loading layer [==================================================>]  29.85MB/29.85MB
Loaded image: nginx:alpine
[root@docker02 ~]# docker images
REPOSITORY   TAG       IMAGE ID       CREATED       SIZE
nginx        alpine    2bc7edbc3cf2   2 weeks ago   40.7MB


#批量导出镜像
docker images |awk 'NR>1{print "docker save",$1":"$2,"-o",$1"_"$2".tar"}'
最后通过|bash运行

3. 案例:删除镜像

docker image rm == docker rmi

注:删除镜像的条件是镜像不能在使用中(没有基于这个镜像的容器)
[root@docker01 ~]# docker images
REPOSITORY   TAG           IMAGE ID       CREATED       SIZE
nginx        1.22-alpine   652309d09131   3 weeks ago   23.5MB
[root@docker01 ~]# docker  rmi 652309d09131
Untagged: nginx:1.22-alpine
Untagged: nginx@sha256:db81e6644d4896391d83b92e6cb7ff7f9f0cfa5a14d2c7a621d682be99d90f43
Deleted: sha256:652309d091315e4f9f5d9d9270b69838b8a4021d9a0fc2860ad37a8c22274ffc
Deleted: sha256:6f98350fdf1ada8310c6c999f2c016c7bb0eedbfde26c146a0a5177ba02b6c20
Deleted: sha256:6371ddc8eb90443de04fcce4b742443532196889aa0e0f5c38e15ab1bac1457d
Deleted: sha256:a49c5f9132622e4dee3dbf6198e76cf9bbfddce75fa3a67445ac840fd5090466
Deleted: sha256:98bded601fe4d4b7960f403a3e082efa9b477d369db59284a124a5a7e2acf46f
Deleted: sha256:15fb64e773636f0a8a1188cec4395024e33541e7ecc6e2913648ca3f976ee67f
Deleted: sha256:aa5968d388b8652cd305e0e037751228967839d83d0cafbde5debf0b092e7c42
[root@docker01 ~]# docker images
REPOSITORY   TAG       IMAGE ID   CREATED   SIZE

4.案例:镜像清理

用于清理一些临时镜像,未来自定义镜像的时候会有

[root@docker02 ~]# docker image prune 
WARNING! This will remove all dangling images.
Are you sure you want to continue? [y/N] n
Total reclaimed space: 0B

5.案例:给镜像设置标签

给镜像设置一个新的名字.

应用场景:

  • 自定义镜像.

  • 搭建与使用内部镜像仓库.registry

[root@docker01 ~]# docker images
REPOSITORY   TAG           IMAGE ID       CREATED       SIZE
nginx        1.22-alpine   652309d09131   3 weeks ago   23.5MB
[root@docker01 ~]# docker tag nginx:1.22-alpine nginx:1.22
[root@docker01 ~]# docker images
REPOSITORY   TAG           IMAGE ID       CREATED       SIZE
nginx        1.22          652309d09131   3 weeks ago   23.5MB
nginx        1.22-alpine   652309d09131   3 weeks ago   23.5MB

#id没有变,就相当生成一个硬链接,占一份空间

6.案例:查看你镜像详细信息

docker家目录  /var/lib/docker

#查看 nginx:alpine镜像的信息,输出的是json格式
[root@docker01 ~]# docker inspect nginx:1.22

7.案例:自定义镜像

docker image build ==docker build

8.jq

json形式数据:key value 键值对,变量和变量内容
处理json形式数据的专用命令:jq
[root@docker01 ~]# yum -y install jq

#查看镜像的id
[root@docker01 ~]# docker inspect nginx:alpine | jq .[].Id
"sha256:2bc7edbc3cf2fce630a95d0586c48cd248e5df37df5b1244728a5c8c91becfe0"
#查看容器主机名
[root@docker01 ~]# docker inspect nginx:1.22-alpine | jq .[].ContainerConfig.Hostname
"60cbd290bbf4"

七、Docker的容器管理

运行起来的镜像可以称为容器,1个容器相当于是1个进程.

docker container xxx   开头的指令一遍表示容器管理指令,部分指令container可以省略.
docker  ps     查看容器列表  -a 查看所有容器  -q只输出容器的id号可以用于批量删除容器
docker run 创建并运行容器
	例子:docker run  -d -it -p 80:80 nginx:latest
	-d 容器后台运行.
	-p 端口映射,外部或其他服务器想要访问容器内部的某个服务的端口. -p 外部用于访问的端口:容器内部服务的端口
	--name 指定容器的名字

docker create 创建容器 name
docker start   启动容器
docker  stop   停止容器
docker  restart 重启容器
docker  kill   强制停止容器
docker  rm     删除容器
docker rm -f `docker ps -a -q`   批量删除所有容器     -f强制删除容器
docker exec   进入正在运行的容器(分配一个新终端)
	例子: docker exec  -it 容器id/容器名字  /bin/bash(/bin/sh)
docker attach 进入正在运行的容器(使用相同的终端),偷偷离开的快捷键ctrl +p,ctrl +q
inspect
stats
top

1.案例:查看当前运行中的容器,查看下80端口是 否被占用,如果没有运行1个nginx容器使用80端口

docker container ps  == docker ps
docker container rm  == docker rm
#查看运行中的容器
[root@docker01 ~]# docker ps
CONTAINER ID   IMAGE     COMMAND   CREATED   STATUS    PORTS     NAMES
#查看所有的容器
[root@docker01 ~]# docker ps -a
CONTAINER ID   IMAGE     COMMAND   CREATED   STATUS    PORTS     NAMES
#运行一个容器
[root@docker01 ~]# docker run -d -p 80:80 --name "nginx_80" nginx:alpine
d59d41778f692b3f8cb3741b5a3b76326bd684288662337c89307d8d7ed6a640
[root@docker01 ~]# docker run -d -p 81:80 --name "nginx_81" nginx:alpine
ac6debefcc7b87eaa2b89acd16f6fe1a4e8cf3d1424861a54d2a17cfda4e0c07
[root@docker01 ~]# docker stop nginx_81
nginx_81
[root@docker01 ~]# docker ps
CONTAINER ID   IMAGE          COMMAND                  CREATED              STATUS              PORTS                               NAMES
d59d41778f69   nginx:alpine   "/docker-entrypoint.…"   About a minute ago   Up About a minute   0.0.0.0:80->80/tcp, :::80->80/tcp   nginx_80
[root@docker01 ~]# docker ps -a
CONTAINER ID   IMAGE          COMMAND                  CREATED              STATUS                      PORTS                               NAMES
ac6debefcc7b   nginx:alpine   "/docker-entrypoint.…"   26 seconds ago       Exited (0) 19 seconds ago                                       nginx_81
d59d41778f69   nginx:alpine   "/docker-entrypoint.…"   About a minute ago   Up About a minute           0.0.0.0:80->80/tcp, :::80->80/tcp   nginx_80

#删除容器
[root@docker01 ~]# docker rm nginx_81
nginx_81
[root@docker01 ~]# docker ps -a
CONTAINER ID   IMAGE          COMMAND                  CREATED         STATUS         PORTS                               NAMES
d59d41778f69   nginx:alpine   "/docker-entrypoint.…"   2 minutes ago   Up 2 minutes   0.0.0.0:80->80/tcp, :::80->80/tcp   nginx_80


注:如果容器运行中无法删除则使用rm -f强制删除.

2.创建centos容器并进入容器

[root@docker01 ~]# docker run -it --name "docker_centos" centos
Unable to find image 'centos:latest' locally
latest: Pulling from library/centos
a1d0c7532777: Pull complete 
Digest: sha256:a27fd8080b517143cbbbab9dfb7c8571c40d67d534bbdee55bd6c473f432b177
Status: Downloaded newer image for centos:latest
[root@3ea2c3d74cd8 /]# ls
bin  dev  etc  home  lib  lib64  lost+found  media  mnt  opt  proc  root  run  sbin  srv  sys  tmp  usr  var
[root@3ea2c3d74cd8 /]# 


-i 进入交互模式
-t 分配一个终端(运行命令解释器) /bin/bash 或 /bin/sh
-it 进入容器并有个命令行(终端).
好处运行容器的同时可以进入到容器中,缺点:退出容器则容器结束.

如果退出容器,那么容器状态会怎么样?

-it 运行容器,容器是一个系统.

容器退出后,容器关闭了.

[root@docker01 ~]# docker run -it --name "docker_centos" centos
Unable to find image 'centos:latest' locally
latest: Pulling from library/centos
a1d0c7532777: Pull complete 
Digest: sha256:a27fd8080b517143cbbbab9dfb7c8571c40d67d534bbdee55bd6c473f432b177
Status: Downloaded newer image for centos:latest
[root@3ea2c3d74cd8 /]# ls
bin  dev  etc  home  lib  lib64  lost+found  media  mnt  opt  proc  root  run  sbin  srv  sys  tmp  usr  var
[root@3ea2c3d74cd8 /]# exit  #退出
[root@docker01 ~]# docker ps -a
CONTAINER ID   IMAGE          COMMAND                  CREATED              STATUS                      PORTS                               NAMES
3ea2c3d74cd8   centos         "/bin/bash"              About a minute ago   `Exited (0) 21 seconds ago`                                       docker_centos   #容器关闭

温馨提示:

容器想要放在后台(-d)一直运行的话,那么容器运行对应初始命令,

必须夯住(阻塞/前台运行),否则容器就会退出.

前台运行
nginx -g 'daemon off;'          nginx前台运行.
/usr/sbin/php-fpm --nodaemonize php前台运行.
/usr/sbin/sshd -D               ssh前台运行.
java -jar xxx.jar               java前台运行.

3.案例:如何进入已经运行中的容器

[root@docker01 ~]# docker ps
CONTAINER ID   IMAGE          COMMAND                  CREATED         STATUS         PORTS                               NAMES
d59d41778f69   nginx:alpine   "/docker-entrypoint.…"   8 minutes ago   Up 8 minutes   0.0.0.0:80->80/tcp, :::80->80/tcp   nginx_80
[root@docker01 ~]# docker exec -it nginx_80 /bin/sh
/ # 

#2. 修改ngx首页文件内容
/ # echo test docker >/usr/share/nginx/html/index.html
/ # nginx -t 
/ # nginx -s reload  #重启nginx
#3. 浏览器测试
http://10.0.0.81

如何后台持续运行纯净系统的容器.

#通过-itd + 指定命令解释器持续运行
docker run -itd   --name docker_centos   centos /bin/bash

4. exec vs attach区别

docker container 指令 exec attach
共同点 连接到容器 连接到容器
区别 连接的时候创建终端 容器要有终端(容器进程中要有个/bin/bash 或/bin/sh) 只能连接到已有的终端中.
区别 不同的exec连接互不影响 共用,所有连接都一样.

5. docker run vs docker create,start,stop,restart

docker run背后
docker pull #如果镜像不存在.
docker create 创建容器.
docker start 启动容器.
docker stop 关闭容器. #向容器中的主进程,pid 1 进程发出信号(kill),关闭.
docker restart重启重启.

6. 如何传输文件到容器中

docker container cp == docker cp
目标
宿主机容器 上传 docker cp 路径或文件 容器:容器中目录
容器宿主机 下载 docker cp 容器:容器中目录 路径或文件
#保存百度的首页
[root@docker01 ~]# curl  -o index.html www.baidu.com
  % Total    % Received % Xferd  Average Speed   Time    Time     Time  Current
                                 Dload  Upload   Total   Spent    Left  Speed
100  2381  100  2381    0     0  56348      0 --:--:-- --:--:-- --:--:-- 56690
[root@docker01 ~]# ll
total 113964
-rw-------. 1 root root      1340 Jan  9 09:09 anaconda-ks.cfg
-rw-r--r--  1 root root 116684757 Mar  3 10:38 docker.tar.gz
-rw-r--r--  1 root root      2381 Mar  6 20:51 index.html
#上传到docker容器中
[root@docker01 ~]# docker cp index.html  nginx_80:/usr/share/nginx/html/index.html
Preparing to copy...
Copying to container - 0B
Copying to container - 0B
Copying to container - 512B
Copying to container - 2.893kB
Copying to container - 3.072kB
Copying to container - 3.584kB
Copying to container - 4.096kB
Successfully copied 4.096kB to nginx_80:/usr/share/nginx/html/index.html
#访问10.0.0.81测试

-a表示保存文件属性不变(uid,gid)

7. 查看容器信息与状态

#stats 查看所有运行中的容器的状态,如果要看所有加上-a选项.
#top 查看某一个容器的进程信息.
#inspect

docker container stats == docker stats 

[root@docker01 ~]# docker stats nginx_80

CONTAINER ID   NAME       CPU %     MEM USAGE / LIMIT     MEM %     NET I/O       BLOCK I/O     PIDS
d59d41778f69   nginx_80   0.00%     1.609MiB / 1.934GiB   0.08%     1.31kB / 0B   0B / 20.5kB   3

[root@docker01 ~]# docker top nginx_80
UID                 PID                 PPID                C                   STIME               TTY                 TIME                CMD

root                6337                6318                0                   20:34               ?                   00:00:00            nginx: master process nginx -g daemon off;

101                 6388                6337                0                   20:34               ?                   00:00:00            nginx: worker process

root                6852                6318                0                   20:44               pts/0               00:00:00            /bin/sh

8. 结束容器

docker stop关闭容器
docker rm删除容器
docker kill

[root@docker01 ~]# docker kill  -s 9 nginx_80
-s表示信号 -s 9 等于 kill -9 pid强制结束.

9. commit用于自定义镜像

使用流程:

  1. 运行服务镜像或系统镜像,启动后成为容器.
  2. 根据需求,对容器进行修改.
  3. 测试完成后.
  4. 最后通过commit命令把容器保存为镜像.
  5. 根据新生成的镜像创建容器并测试.
需求
基于ngx镜像创建容器
修改站点目录 /app/code/restart/ (default.conf)
上传代码,解压.
测试
commit
#创建容器
[root@docker01 ~]# docker run -d -p 80:80 --name "nginx_restart" nginx:alpine
cb6c6fb202f02dcea7e538c673802624baca1a2757780ae4164a0f5fd9a08f07
[root@docker01 ~]# docker ps
CONTAINER ID   IMAGE          COMMAND                  CREATED         STATUS        PORTS                               NAMES
cb6c6fb202f0   nginx:alpine   "/docker-entrypoint.…"   3 seconds ago   Up 1 second   0.0.0.0:80->80/tcp, :::80->80/tcp   nginx_restart
#进入容器
[root@docker01 ~]# docker exec -it nginx_restart /bin/sh
/ # 

#修改配置文件与准备环境
[root@docker01 ~]# docker exec -it nginx_restart /bin/sh
/ # vi /etc/nginx/conf.d/default.conf 
/ # cat /etc/nginx/conf.d/default.conf 
server {
  listen 80;
  server_name restart.oldboylinux.cn;
  root /app/code/restart;
  location / {
    index index.html;
  }
  
  location ~* \.css$ {
    root /app/code/restart/css;
  }

}
/ # mkdir -p /app/code/restart

#拷贝源码到容器
[root@docker01 ~]# docker cp restart-new.zip nginx_restart:/root/
[root@docker01 ~]# docker exec -it nginx_restart /bin/sh
/ # cd /root/
~ # unzip restart-new.zip -d /app/code/restart/
~ # cd /app/code/restart/
/app/code/restart # ls
restart-new
/app/code/restart # mv restart-new/* .
/app/code/restart # ls -l
total 32
-rw-r--r--    1 root     root          6234 Mar  6 13:02 condition_test.html
drwxrwxrwx    2 root     root            60 Mar  6 13:02 css
drwxrwxrwx    2 root     root           302 Mar  6 13:02 data
-rw-r--r--    1 root     root          3064 Mar  6 13:02 iconfont.ttf
-rw-r--r--    1 root     root          1960 Mar  6 13:02 iconfont.woff
-rw-r--r--    1 root     root          1532 Mar  6 13:02 iconfont.woff2
drwxrwxrwx    3 root     root            19 Mar  6 13:02 images
-rw-r--r--    1 root     root          3720 Mar  6 13:02 index.html
drwxrwxrwx    2 root     root            36 Mar  6 13:02 js
drwxrwxrwx    2 root     root            60 Mar  6 13:02 lib
-rw-r--r--    1 root     root          1147 Mar  6 13:02 manifest.json
drwxrwxrwx    2 root     root            23 Mar  6 13:02 public
drwxrwxrwx    2 root     root             6 Mar  6 13:02 restart-new
-rw-r--r--    1 root     root          3292 Mar  6 13:02 test.html
/app/code/restart # rm -rf restart-new/
/app/code/restart # nginx -t
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful
/app/code/restart # nginx -s reload
2023/03/06 13:03:41 [notice] 55#55: signal process started


[root@docker01 ~]# sysctl -p
net.ipv4.ip_forward = 1

#http://10.0.0.81/访问测试可以访问

#制造镜像
[root@docker01 ~]# docker commit nginx_restart nginx:alpine_restart
sha256:b0171f7d53c5e2afec15c14922994e85615645c722287bbc6b1f6252f9d3a7fd
[root@docker01 ~]# docker images
REPOSITORY   TAG              IMAGE ID       CREATED         SIZE
nginx        alpine_restart   b0171f7d53c5   3 seconds ago   47.4MB
#测试新的镜像
[root@docker01 ~]# docker run -d -p 81:80 --name "docker_restart_81" nginx:alpine_restart
ef05fe2968ded90c4595fe8a84787726677a6b6680f78fa508f4af755665628f
#测试http://10.0.0.81:81/可以正常访问

八、端口映射(docker run -p)

使用docker的时候 外界访问docker容器中的服务或端口,需要使用端口映射.本质类似于iptables防火墙的端口映射.

应用场景:

未来容器需要被外界访问(80端口).需要暴漏在外界一个端口.

用户通过端口访问容器中的某个端口.

实现方法:docker run通过-p选项实现.

本质是通过iptables nat规则实现的.nat表中创建了docker自定义的链.

1.端口映射的本质是什么?

添加了对应防火墙规则 iptables -t nat -A DOCKER ! -i docker0 -p tcp -m tcp dport 80-j DNAT todestination 172.17.0.10:80

开启内核转发功能(需要我们自己开启)

[root@docker01 ~]# iptables -nL -t nat
Chain PREROUTING (policy ACCEPT)
target     prot opt source               destination         
DOCKER     all  --  0.0.0.0/0            0.0.0.0/0            ADDRTYPE match dst-type LOCAL

Chain INPUT (policy ACCEPT)
target     prot opt source               destination         

Chain OUTPUT (policy ACCEPT)
target     prot opt source               destination         
DOCKER     all  --  0.0.0.0/0           !127.0.0.0/8          ADDRTYPE match dst-type LOCAL

Chain POSTROUTING (policy ACCEPT)
target     prot opt source               destination         
MASQUERADE  all  --  172.17.0.0/16        0.0.0.0/0           
MASQUERADE  tcp  --  172.17.0.2           172.17.0.2           tcp dpt:80
MASQUERADE  tcp  --  172.17.0.3           172.17.0.3           tcp dpt:80

Chain DOCKER (2 references)
target     prot opt source               destination         
RETURN     all  --  0.0.0.0/0            0.0.0.0/0           
DNAT       tcp  --  0.0.0.0/0            0.0.0.0/0            tcp dpt:80 to:172.17.0.2:80
DNAT       tcp  --  0.0.0.0/0            0.0.0.0/0            tcp dpt:81 to:172.17.0.3:80
#最后这两行

2.用户访问容器流程

image

3.端口映射案例

docker run
-p选项(小写字母P) 宿主机端口:容器中的端口 -p 80:80 -p 443:443
-p :容器中端口 -p :80 表示宿主机端口随机,很少用.
-p 端口范围:端口范围 -p 80-88:80-88

3.1 1对1端口映射

docker run -d -p 80:80 --name "nginx_80" nginx:alpine

3.2 映射多个端口

映射8080,8081,8082 到容器中容器中也是8080,8081,8082

docker run -d -p 80:80 -p 8080:8080 -p 8088:8088  nginx:alpine

docker run -d -p 8080-8088:8080-8088   nginx:alpine


[root@docker01 ~]# docker run -d -p 80:80 -p 8080:8080 -p 8088:8088  nginx:alpine
a4d95425644c6737375858729326f8e67f7cf894599a8365e9d712c293b94309
[root@docker01 ~]# docker ps -a
CONTAINER ID   IMAGE          COMMAND                  CREATED         STATUS         PORTS                      NAMES
a4d95425644c   nginx:alpine   "/docker-entrypoint.…"   6 seconds ago   Up 5 seconds   0.0.0.0:80->80/tcp, :::80->80/tcp, 0.0.0.0:8080->8080/tcp, :::8080->8080/tcp, 0.0.0.0:8088->8088/tcp, :::8088->8088/tcp   kind_cray
[root@docker01 ~]# docker port kind_cray
80/tcp -> 0.0.0.0:80
80/tcp -> [::]:80
8080/tcp -> 0.0.0.0:8080
8080/tcp -> [::]:8080
8088/tcp -> 0.0.0.0:8088
8088/tcp -> [::]:8088

3.3 ip绑定端口

显示用户只能通过宿主机的某个网卡连接这个端口.

安全防护作用.

[root@docker01 ~]# docker run -d --name "nginx_bind_ip"   -p 172.16.1.81:8090:80  nginx:alpine
827782514e7529d57eb40a1a56f3003d3cb7a3835f51499b61f1d1e0d0134851
[root@docker01 ~]# docker ps |grep nginx_bind_ip
827782514e75   nginx:alpine   "/docker-entrypoint.…"   22 seconds ago   Up 21 seconds   172.16.1.81:8090->80/tcp   nginx_bind_ip
#绑定ip

九、数据卷挂载

1. 概述

如何解决数据持久化问题?

数据卷(挂载),让数据永久保存在宿主机中.

2.案例:使用数据卷挂载index.html到容器中 的/usr/share/nginx/html/index.html

[root@docker01 ~]# mkdir -p /app/docker/code
[root@docker01 ~]# echo "docker_volumnt" >/app/docker/code/index.html
[root@docker01 ~]# cat /app/docker/code/index.html
docker_volumnt
[root@docker01 ~]# docker run -d -p 82:80 --name 'docker_volumnt'  \
> -v /app/docker/code/index.html:/usr/share/nginx/html/index.html \
> nginx:alpine 
de9cc9e9d2d2e94d028f906ce34d96cabb93a40e1d34a7f8ecad1e5d6297b1e7
[root@docker01 ~]# docker inspect docker_volumnt |jq .[].HostConfig.Binds
[
  "/app/docker/code/index.html:/usr/share/nginx/html/index.html"
]

#http://10.0.0.81:82/ 就会发现,页面显示的是属主机挂载的卷了

温馨提示:

注意:使用vi/vim/sed -i修改,需要重启下容器,因为对应文件inode变化,导致容器无法识别.

需要 docker restart docker_volumnt

3.挂载代码目录,配置文件目录

用数据卷挂载:代码目录.

用数据卷挂载:配置文件,配置文件目录.

用数据卷挂载:数据目录(数据库)

#拷贝代码
[root@docker01 ~]# mkdir -p /app/docker/restart/{conf,code}
[root@docker01 ~]# cd /app/docker/restart/code/
[root@docker01 /app/docker/restart/code]# cp ~/restart-new.zip .
[root@docker01 /app/docker/restart/code]# unzip restart-new.zip 
[root@docker01 /app/docker/restart/code]# mv restart-new/* .
[root@docker01 /app/docker/restart/code]# rm -rf restart-new
[root@docker01 /app/docker/restart/code]# rm -rf restart-new.zip 


#拷贝nginx配置文件
[root@docker01 /app/docker/restart/conf]# mkdir nginx
[root@docker01 /app/docker/restart/conf/nginx]# docker cp nginx_restart:/etc/nginx/nginx.conf .
Preparing to copy...
Successfully copied 2.56kB to /app/docker/restart/conf/nginx.
[root@docker01 /app/docker/restart/conf/nginx]# ll
total 4
-rw-r--r-- 1 root root 648 Dec 14 02:23 nginx.conf
[root@docker01 /app/docker/restart/conf/nginx]# cat conf.d/restart.cn.conf 
server {
  listen 80;
  server_name restart.cn;
  root /app/code/restart;
  location / {
    index index.html;
  }
  
  location ~* \.css$ {
     root /app/code/restart/css; 
  }
}

[root@docker01 /app/docker/restart/conf/nginx]# docker run -d -p 80:80 --name "restart_volume" \
> -v /app/docker/restart/conf/nginx/conf.d/:/etc/nginx/conf.d/ \
> -v /app/docker/restart/conf/nginx/nginx.conf:/etc/nginx/nginx.conf \
> -v /app/docker/restart/code/:/app/code/restart/ \
> nginx:alpine
374757d11e9605bbb0b63552545369743a240b2d27f113ac3f742f009b983508

#访问10.0.0.81可以访问到页面

4.创建数据卷

#创建数据卷
[root@docker01 ~]# docker volume create logdata
logdata
#查看数据卷
[root@docker01 ~]# docker volume ls
DRIVER    VOLUME NAME
local     logdata
[root@docker01 ~]# tree /var/lib/docker/volumes/logdata/
/var/lib/docker/volumes/logdata/
└── _data
#挂载数据卷
[root@docker01 ~]# docker run -d --name "vol_logdata" -p 82:80 -v logdata:/var/log/nginx nginx:alpine
6115ab08385f4efcb7b89036e083ebe3f0d8b269c86e2d2927f711665978defa
[root@docker01 ~]# ll /var/lib/docker/volumes/
total 24
brw------- 1 root root 253, 0 Mar  3 10:58 backingFsBlockDev
drwx-----x 3 root root     19 Mar  7 19:49 logdata
-rw------- 1 root root  32768 Mar  7 19:49 metadata.db

补充:

nginx容器的日志默认是输出到docker标准输出和标准错误输出的,而不是存放在文件中.

未来查看日志的时候,不用进入到容器,然后tail/less使用命令查看.

直接使用 docker logs 容器id或名字 就可以看日志. 相当于查看access.log或error.log

#相当于tail -f
[root@docker01 ~]# docker logs -f vol_logdata   
/docker-entrypoint.sh: /docker-entrypoint.d/ is not empty, will attempt to perform configuration
/docker-entrypoint.sh: Looking for shell scripts in /docker-entrypoint.d/
/docker-entrypoint.sh: Launching /docker-entrypoint.d/10-listen-on-ipv6-by-default.sh
10-listen-on-ipv6-by-default.sh: info: Getting the checksum of /etc/nginx/conf.d/default.conf
10-listen-on-ipv6-by-default.sh: info: Enabled listen on IPv6 in /etc/nginx/conf.d/default.conf
/docker-entrypoint.sh: Launching /docker-entrypoint.d/20-envsubst-on-templates.sh
/docker-entrypoint.sh: Launching /docker-entrypoint.d/30-tune-worker-processes.sh
/docker-entrypoint.sh: Configuration complete; ready for start up
2023/03/07 11:52:14 [notice] 1#1: using the "epoll" event method
2023/03/07 11:52:14 [notice] 1#1: nginx/1.23.3
2023/03/07 11:52:14 [notice] 1#1: built by gcc 12.2.1 20220924 (Alpine 12.2.1_git20220924-r4) 
2023/03/07 11:52:14 [notice] 1#1: OS: Linux 3.10.0-1160.el7.x86_64
2023/03/07 11:52:14 [notice] 1#1: getrlimit(RLIMIT_NOFILE): 1048576:1048576
2023/03/07 11:52:14 [notice] 1#1: start worker processes
2023/03/07 11:52:14 [notice] 1#1: start worker process 30
10.0.0.1 - - [07/Mar/2023:11:59:13 +0000] "GET / HTTP/1.1" 200 615 "-" "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/110.0.0.0 Safari/537.36" "-"

#如何让容器里的日志变成可以docker log查看
#进入容器
#把日志进行软链接到/dev/stdout
/var/log/nginx # ls -la
total 0
drwxr-xr-x    2 root     root            41 Mar  7 11:52 .
drwxr-xr-x    1 root     root            19 Feb 11 10:03 ..
lrwxrwxrwx    1 root     root            11 Feb 11 10:03 access.log -> /dev/stdout
lrwxrwxrwx    1 root     root            11 Feb 11 10:03 error.log -> /dev/stderr

ln -s /dev/stdout  /app/tools/tengine/logs/access.log  
访问日志 stdout标准输出
ln -s /dev/sdterr   /app/tools/tengine/logs/error.log

错误日志 stderr错误输出
只要有访问日志生成就会输出到屏幕,就可以通过docker logs 查看
logs -f 查看

5.随机卷,使用很少

docker run  -d  name "nginx_vol_logdatav2"  -p :80    -v :/var/log/nginx/ nginx:alpine
posted @ 2023-03-13 17:24  wh459086748  阅读(1140)  评论(2)    收藏  举报