基础篇

docker安装,卸载

一步安装

yum install -y yum-utils device-mapper-persistent-data lvm2 \
&& yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo \
&& yum makecache \
&& yum -y install docker-ce \
&& mkdir -p  /etc/docker/ \
&& echo -e '{\n  "registry-mirrors": ["https://x3n9jrcg.mirror.aliyuncs.com"]\n}' > /etc/docker/daemon.json \
&& systemctl daemon-reload && systemctl start docker && systemctl enable docker
  • 卸载旧版本(没有可跳过)

  • 需要的安装包

yum install -y yum-utils
  • 设置镜像仓库(使用阿里云)
yum-config-manager --add-repo \
    http://download.docker.com/linux/centos/docker-ce.repo   #外国网站
yum-config-manager --add-repo \
	http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo #阿里云
         
    Loaded plugins: fastestmirror
    adding repo from: http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
    grabbing file http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo to /etc/yum.repos.d/docker-ce.repo
    repo saved to /etc/yum.repos.d/docker-ce.repo
  • 新软件包的索引
yum makecache fast
    
    Loaded plugins: fastestmirror
    Loading mirror speeds from cached hostfile
     * base: mirrors.163.com
     * extras: mirrors.ustc.edu.cn
     * updates: mirrors.ustc.edu.cn
    base                                                                                          | 3.6 kB  00:00:00     
    docker-ce-stable                                                                              | 3.5 kB  00:00:00     
    extras                                                                                        | 2.9 kB  00:00:00     
    updates                                                                                       | 2.9 kB  00:00:00     
    (1/2): docker-ce-stable/7/x86_64/updateinfo                                                   |   55 B  00:00:00     
    (2/2): docker-ce-stable/7/x86_64/primary_db                                                   |  76 kB  00:00:00     
    Metadata Cache Created
  • 安装docker docker-ce(社区版)
yum install docker-ce docker-ce-cli containerd.io
    
    Dependency Updated:
      audit.x86_64 0:2.8.5-4.el7                           audit-libs.x86_64 0:2.8.5-4.el7                              
      libselinux.x86_64 0:2.5-15.el7                       libselinux-python.x86_64 0:2.5-15.el7                        
      libselinux-utils.x86_64 0:2.5-15.el7                 libsemanage.x86_64 0:2.5-14.el7                              
      libsepol.x86_64 0:2.5-10.el7                         policycoreutils.x86_64 0:2.5-34.el7                          
      selinux-policy.noarch 0:3.13.1-268.el7_9.2           selinux-policy-targeted.noarch 0:3.13.1-268.el7_9.2          
    
    Complete!
  • 启动docker
systemctl start docker
  • 使用docker version确保安装成功
docker version
    
    Client: Docker Engine - Community
     Version:           20.10.15
     API version:       1.41
     Go version:        go1.17.9
     Git commit:        fd82621
     Built:             Thu May  5 13:16:58 2022
     OS/Arch:           linux/amd64
     Context:           default
     Experimental:      true
    
    Server: Docker Engine - Community
     Engine:
      Version:          20.10.15
      API version:      1.41 (minimum version 1.12)
      Go version:       go1.17.9
      Git commit:       4433bf6
      Built:            Thu May  5 13:15:18 2022
      OS/Arch:          linux/amd64
      Experimental:     false
     containerd:
      Version:          1.6.4
      GitCommit:        212e8b6fa2f44b9c21b2798135fc6fb7c53efc16
     runc:
      Version:          1.1.1
      GitCommit:        v1.1.1-0-g52de29d
     docker-init:
      Version:          0.19.0
      GitCommit:        de40ad0
  • 启动hallo-world
docker run hello-world
    
    Unable to find image 'hello-world:latest' locally
    latest: Pulling from library/hello-world
    2db29710123e: Pull complete 
    Digest: sha256:10d7d58d5ebd2a652f4d93fdd86da8f265f5318c6a73cc5b6a9798ff6d2b2e67
    Status: Downloaded newer image for hello-world:latest
    
    Hello from Docker!
    This message shows that your installation appears to be working correctly.
    
    To generate this message, Docker took the following steps:
     1. The Docker client contacted the Docker daemon.
     2. The Docker daemon pulled the "hello-world" image from the Docker Hub.
        (amd64)
     3. The Docker daemon created a new container from that image which runs the
        executable that produces the output you are currently reading.
     4. The Docker daemon streamed that output to the Docker client, which sent it
        to your terminal.
    
    To try something more ambitious, you can run an Ubuntu container with:
     $ docker run -it ubuntu bash
    
    Share images, automate workflows, and more with a free Docker ID:
     https://hub.docker.com/
    
    For more examples and ideas, visit:
     https://docs.docker.com/get-started/
    
    证明安装成功
  • 查看镜像
docker images
    
    REPOSITORY    TAG       IMAGE ID       CREATED        SIZE
    hello-world   latest    feb5d9fea6a5   7 months ago   13.3kB
  • 卸载

    • 1.卸载依赖
    yum remove docker-ce docker-ce-cli containerd.io
  • 删除资源
rm -rf /var/lib/docker
      
    /var/lib/docker  docker的默认工作路径

基础命令

帮助命令

  • docker version #查看docker 版本信息

  • docker info #查看docker系统信息,包括镜像和容器的数量

  • docker 命令 --help #帮助命令

镜像命令

查看
[root@CentOS ~]# docker images
REPOSITORY    TAG       IMAGE ID       CREATED        SIZE
hello-world   latest    feb5d9fea6a5   6 months ago   13.3kB

#  解释
REPOSITORY        镜像的仓库源         
TAG               镜像的标签
IMAGE ID          镜像的id
CREATED           镜像的创建时间
SIZE              镜像的大小
#  可选项
-a , --all                # 列出所有镜像
-q , --quiet              # 只显示镜像id
搜索
  • 命令格式 :docker search 名字
[root@CentOS ~]# docker search mysql
  NAME                             DESCRIPTION                                     STARS     OFFICIAL   AUTOMATED
  mysql                            MySQL is a widely used, open-source relation…   12351     [OK]       
  mariadb                          MariaDB Server is a high performing open sou…   4754      [OK]       
  mysql/mysql-server               Optimized MySQL Server Docker images. Create…   916                  [OK]
  
  #可选项
  --filter=STARS=3000        #搜索出来的镜像就是STARS大于3000的
下载
  • 命令格式:docker pull [名字] [:tag]

  • 例如:docker pull mysql:5.7

[root@CentOS ~]# docker pull mysql
Using default tag: latest               #如果不加 tag,默认就是latest
latest: Pulling from library/mysql
f003217c5aae: Pull complete             #分层下载,docker iamge的核心 联合文件系统
65d94f01a09f: Pull complete 
43d78aaa6078: Pull complete 
a0f91ffbdf69: Pull complete 
59ee9e07e12f: Pull complete 
04d82978082c: Pull complete 
70f46ebb971a: Pull complete 
db6ea71d471d: Pull complete 
c2920c795b25: Pull complete 
26c3bdf75ff5: Pull complete 
9ec1f1f78b0e: Pull complete 
4607fa685ac6: Pull complete 
Digest: sha256:1c75ba7716c6f73fc106dacedfdcf13f934ea8c161c8b3b3e4618bcd5fbcf195 #签名
Status: Downloaded newer image for mysql:latest
docker.io/library/mysql:latest        #真实地址

#等价与它
docker pull mysql   
docker.io/library/mysql:latest  
删除
  • 命令格式:docker rmi 【名字或id】
[root@CentOS ~]# docker rmi -f  667ee8fb158e              #删除指定镜像
[root@CentOS ~]# docker rmi -f  容器id  容器id  容器id     #删除多个镜像       
[root@CentOS ~]# docker rmi -f  $(docker iamges -aq)      #删除全部镜像

容器命令

  • 说明:有了镜像才能创建容器,下载sentos系统测试
[root@CentOS ~]# docker pull centos
Using default tag: latest
latest: Pulling from library/centos
a1d0c7532777: Pull complete 
Digest: sha256:a27fd8080b517143cbbbab9dfb7c8571c40d67d534bbdee55bd6c473f432b177
Status: Downloaded newer image for centos:latest
docker.io/library/centos:latest
新建容器并启动
  • 命令格式:docker run [可选参数] iamge
  #参数说明
  --name="Name"     容器名字  用来区分容器
  -d                后台方式运行
  -it               使用交互方式运行,进入容器查看内容
  -p                指定容器端口   -p 8080:8080 
  (1)-p ip:主机端口:容器端口   (2)-p   主机端口:容器端口(常用) (3)-p  容器端口
  -P                随机指定端口
  • 测试,创建启动并进入容器
[root@CentOS ~]# docker run -it centos /bin/bash
WARNING: IPv4 forwarding is disabled. Networking will not work.
[root@32c10aad935b /]# ls         #查看容器内的centos,基础版本,很多命令是不完善!
bin  dev  etc  home  lib  lib64  lost+found  media  mnt  opt  proc  root  run  sbin  srv  sys  tmp  usr  var
[root@6537606d468c /]# exit        #从容器退回主机
exit
列出所有运行的容器
  • 命令格式:docker ps
[root@CentOS ~]# docker ps
CONTAINER ID   IMAGE     COMMAND   CREATED   STATUS    PORTS     NAMES
[root@CentOS ~]# docker ps -a
CONTAINER ID   IMAGE         COMMAND       CREATED         STATUS                          PORTS     NAMES
6537606d468c   centos        "/bin/bash"   5 minutes ago   Exited (0) About a minute ago             objective_lamport
32c10aad935b   centos        "/bin/bash"   6 minutes ago   Exited (127) 5 minutes ago                amazing_dirac
40553ff2206e   centos        "/bin/bash"   8 minutes ago   Exited (0) 7 minutes ago                  infallible_wing
7bf792cc2597   hello-world   "/hello"      9 days ago      Exited (0) 9 days ago                     admiring_bhabha


#可选参数
None                列出当前正在运行的容器
-a                  列出当前正在运行的容器+带出历史运行过的容器
-n=1                列出最近创建的一个容器
-n=?                列出最近创建的所有容器
-p                  只显示容器的编号
退出容器

exit 直接容器停止并退出

ctrl+P+Q 容器不停止退出

删除容器
docker  rm  容器id               #删除指定的容器,不能删除正在运行的容器,如果要强制删除 rm  -f
docker rm -f  $(docker  ps  -aq)          #删除所有容器
docker  ps  -a  -q  | xargs  docker rm    #删除所有容器
启动和停止容器
docker  start  容器id             #启动容器
docker  restart  容器id          #重启容器
docker   stop   容器id            #停止当前正在运行的容器
docker  kill  容器id                  #强制停止当前容器

常用命令

后台启动容器

命令格式:docker run -d 镜像名

[root@CentOS ~]# docker run -d centos
WARNING: IPv4 forwarding is disabled. Networking will not work.
202527a0e38696d3173571bc6783b04bf28727c03f6fdda1f4cd675aa628f992
[root@CentOS ~]# docker ps
CONTAINER ID   IMAGE     COMMAND   CREATED   STATUS    PORTS     NAMES

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

查看日志

命令各式:docker logs [可选参数] [容器id]

#自己编写一段shell脚本
[root@CentOS ~]# docker run -d centos /bin/bash -c "while true;do echo yangxiaobin;sleep 1;done"
WARNING: IPv4 forwarding is disabled. Networking will not work.
27fd2b95e71e3bd1290167c7566e7d40138d75e026a94ca613194f560e59b5f1

[root@CentOS ~]# docker ps
CONTAINER ID   IMAGE     COMMAND                  CREATED              STATUS              PORTS     NAMES
27fd2b95e71e   centos    "/bin/bash -c 'while…"   About a minute ago   Up About a minute             festive_shirley

#可选参数
-tf                             #显示日志
--tial  数字                     #显示日志条数

查看容器中进程信息

命令格式:docker top 容器id

[root@CentOS ~]# docker top d8f1b58c06fc
UID                 PID                 PPID                C                   STIME               TTY                 TIME                CMD
root                25925               25906               0                   01:17               pts/0               00:00:00            /bin/bash

查看镜像元数据

命令格式:docker inspect 镜像id

[root@CentOS ~]# docker inspect centos
[
    {
        "Id": "sha256:5d0da3dc976460b72c77d94c8a1ad043720b0416bfc16c52c45d4847e53fadb6",
        "RepoTags": [
            "centos:latest"
        ],
        "RepoDigests": [
            "centos@sha256:a27fd8080b517143cbbbab9dfb7c8571c40d67d534bbdee55bd6c473f432b177"
        ],
        "Parent": "",
        "Comment": "",
        "Created": "2021-09-15T18:20:05.184694267Z",
        "Container": "9bf8a9e2ddff4c0d76a587c40239679f29c863a967f23abf7a5babb6c2121bf1",
        "ContainerConfig": {
            "Hostname": "9bf8a9e2ddff",
            "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",
                "#(nop) ",
                "CMD [\"/bin/bash\"]"
            ],
            "Image": "sha256:f5b050f177fd426be8fe998a8ecf3fb1858d7e26dff4080b29a327d1bd5ba422",
            "Volumes": null,
            "WorkingDir": "",
            "Entrypoint": null,
            "OnBuild": null,
            "Labels": {
                "org.label-schema.build-date": "20210915",
                "org.label-schema.license": "GPLv2",
                "org.label-schema.name": "CentOS Base Image",
                "org.label-schema.schema-version": "1.0",
                "org.label-schema.vendor": "CentOS"
            }
        },
        "DockerVersion": "20.10.7",
        "Author": "",
        "Config": {
            "Hostname": "",
            "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/bash"
            ],
            "Image": "sha256:f5b050f177fd426be8fe998a8ecf3fb1858d7e26dff4080b29a327d1bd5ba422",
            "Volumes": null,
            "WorkingDir": "",
            "Entrypoint": null,
            "OnBuild": null,
            "Labels": {
                "org.label-schema.build-date": "20210915",
                "org.label-schema.license": "GPLv2",
                "org.label-schema.name": "CentOS Base Image",
                "org.label-schema.schema-version": "1.0",
                "org.label-schema.vendor": "CentOS"
            }
        },
        "Architecture": "amd64",
        "Os": "linux",
        "Size": 231268856,
        "VirtualSize": 231268856,
        "GraphDriver": {
            "Data": {
                "MergedDir": "/var/lib/docker/overlay2/9170879ea41e2400b308a75ec2f104b39325453732d908e87ad4775d16370c25/merged",
                "UpperDir": "/var/lib/docker/overlay2/9170879ea41e2400b308a75ec2f104b39325453732d908e87ad4775d16370c25/diff",
                "WorkDir": "/var/lib/docker/overlay2/9170879ea41e2400b308a75ec2f104b39325453732d908e87ad4775d16370c25/work"
            },
            "Name": "overlay2"
        },
        "RootFS": {
            "Type": "layers",
            "Layers": [
                "sha256:74ddd0ec08fa43d09f32636ba91a0a3053b02cb4627c35051aff89f853606b59"
            ]
        },
        "Metadata": {
            "LastTagTime": "0001-01-01T00:00:00Z"
        }
    }
]

进入当前正在运行的容器

我们通常容器都是使用后台方式运行的,需要进入容器,修改一些配置

  • 方法一:docker exec -it 容器id
[root@CentOS ~]# docker ps 
CONTAINER ID   IMAGE     COMMAND       CREATED         STATUS         PORTS     NAMES
d8f1b58c06fc   centos    "/bin/bash"   7 minutes ago   Up 7 minutes             crazy_payne
[root@CentOS ~]# docker exec -it d8f1b58c06fc /bin/bash
[root@d8f1b58c06fc /]# ls
bin  dev  etc  home  lib  lib64  lost+found  media  mnt  opt  proc  root  run  sbin  srv  sys  tmp  usr  var
[root@d8f1b58c06fc /]# ps -ef
UID         PID   PPID  C STIME TTY          TIME CMD
root          1      0  0 05:17 pts/0    00:00:00 /bin/bash
root         15      0  0 05:25 pts/1    00:00:00 /bin/bash
root         30     15  0 05:25 pts/1    00:00:00 ps -ef
  • 方法二 :docker attach 容器id
[root@d8f1b58c06fc /]# docker attach d8f1b58c06fc
bash: docker: command not found          #正在执行当前的代码…
  • docker exec # 进入容器后开启一个新的终端,可以在里面操作(常用)

    docker attach # 进入容器正在执行的终端,不会启动新的进程

从容器内拷贝文件到主机上

命令格式:docker cp 容器id:容器路径 目的主机路径

#查看当前主机目录
[root@CentOS home]# ls
centos

#进入容器内部
[root@CentOS home]# docker ps
CONTAINER ID   IMAGE     COMMAND       CREATED          STATUS          PORTS     NAMES
d8f1b58c06fc   centos    "/bin/bash"   20 minutes ago   Up 20 minutes             crazy_payne
[root@CentOS home]# docker attach d8f1b58c06fc
[root@d8f1b58c06fc /]# 

#查看并创建文件
[root@d8f1b58c06fc /]# cd /home 
[root@d8f1b58c06fc home]# ls
[root@d8f1b58c06fc home]# touch yangxiaobin.txt
[root@d8f1b58c06fc home]# exit
exit
[root@CentOS home]# docker ps                     #查看正在运行的容器
CONTAINER ID   IMAGE     COMMAND   CREATED   STATUS    PORTS     NAMES
[root@CentOS home]# docker ps -a                  #查看历史运行过的容器  
CONTAINER ID   IMAGE     COMMAND       CREATED          STATUS                      PORTS     NAMES
d8f1b58c06fc   centos    "/bin/bash"   25 minutes ago   Exited (0) 27 seconds ago             crazy_payne

#将文件拷贝出来主机上
[root@CentOS home]# docker cp d8f1b58c06fc:/home/yangxiaobin.txt /home
[root@CentOS home]# ls
centos  yangxiaobin.txt

#拷贝是一个手动过程,使用  -v  卷技术,可以实现自动同步  /home  /home

commit提交镜像

docker commit 提交容器称为一个新的副本
docker commit -m='提交的描述信息' -a='作者' 容器id 目标镜像名:[tag]

docker commit -m='info' -a='yangxiaobin' c6e5d001104a centos:2.0

容器数据卷

容器之间数据共享,Docker容器产生的数据,同步到本地

目录的挂载,将容器目录挂载到Linux上面

容器间也可以数据共享

方式一:直接使用命令 -v

docker -it -v 主机目录:容器内目录

#测试
docker run -it -v /home/ceshi:/home centos /bin/bash
docker inspect 96243a8f4398

外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传

两边互相修改数据都可进行数据更新

部署MySQL

#下载
docker pull mysql

#启动
#官方测试    docker run --name some-mysql -v /my/custom:/etc/mysql/conf.d -e MYSQL_ROOT_PASSWORD=my-secret-pw -d mysql:tag

docker run -d -p 3310:3306 -v /home/docker/mysql/conf:/etc/mysql/conf.d -v /home/docker/mysql/data/:/var/lib/mysql -e MYSQL_ROOT_PASSWORD=123456 --name mysql01 mysql

-d 后台运行
-e 环境配置
--name 容器名字
# 启动成功之后使用本地sqlyog来连接测试    3310

部署nginx

网页无法获取尝试进入容器开启nginx服务

service nginx start

实践

构建自定义镜像

commit

docker commit -a="作者" -m="提交的描述信息" 容器id 目标镜像名:版本

dockerfile

mkdir nginx-image
cd nginx-image/
wget http://nginx.org/download/nginx-1.18.0.tar.gz
mkdir wwwroot
vi wwwroot/index.html
<html>
    <head>
        <title>Nginx</title>
    </head>
    <body>
        <span>Test Nginx Image</span>
    </body>
</html>

创建dockerfile

FROM centos:centos7
MAINTAINER "yangxiaobin"
ADD nginx-1.18.0.tar.gz /opt
WORKDIR /opt/nginx-1.18.0
RUN yum -y install gcc pcre-devel openssl-devel make \
    && groupadd www-data && useradd -s /sbin/nologin -g www-data www-data \
    && ./configure \
    --prefix=/usr/local/nginx \
    --conf-path=/etc/nginx/nginx.conf \
    --user=www-data \
    --group=www-data \
    --with-pcre \
    --with-http_v2_module \
    --with-http_ssl_module \
    --with-http_realip_module \
    --with-http_addition_module \
    --with-http_sub_module \
    --with-http_dav_module \
    --with-http_flv_module \
    --with-http_mp4_module \
    --with-http_gunzip_module \
    --with-http_gzip_static_module \
    --with-http_random_index_module \
    --with-http_secure_link_module \
    --with-http_stub_status_module \
    --with-http_auth_request_module \
    --with-mail \
    --with-mail_ssl_module \
    --with-file-aio \
    --with-http_v2_module \
    --with-threads \
    --with-stream \
    --with-stream_ssl_module && make && make install
VOLUME  ["/usr/local/nginx/html"]
ENV PATH /usr/local/nginx/sbin:$PATH 
EXPOSE 80
ENTRYPOINT ["nginx"]       
CMD ["-g","daemon off;"]
docker build ./ -t nginx:v2

检查

容器操作

复制文件到容器

echo "数据" > index.html
docker cp index.html mynginx:/usr/share/nginx/html

打包容器成tar文件

docker export -o mynginx.tar mynginx

将tar文件新建一个镜像

docker import mynginx.tar nginx:v1.0

查看容器与宿主机端口映射

docker port mynginx

资源管理

限制容器内存

docker run -itd --name=busybox -m 512m busybox

限制CPU份额

docker run -itd -c 1000 --name test01 progrium/stress --cpu 4
#查看
top

占满一颗CPU

docker run -itd --cpuset-cpus=1 --name cputest agileek/cpuset-test

磁盘I/O

  • 读写带宽

    docker run -itd --name centos01 --blkio-weight=800 centos
    
  • 读写效率

    docker run -itd --name busybox --device-read-bps /dev/sda:30MB busybox
    

数据卷

创建数据卷

docker run -itd --name=mynginx -p 80:80 -v myweb:/usr/share/nginx/html nginx
docker inspect mynginx
"Mounts":[]

创建数据卷容器,容器的数据共享

创建数据卷
docker run -it --name=cintainer -v /share:/mnt centos:7
cd /mnt/
echo mycentos > test.txt
exit

cd /share/
ls
cat test.txt
数据共享
docker run -it --name=test1 --volumes-from container centos:7
cd /mnt
ls
cat test.txt

删除container容器,test1容器与宿主机数据还在

备份和回复

创建数据卷
docker run -it --name=data-volume -v /var/volume centos:7
ls
echo hello > /var/volume/test.txt
exit
备份
docker run --rm --volumes-from data-volume -v /root/backup:/backup centos:7 \ 
tar cvf /backup/backup.tar /var/volume
ls
cd backup/
ls
tar -xf backup.tar
ls
cat var/volume/test.txt
删除容器备份文件后恢复
docker run -it --rm --volumes-from data-volume -v /root/backup:/backup centos:7 \
tar xvf /backup/backup.tar -C

docker网络

[root@host1~]# vi  /etc/docker/daemon.json
{
  "registry-mirrors": ["https://x3n9jrcg.mirror.aliyuncs.com"],
 "bip": "192.168.2.1/24"
}

[root@host1~]# systemctl restart docker
  • 使用同样的方法,调整host2主机上的docker网络,将docker0的IP地址调整为192.168.3.1/24

  • 添加互通路由

    [root@host1~]# ip route add 192.168.3.0/24 via 192.168.1.8
    [root@host1~]# route –n
    
    
    [root@host2~]# ip route add 192.168.2.0/24 via 192.168.1.7
    [root@host2~]#route -n
    
  • 配置防火墙的NAT规则

    [root@host1~]# iptables -t nat -I PREROUTING -s 192.168.2.0/24 -d 192.168.3.0/24 -j DNAT --to 192.168.1.8
    
    [root@host2~]# iptables -t nat -I PREROUTING -s 192.168.3.0/24 -d 192.168.2.0/24 -j DNAT --to 192.168.1.7
    

Flannel网络

[root@host1~]# yum -y install etcd flannel
配置etcd
[root@host1~]# vi  /etc/etcd/etcd.conf 
ETCD_DATA_DIR="/var/lib/etcd/default.etcd"
ETCD_LISTEN_CLIENT_URLS="http://0.0.0.0:2379"
ETCD_NAME="default"
ETCD_ADVERTISE_CLIENT_URLS="http://0.0.0.0:2379"

# 启动 etcd 服务
[root@host1~]# systemctl start etcd && systemctl enable etcd

# flannel 配置
[root@host1~]# vi /etc/sysconfig/flanneld
FLANNEL_ETCD_ENDPOINTS="http://192.168.100.10:2379"
FLANNEL_ETCD_PREFIX="/atomic.io/network"

# 在 etcd 中添加网段
[root@host1~]# etcdctl mk /atomic.io/network/config '{"Network":"172.20.0.0/16"}'

# 查看etcd是否生效
[root@host1~]# etcdctl get /atomic.io/network/config
{"Network":"172.20.0.0/16"}

# 启动 flannel 服务
[root@host1~]# systemctl start flanneld && systemctl enable flanneld
[root@host2~]# yum -y install flannel 

# flannel 配置
[root@host2~]#vi /etc/sysconfig/flanneld
FLANNEL_ETCD_ENDPOINTS="http://192.168.100.10:2379"
FLANNEL_ETCD_PREFIX="/atomic.io/network"

# 启动 flannel 服务
[root@host2~]# systemctl start flanneld && systemctl enable flanneld
  • 配置docker使用

    [root@host1~]# cat /run/flannel/subnet.env
    FLANNEL_NETWORK=172.20.0.0/16
    FLANNEL_SUBNET=172.20.24.1/24
    FLANNEL_MTU=1472
    FLANNEL_IPMASQ=false
    
    [root@host1~]# vi /etc/docker/daemon.json
    {
      "registry-mirrors": ["https://x3n9jrcg.mirror.aliyuncs.com"],
      "bip": "172.20.24.1/24",
      "mtu": 1472
    }
    
    
    
    [root@host2~]# cat /run/flannel/subnet.env
    FLANNEL_NETWORK=172.20.0.0/16
    FLANNEL_SUBNET=172.20.32.1/24
    FLANNEL_MTU=1472
    FLANNEL_IPMASQ=false
    
    [root@host2~]# vi /etc/docker/daemon.json
    {
      "registry-mirrors": ["https://x3n9jrcg.mirror.aliyuncs.com"],
      "bip": "172.20.32.1/24",
      "mtu": 1472
    }
    
    
    两个主机均重启 docker服务、修改防火墙规则
    # systemctl restart docker
    #iptables -P INPUT ACCEPT
    #iptables -P FORWARD ACCEPT
    #iptables -F
    

私有仓库

  • 生成证书

    mkdir -p /opt/docker/registry/certs
    openssl req -newkey rsa:4096 -nodes -sha256 -keyout /opt/docker/registry/certs/domain.key -x509 -days 365 -out /opt/docker/registry/certs/domain.crt
    
    解析域名
    vi /etc/hosts
    cat /etc/hosts
    127.0.0.1   localhost localhost.localdomain localhost4 localhost4.localdomain4
    ::1         localhost localhost.localdomain localhost6 localhost6.localdomain6
    192.168.100.10 registry.docker.com
    
    
    mkdir /etc/docker/certs.d
    cd /etc/docker/certs.d/
    mkdir registry.docker.com:5000
    cp -r -p /opt/docker/registry/certs/domain.crt /etc/docker/certs.d/registry.docker.com:5000/ca.crt
    ls registry.docker.com\:5000/
    
    
    
    [root@host1 ~]# vi /etc/docker/daemon.json 
    [root@host1 ~]# cat /etc/docker/daemon.json 
    {
      "registry-mirrors": ["https://x3n9jrcg.mirror.aliyuncs.com"],
      "insecure-registries": ["registry.docker.com:5000"]
    }
    systemctl daemon-reload
    systemctl restart docker
    
    mkdir /opt/docker/registry/auth
    yum install -y httpd
    htpasswd -Bbn yxb yxbpassword > /opt/docker/registry/auth/htpasswd
    cd /opt/docker/registry/auth/
    ls
    
    
    
    docker run -d -it \
    --name registry-auth \
    -p 5000:5000 \
    -v /opt/docker/registry/auth/:/auth \
    -e "REGISTRY_AUTH=htpasswd" \
    -e "REGISTRY_AUTH_HTPASSWD_REALM=Registry Realm" \
    -e REGISTRY_AUTH_HTPASSWD_PATH=/auth/htpasswd \
    -v /opt/docker/registry/certs:/certs \
    -e REGISTRY_HTTP_TLS_CERTIFICATE=/certs/domain.crt \
    -e REGISTRY_HTTP_TLS_KEY=/certs/domain.key registry
    

可视化私有仓库

[root@host1 ~]# vi /etc/docker/daemon.json 
[root@host1 ~]# cat /etc/docker/daemon.json 
{
  "registry-mirrors": ["https://x3n9jrcg.mirror.aliyuncs.com"],
  "insecure-registries": ["192.168.100.10:5000"]
}


docker pull registry
docker run -itd -p 5000:5000 \
--restart=always \
--name registry registry


docker pull hyper/docker-registry-web
docker run -itd \
--restart=always \
-p 8080:8080 \
--name registry-web \
-- link registry \
-e REGISTRY_URL=http://192.168.100.10:5000/v2 \
-e REGISTRY_NAME=192.168.100.10:5000 hyper/docker-registry-web


#测试
docker pull centos
docker tag centos 192.168.100.10:5000/centos
docker push 192.168.100.10:5000/centos

可视化管理容器

vi /usr/local/bin/scope
#!/bin/sh

set -eu

ARGS="$*"
SCRIPT_VERSION="1.13.2"
if [ "$SCRIPT_VERSION" = "(unreleased version)" ]; then
    IMAGE_VERSION=latest
else
    IMAGE_VERSION="$SCRIPT_VERSION"
fi
IMAGE_VERSION=${VERSION:-$IMAGE_VERSION}
DOCKERHUB_USER=${DOCKERHUB_USER:-weaveworks}
SCOPE_IMAGE_NAME="$DOCKERHUB_USER/scope"
SCOPE_IMAGE="$SCOPE_IMAGE_NAME:$IMAGE_VERSION"
# Careful: it's easy to operate on (e.g. stop) the wrong scope instance
# when SCOPE{_APP,}_CONTAINER_NAME values differ between runs. Handle
# with care.
SCOPE_CONTAINER_NAME="${SCOPE_CONTAINER_NAME:-weavescope}"
SCOPE_APP_CONTAINER_NAME="${SCOPE_APP_CONTAINER_NAME:-weavescope-app}"
IP_REGEXP="[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}\\.[0-9]{1,3}"
IP_ADDR_CMD="find /sys/class/net -type l | xargs -n1 basename | grep -vE 'docker|veth|lo' | \
    xargs -n1 ip addr show | grep inet | awk '{ print \$2 }' | grep -oE '$IP_REGEXP'"
LISTENING_IP_ADDR_CMD="for I in \$( $IP_ADDR_CMD ); do if curl -m 1 -s \${I}:4040 > /dev/null ; then echo \${I}; fi; done"
WEAVESCOPE_DOCKER_ARGS=${WEAVESCOPE_DOCKER_ARGS:-}

# When docker daemon is running with User Namespace enabled, this tool will run into errors:
#  "Privileged mode is incompatible with user namespaces" for `docker run --privileged`
#  "Cannot share the host's network namespace when user namespaces are enabled" for `docker run --net=host`
# To avoid above errors, use `--userns=host` option to let container use host User Namespace.
# This option(saved in $USERNS_HOST) will be inserted ONLY IF docker support `--userns` option.
USERNS_HOST=""
docker run --help | grep -q -- --userns && USERNS_HOST="--userns=host"

usage() {
    name=$(basename "$0")
    cat >&2 <<-EOF
		Usage:
		$name launch {OPTIONS} {PEERS} - Launch Scope
		$name stop                     - Stop Scope
		$name command                  - Print the docker command used to start Scope
		$name help                     - Print usage info
		$name version                  - Print version info

		PEERS are of the form HOST[:PORT]
		HOST may be an ip or hostname.
		PORT defaults to 4040.

		Launch options:
	EOF
    docker run --rm --entrypoint=/home/weave/scope "$SCOPE_IMAGE" -h >&2
}

usage_and_die() {
    usage
    exit 1
}

[ $# -gt 0 ] || usage_and_die
COMMAND=$1
shift 1

check_docker_access() {

    # Extract socket path
    DOCKER_SOCK_FILE=""
    if [ -z "${DOCKER_HOST+x}" ]; then
        DOCKER_SOCK_FILE="/var/run/docker.sock"
    else
        WITHOUT_PREFIX="${DOCKER_HOST#unix://}"
        if [ "$WITHOUT_PREFIX" != "$DOCKER_HOST" ]; then
            DOCKER_SOCK_FILE="$WITHOUT_PREFIX"
        fi
    fi

    # shellcheck disable=SC2166
    if [ \( -n "$DOCKER_SOCK_FILE" \) -a \( ! -w "$DOCKER_SOCK_FILE" \) ]; then
        echo "ERROR: cannot write to docker socket: $DOCKER_SOCK_FILE" >&2
        echo "change socket permissions or try using sudo" >&2
        exit 1
    fi
}

# - The image embeds the weave script & Docker 1.13.1 client (mimicking a 1.10 client)
# - Weave needs 1.10.0 now (image pulling changes)
MIN_DOCKER_VERSION=1.10.0

check_docker_version() {
    if ! DOCKER_VERSION=$(docker -v | sed -n 's%^Docker version \([0-9]\{1,\}\.[0-9]\{1,\}\.[0-9]\{1,\}\).*$%\1%p') \
        || [ -z "$DOCKER_VERSION" ]; then
        echo "ERROR: Unable to parse docker version" >&2
        exit 1
    fi

    DOCKER_VERSION_MAJOR=$(echo "$DOCKER_VERSION" | cut -d. -f 1)
    DOCKER_VERSION_MINOR=$(echo "$DOCKER_VERSION" | cut -d. -f 2)
    DOCKER_VERSION_PATCH=$(echo "$DOCKER_VERSION" | cut -d. -f 3)

    MIN_DOCKER_VERSION_MAJOR=$(echo "$MIN_DOCKER_VERSION" | cut -d. -f 1)
    MIN_DOCKER_VERSION_MINOR=$(echo "$MIN_DOCKER_VERSION" | cut -d. -f 2)
    MIN_DOCKER_VERSION_PATCH=$(echo "$MIN_DOCKER_VERSION" | cut -d. -f 3)

    # shellcheck disable=SC2166
    if [ \( "$DOCKER_VERSION_MAJOR" -lt "$MIN_DOCKER_VERSION_MAJOR" \) -o \
        \( "$DOCKER_VERSION_MAJOR" -eq "$MIN_DOCKER_VERSION_MAJOR" -a \
        \( "$DOCKER_VERSION_MINOR" -lt "$MIN_DOCKER_VERSION_MINOR" -o \
        \( "$DOCKER_VERSION_MINOR" -eq "$MIN_DOCKER_VERSION_MINOR" -a \
        \( "$DOCKER_VERSION_PATCH" -lt "$MIN_DOCKER_VERSION_PATCH" \) \) \) \) ]; then
        echo "ERROR: scope requires Docker version $MIN_DOCKER_VERSION or later; you are running $DOCKER_VERSION" >&2
        exit 1
    fi
}

check_probe_only() {
    echo "${ARGS}" | grep -q -E -e "--no-app|--service-token|--probe-only"
}

check_listen_address_arg() {
    echo "${ARGS}" | grep -q -E -e "--app\\.http\\.address"
}

check_docker_for_mac() {
    [ "$(uname)" = "Darwin" ] \
        && [ -S /var/run/docker.sock ] \
        && [ ! "${DOCKER_HOST+x}" = x ] \
        && [ "${HOME+x}" = x ] \
        && [ -d "${HOME}/Library/Containers/com.docker.docker/Data" ]
}

# Check that a container named $1 with image $2 is not running
check_not_running() {
    case $(docker inspect --format='{{.State.Running}} {{.Config.Image}}' "$1" 2>/dev/null) in
        "true $2")
            echo "$1 is already running." >&2
            exit 1
            ;;
        "true $2:"*)
            echo "$1 is already running." >&2
            exit 1
            ;;
        "false $2")
            docker rm "$1" >/dev/null
            ;;
        "false $2:"*)
            docker rm "$1" >/dev/null
            ;;
        true*)
            echo "Found another running container named '$1'. Aborting." >&2
            exit 1
            ;;
        false*)
            echo "Found another container named '$1'. Aborting." >&2
            exit 1
            ;;
    esac
}

check_plugins_dir() {
    # If plugins dir exists for Docker containers then we will mount it
    # (the context for Docker might be different to that for this script, e.g. when using Docker for Mac)
    if docker run $USERNS_HOST --rm --entrypoint=/bin/sh \
        -v /var/run:/var/run \
        "$SCOPE_IMAGE" -c "test -d /var/run/scope/plugins"; then
        PLUGINS_DIR_EXISTS=true
    fi
}

docker_args() {
    echo --privileged $USERNS_HOST --net=host --pid=host \
        -v /var/run/docker.sock:/var/run/docker.sock \
        -v /sys/kernel/debug:/sys/kernel/debug \
        -e CHECKPOINT_DISABLE
    # shellcheck disable=SC2039
    [ -n "${PLUGINS_DIR_EXISTS:-}" ] && echo -v /var/run/scope/plugins:/var/run/scope/plugins
}

launch_command() {
    # shellcheck disable=SC2046,SC2086
    echo docker run -d --name="$SCOPE_CONTAINER_NAME" $(docker_args) \
        $WEAVESCOPE_DOCKER_ARGS "$SCOPE_IMAGE" --probe.docker=true
}

launch_docker4mac_app_command() {
    # shellcheck disable=SC2086
    echo docker run -d --name="$SCOPE_APP_CONTAINER_NAME" \
        -e CHECKPOINT_DISABLE \
        -p 0.0.0.0:4040:4040 \
        $WEAVESCOPE_DOCKER_ARGS "$SCOPE_IMAGE" --no-probe
}

launch() {
    check_not_running "$SCOPE_CONTAINER_NAME" "$SCOPE_IMAGE_NAME"
    docker rm -f "$SCOPE_CONTAINER_NAME" >/dev/null 2>&1 || true
    $(launch_command) "$@"
    echo "Scope probe started"
}

print_app_endpoints() {
    HOST_SUFFIX=""
    if [ -n "${DOCKER_HOST+x}" ]; then
        DOCKER_HOSTNAME=$(run_in_scope_container hostname)
        HOST_SUFFIX=" of host $DOCKER_HOSTNAME"
    fi
    echo "Weave Scope is listening at the following URL(s)${HOST_SUFFIX}:" >&2
    for ip in "$@"; do
        echo "  * http://$ip:4040/" >&2
    done
}

dry_run() {
    # Do a dry run of scope in the foreground, so it can parse args etc
    # avoiding the entrypoint script in the process.
    # shellcheck disable=SC2046
    docker run --rm --entrypoint=/home/weave/scope $(docker_args) "$SCOPE_IMAGE" --dry-run "$@"
}

run_in_scope_container() {
    docker run --rm $USERNS_HOST --net=host --entrypoint /bin/sh "$SCOPE_IMAGE" -c "$1"
}

# Wait for the scope app to start listening on localhost:4040
wait_for_http() {
    for seconds in $(seq 5); do
        if run_in_scope_container "curl -m 1 -s localhost:4040" >/dev/null; then
            break
        fi
        sleep 1
    done
    if [ "$seconds" -eq 5 ]; then
        echo "The Scope App is not responding. Consult the container logs for further details."
        exit 1
    fi
}

check_docker_access
check_docker_version

case "$COMMAND" in
    command)
        # Most systems should have printf, but the %q specifier isn't mandated by posix
        # and can't be guaranteed. Since this is mainly a cosmetic output and the alternative
        # is not making any attempt to do escaping at all, we might as well try.
        # shellcheck disable=SC2039
        quoted=$(printf '%q ' "$@" 2>/dev/null || true)
        # printf %q behaves oddly with zero args (it acts as though it received one empty arg)
        # so we ignore that case.
        if [ -z "$quoted" ] || [ $# -eq 0 ]; then
            quoted="$*"
        fi
        echo "$(launch_command) $quoted"
        ;;

    version)
        docker run --rm --entrypoint=/home/weave/scope "$SCOPE_IMAGE" --mode=version
        ;;

    -h | help | -help | --help)
        usage
        ;;

    launch)
        dry_run "$@"
        check_plugins_dir
        if check_docker_for_mac; then
            if check_probe_only; then
                launch "$@"
                exit
            fi
            # Docker for Mac (as of beta9) does not ship vmnet driver and
            # thereby only access container ports via a tunnel, preventing
            # access to host ports of the VM.
            # - https://github.com/weaveworks/scope/issues/1411
            # - https://forums.docker.com/t/ports-in-host-network-namespace-are-not-accessible/10789
            if check_listen_address_arg; then
                echo "--app.http.address argument not supported on Docker for Mac" >&2
                exit 1
            fi
            check_not_running "$SCOPE_APP_CONTAINER_NAME" "$SCOPE_IMAGE_NAME"
            check_not_running "$SCOPE_CONTAINER_NAME" "$SCOPE_IMAGE_NAME"
            docker rm -f "$SCOPE_APP_CONTAINER_NAME" >/dev/null 2>&1 || true
            CONTAINER=$($(launch_docker4mac_app_command) "$@")
            echo "Scope probe started"
            app_ip=$(docker inspect -f '{{.NetworkSettings.IPAddress}}' "${CONTAINER}")
            docker rm -f "$SCOPE_CONTAINER_NAME" >/dev/null 2>&1 || true
            # shellcheck disable=SC2091
            CONTAINER=$($(launch_command) --no-app "$@" "${app_ip}:4040")
            print_app_endpoints "localhost"
            exit
        fi
        launch "$@"
        if ! check_probe_only; then
            if check_listen_address_arg; then
                echo "Weave Scope is listening at the address specified with --app.http.address" >&2
            else
                wait_for_http
                IP_ADDRS=$(run_in_scope_container "$LISTENING_IP_ADDR_CMD")
                # shellcheck disable=SC2086
                print_app_endpoints $IP_ADDRS
            fi
        fi
        ;;

    stop)
        [ $# -eq 0 ] || usage_and_die
        if docker inspect "$SCOPE_CONTAINER_NAME" >/dev/null 2>&1; then
            docker stop "$SCOPE_CONTAINER_NAME" >/dev/null
        fi
        if check_docker_for_mac; then
            if docker inspect "$SCOPE_APP_CONTAINER_NAME" >/dev/null 2>&1; then
                docker stop "$SCOPE_APP_CONTAINER_NAME" >/dev/null
            fi
        fi
        ;;

    *)
        echo "Unknown scope command '$COMMAND'" >&2
        usage_and_die
        ;;

esac

给权限

chmod a+x /usr/local/bin/scope
scope launch
Logo

码道开发者社区,聚焦华为云码道 CodeArts 代码智能体,沉淀 Agent、Skill、鸿蒙开发实战内容,供开发者查阅资料、交流技术、分享工程实践

更多推荐