写点什么

docker 基础

作者:小麦
  • 2021 年 11 月 11 日
  • 本文字数:16213 字

    阅读完需:约 53 分钟

基础

常用命令

安装启动 docker


sudo yum install -y yum-utils sudo yum-config-manager \ --add-repo \ https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
sudo sed -i 's/download.docker.com/mirrors.aliyun.com\/docker-ce/g' /etc/yum.repos.d/docker-ce.repo
sudo yum install docker-ce docker-ce-cli containerd.iosystemctl enable docker # docker开机启动
systemctl stop firewalld && systemctl disable firewalld # 关闭防火墙systemctl restart docker # 关闭防火墙后重启docker,如果不重启则docker的ip包转发功能无法使用。即使防火墙关了,docker会调用没和模块netfilter增加规则,所以能看到防火墙规则iptables -L -n #多了docker的一些路由
复制代码


具体文档https://yeasy.gitbook.io/docker_practice/install/centos

设置镜像加速

sudo mkdir -p /etc/docker sudo tee /etc/docker/daemon.json <<-'EOF' { "registry-mirrors": ["https://0jcr2954.mirror.aliyuncs.com"] } EOFsudo systemctl daemon-reload sudo systemctl restart docker
复制代码

镜像操作

docker images  #显示镜像docker  search tomcat  #搜索镜像docker  pull  tomcat  # 拉取镜像docker pull mysql:5.7    # 下载指定版本docker rmi hello-world #删除镜像docker rmi -f  bf7334 #删除镜像(bf7镜像id)docker rmi -f $(docker images -aq) # 删除所有镜像docker load -i tar包名称  # 加载 某个镜像
复制代码

容器启动停止

docker  run  -it  tomcat # -i: 交互式操作。-t: 终端。docker  run  -it  tomcat:latest  /bin/bash   # 启动 镜像名tomcat, tag为latest的镜像Exit #  容器停止并退出
docker run --rm -v /var/run/docker.sock:/var/run/docker.sock assaflavie/runlike apollo-configservice # 查看正在运行容器apollo-configservice的启动命令ctrl+P+Q #容器不停止退出docker run -d --name tomcat01 -p 8088:8080 tomcat # -d 指定容器的运行分离模式(后台) --name 启动的时候执行实例名称为tomcat01docker rename tomcat1 tomcat2 # 吧tomcat1改成tomcat2docker start b750bbbcfd88 # b750 容器id;使用 docker start 启动一个已停止的容器;docker stop b750bbbcfd88 # b750 容器id;使用 docker stop停止容器;docker kill b750bbbcfd88 # b750 容器id;强制停止docker rm -f 1e560fca3906 # 删除容器docker ps -a # 查看所有容器,包括已停止的容器docker ps # 查看当前运行的容器docker logs 实例id # 查看日志docker run --restart=always -itd --name 容器名 镜像 /bin/bash # 容器开机启动docker update --restart=always 容器名 # 更改重启策略,改为开机启动docker run -it --cpuset -cpus 0,1 -m 128m centos # 启动centos镜像,限制只能再cpu0 和cpu1上跑,且内存最大不超过128m[root@localhost ~]# docker ps CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES70062327fc72 apollo-portal "/apollo-portal/scri…" 2 years ago Up 4 weeks 0.0.0.0:8070->8070/tcp apollo-portal808793d179ee apollo-adminservice "/apollo-adminservic…" 2 years ago Up 4 weeks 0.0.0.0:8090->8090/tcp apollo-adminservice7feade55a442 apollo-configservice "/apollo-configservi…" 2 years ago Up 4 weeks 0.0.0.0:8080->8080/tcp apollo-configservice89f85b83a29b mysql:5.7.19 "docker-entrypoint.s…" 2 years ago Up 4 weeks 0.0.0.0:13306->3306/tcp mysql
docker exec -it b750bbbcfd88 /bin/sh #进入在运行的容器中执行命令,开启一个新的终端docker attach b750bbbcfd88 #进入正在执行的终端,不会启动新的进程docker run --name mysql-go -e MYSQL_ROOT_PASSWORD=my-secret-pw -d mysql:5.7 # 启动mysql带密码
复制代码

日志 &进程 &镜像元数据 &监控

docker logs -f -t --tail 20  83f60d01e043  # 83f容器id;查看容器日志docker top 83f60d01e043    # 查看docker容器内的进程信息;docker inspect 83f60d01e043      # 查看镜像元数据docker stats  # 查看容器占用cpu 内存情况
复制代码

拷贝

docker cp  容器id:容器内路径    目的主机路径  #吧容器内的文件拷贝到宿主机
复制代码


ADD 和 COPY 的区别 ADD 指令的功能是将主机构建环境(上下文)目录中的文件和目录、以及一个 URL 标记的文件 拷贝到镜像中。其格式是: ADD 源路径 目标路径如果源文件是个归档文件(压缩文件),则 docker 会自动帮解压 ADD /foo.tar.gz /tmp/上述指令会使 foo.tar.gz 压缩文件解压到容器的/tmp 目录。URL 下载和解压特性不能一起使用。任何压缩文件通过 URL 拷贝,都不会自动解压。目前 ADD 指令有点让人迷惑,有时候解压文件,有时候不解压文件,如果你想拷贝一个压缩文件,你会以为地解压。如果文件是某种不能识别的压缩文件,如果你想解压,你又会意外地复制它。这种解释似乎是 ADD 尝试做的太多了,让用户有些疑惑。很明显,没人想要打破向后兼容性。所以决定新增一个行为更加明确的指令。COPY 和 ADD 相似,但是功能少一些。在 Docker 1.0 发布时候,包括了新指令 COPY。不像是 ADD,COPY 更加直接了当,只复制文件或者目录到容器里。COPY 不支持 URL,也不会特别对待压缩文件。Docker 团队的建议是在大多数情况下使用 COPY。拷贝文件的原则:使用 COPY(除非你明确你需要 ADD)

Commit 提交

docker commit -a="mairongcong" -m="随便加了一个文件 webapps"  248541cf6089 tomcat008:1.0 # 提交容器新的版本镜像
复制代码

数据卷挂载

docker run -it -v /home/testmai:/home tomcat   /bin/bash   # 挂载;为了容器的持久化和同步操作;容器之间数据共享;吧容器内的/home 目录挂到宿主机(物理机)上的/home/testmai 目录上,实现文件同步;双向绑定,反过来同理 docker run -d -p 3310:3306 -v /home/mysql/conf:/etc/mysql/conf.d -v /home/mysql/data:/var/lib/mysql -e MYSQL_ROOT_PASSWORD=123456 --name mysql02 mysql:5.7#mysql 数据卷挂载
复制代码

DockerFile

编写 dockerfile 文件


FROM centosMAINTAINER mairongcong<rcmai@qq.com>ENV MYPATH /usr/localWORKDIR $MYPATHRUN yum -y install vim RUN yum -y install net-toolsEXPOSE 80CMD echo $MYPATHCMD echo 'end------'CMD /bin/bash
复制代码


#执行编译命令


docker build  -f mydockerfile  -t mycentos:0.1 . 
复制代码


#查看是否构建成功




docker images[root@VM_0_17_centos dockerfile]# docker imagesREPOSITORY TAG IMAGE ID CREATED SIZEmycentos 0.1 c1d5e43eaa55 3 minutes ago 291MB
复制代码


#运行


docker run -it mycentos:0.1 
复制代码


#查看镜像的构建过程


docker history   c1d5e43eaa55
复制代码


#CMD 命令和 ENTRYPOINT 区别


FROM centosCMD  ["ls","-a"]# CMD 命令一般的镜像都会提供容器启动时的默认命令,但是有些场景中用户并不想执行默认的命令。用户可以通过命令行参数的方式覆盖 CMD 指令提供的默认命令。比如通过下面命令创建的镜像:FROM ubuntuCMD [ "top" ]在启动容器时我们通过命令行指定参数 ps aux 覆盖默认的 top 命令:Docker  run  --rm  test1  ps  aux 
复制代码

自制 tomcat 镜像

  • dockerfile


FROM centosMAINTAINER mairongcong<rcmai@qq.com>COPY readme.txt /usr/local/readme.txtADD jdk-8u271-linux-x64.tar.gz   /usr/local/ADD  apache-tomcat-9.0.41.tar.gz /usr/local/RUN  yum -y install vimENV MYPATH  /usr/localWORKDIR  $MYPATHENV JAVA_HOME /usr/local/jdk1.8.0_271ENV CLASS_PATH $JAVA_HOME/lib/dt.jar:$JAVA_HOME/lib/tools.jarENV CATALINA_HOME /usr/local/apache-tomcat-9.0.41ENV CATALINA_BASH /usr/local/apache-tomcat-9.0.41ENV PATH  $PATH:$JAVA_HOME/bin:$CATALINA_HOME/lib:$CATALINA_HOME/binEXPOSE 8080 CMD /usr/local/apache-tomcat-9.0.41/bin/startup.sh && tail -F /usr/local/apache-tomcat-9.0.41/logs/catalina.out
复制代码


  • 查看 tomcat 镜像


docker  images [root@VM_0_17_centos dockerfile]# docker imagesREPOSITORY      TAG       IMAGE ID       CREATED          SIZEmytomcat        latest    dbfc7c2b1185   12 minutes ago   639MB
复制代码


  • 启动 tomcat 容器


docker run  -d -p 9090:8080 --name maitomcat -v /home/mairongcong/build/tomcat/test:/usr/local/apache-tomcat-9.0.41/webapps/test -v/home/mairongcong/build/tomcat/tomcatlogs/:/usr/local/apache-tomcat-9.0.41/logs  mytomcat
复制代码


  • ADD 和 COPY 的区别


ADD 指令的功能是将主机构建环境(上下文)目录中的文件和目录、以及一个 URL 标记的文件 拷贝到镜像中。其格式是: ADD 源路径 目标路径如果源文件是个归档文件(压缩文件),则 docker 会自动帮解压 ADD /foo.tar.gz /tmp/上述指令会使 foo.tar.gz 压缩文件解压到容器的/tmp 目录。URL 下载和解压特性不能一起使用。任何压缩文件通过 URL 拷贝,都不会自动解压。目前 ADD 指令有点让人迷惑,有时候解压文件,有时候不解压文件,如果你想拷贝一个压缩文件,你会以为地解压。如果文件是某种不能识别的压缩文件,如果你想解压,你又会意外地复制它。


这种解释似乎是 ADD 尝试做的太多了,让用户有些疑惑。很明显,没人想要打破向后兼容性。所以决定新增一个行为更加明确的指令。COPY 和 ADD 相似,但是功能少一些。在 Docker 1.0 发布时候,包括了新指令 COPY。不像是 ADD,COPY 更加直接了当,只复制文件或者目录到容器里。COPY 不支持 URL,也不会特别对待压缩文件。Docker 团队的建议是在大多数情况下使用 COPY。拷贝文件的原则:使用 COPY(除非你明确你需要 ADD)


  • RUN、CMD 和 ENTRYPOINTD 区别


从根本上说, ENTRYPOINT 和 CMD 都是让用户指定一个可执行程序, 这个可执行程序在 container 启动后自动启动. 实际上, 如果你想让自己制作的镜像自动运行程序(不需要在 docker run 后面添加命令行指定运行的命令), 你必须在 Dockerfile 里面, 使用 ENTRYPOINT 或者 CMD 命令比如执行运行一个没有调用 ENTRYPOINT 或者 CMD 的 docker 镜像, 一定返回错误 $ docker run alpineFATA[0000] Error response from daemon: No command specified 大部分 Linu 发行版的基础镜像里面调用 CMD 命令, 指定容器启动后执行/bin/sh 或/bin/bash. 这样镜像启动默认进入交互式的 shell



译注: 3 个不同的 Linux 镜像(ubuntu, busybox, debian)都在 Dockerfile 的最后调用 CMD '/bin/bash'启动 Linux 发行版的基础 container 后, 默认调用 shell 程序, 符合大多数人的习惯.但是, 作为开发者, 你希望在 docker 镜像启动后, 自动运行其他程序. 所以, 你需要用 CMD 或者 ENTRYPOINT 命令显式地指定具体的命令.


  • 三者的区别,另一种解释:


RUN、CMD 和 ENTRYPOINT 这三个 Dockerfile 指令看上去很类似,很容易混淆。本节将通过实践详细讨论它们的区别。简单的说:RUN 执行命令并创建新的镜像层,RUN 经常用于安装软件包。CMD 设置容器启动后默认执行的命令及其参数,但 CMD 能够被 docker run 后面跟的命令行参数替换。ENTRYPOINT 配置容器启动时运行的命令。


Shell 和 Exec 格式我们可用两种方式指定 RUN、CMD 和 ENTRYPOINT 要运行的命令:Shell 格式和 Exec 格式,二者在使用上有细微的区别。Shell 格式<instruction> <command>例如:RUN apt-get install python3  CMD echo "Hello world"  ENTRYPOINT echo "Hello world" 当指令执行时,shell 格式底层会调用/bin/sh -c <command> 。例如下面的 Dockerfile 片段:ENV name Cloud Man  ENTRYPOINT echo "Hello, name"] 运行容器将输出:Hello, name"] 运行容器将输出:Hello, Cloud Man CMD 和 ENTRYPOINT 推荐使用 Exec 格式,因为指令可读性更强,更容易理解。RUN 则两种格式都可以。


下面看看 CMD 是如何工作的。Dockerfile 片段如下:CMD echo "Hello world" 运行容器 docker run -it [image]将输出:Hello world 但当后面加上一个命令,比如 docker run -it [image] /bin/bash,CMD 会被忽略掉,命令 bash 将被执行:root@10a32dc7d3d3:/#


ENTRYPOINT 看上去与 CMD 很像,它们都可以指定要执行的命令及其参数。不同的地方在于 ENTRYPOINT 参数不会被忽略,一定会被执行,即使运行 docker run 时指定了其他命令。


重点 ENTRYPOINT 的 Exec 格式用于设置要执行的命令及其参数,同时可通过 CMD 提供额外的参数。ENTRYPOINT 中的参数始终会被使用,而 CMD 的额外参数可以在容器启动时动态替换掉。比如下面的 Dockerfile 片段:ENTRYPOINT ["/bin/echo", "Hello"]CMD ["world"] 当容器通过 docker run -it [image] 启动时,输出为:Hello world 而如果通过 docker run -it [image] CloudMan 启动,则输出为:Hello CloudMan 参考文章 [https://www.jianshu.com/p/f0a0f6a43907]

Push 发布到 dockerHub

https://hub.docker.com/ # 注册账号docker  login username   #登录docker tag  dbfc7c2b1185    mairongcong/mytomcat:1.0 # 打标签docker push mairongcong/mytomcat:1.0   #提交镜像
复制代码

Push 发布到阿里云

https://cr.console.aliyun.com/cn-hangzhou/instances/repositories # 创建命名空间https://cr.console.aliyun.com/cn-hangzhou/instances/repositories   #创建镜像仓库docker tag  dbfc7c2b1185    mairongcong/mytomcat:1.0 # 打标签docker push mairongcong/mytomcat:1.0   #提交镜像
复制代码

Save  & Load

docker save -o my_tomcat_v3.tar mytomcat    # 将指定镜像保存成 tar 归档文件docker save  本地镜像名:镜像标签 | gzip  > 导出的镜像名 # 压缩后的镜像docker load < my_tomcat_v3.tar  # 导入使用 docker save 命令导出的镜像;
复制代码

网络 evth-pair

[root@VM_0_17_centos WEB-INF]# ip addr  # 宿主机查看 网卡情况,有了一个docker0的网卡3: docker0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default     link/ether 02:42:6a:49:63:63 brd ff:ff:ff:ff:ff:ff    inet 172.17.0.1/16 brd 172.17.255.255 scope global docker0   [root@VM_0_17_centos ]# docker ps # 查看已有容器CONTAINER ID   IMAGE       COMMAND                  CREATED        STATUS        PORTS                               NAMES4845a637cb1e   mytomcat    "/bin/sh -c '/usr/lo…"   41 hours ago   Up 41 hours   0.0.0.0:9090->8080/tcp              maitomcat3[root@VM_0_17_centos WEB-INF]# docker exec -it  maitomcat3 ip addr  #查看容器内的网络地址ip  addr ;每启动一个docker容器,docker就会给docker容器分配一个ip,我们只要安装了docker,就会有一个网卡docker0 ,是桥接模式,使用了evth-pair 技术1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00    inet 127.0.0.1/8 scope host lo       valid_lft forever preferred_lft forever96: eth0@if97: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default     link/ether 02:42:ac:11:00:05 brd ff:ff:ff:ff:ff:ff link-netnsid 0    inet 172.17.0.5/16 brd 172.17.255.255 scope global eth0       valid_lft forever preferred_lft forever[root@VM_0_17_centos WEB-INF]# docker run -d --name mytomcat04 dbfc7c2b1185#再启动一个容器[root@VM_0_17_centos WEB-INF]# docker exec -it 0b30c016ed6f ip addr #查看多了一对网卡98 99  ,这些容器带来的网卡,都是一对一对的,就是evth-pair 技术,一端连着协议,一端彼此相连,有了这个特性,evth-pair充当桥梁,连接各种虚拟网络设备,docker之间的容器连接,都是使用了evth-pair 技术1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00    inet 127.0.0.1/8 scope host lo       valid_lft forever preferred_lft forever98: eth0@if99: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue state UP group default     link/ether 02:42:ac:11:00:06 brd ff:ff:ff:ff:ff:ff link-netnsid 0    inet 172.17.0.6/16 brd 172.17.255.255 scope global eth0       valid_lft forever preferred_lft forever[root@VM_0_17_centos WEB-INF]# ip addr99: veth8faa9cc@if98: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc noqueue master docker0 state UP group default link/ether 3e:e2:7b:fe:99:de brd ff:ff:ff:ff:ff:ff link-netnsid 4    inet6 fe80::3ce2:7bff:fefe:99de/64 scope link        valid_lft forever preferred_lft forever[root@VM_0_17_centos ]# docker exec -it  maitomcat3 ping  172.17.0.6 #容器之间是可以ping通的; tomcat1 和tomcat2是公用的同一个路由器Docker0,所有的容器再不指定网络的情况下,都是docker0路由的,docker会给我们的容器分配一个默认的可用ip; 但是该命令无法支持高可用,只能具体ping ip ,不能ping 容器名称
复制代码



Link(不再建议使用)

  • 缺点:无法 ping 通容器名


root@VM_0_17_centos ]# docker exec -it  maitomcat3 ping  mytomcat04 # 无法ping通容器名ping: mytomcat04: Name or service not known[root@VM_0_17_centos ]# docker run -d -P --name maitomcat5  --link mytomcat04  mytomcat #启动容器时通过 --link 来解决对应的网络问题d680bb22ed412f93b031f5314be9950642b8a17d5fb9c5719c55c1840caf64b6[root@VM_0_17_centos ]# docker exec -it  maitomcat5 ping mytomcat04PING mytomcat04 (172.17.0.6) 56(84) bytes of data.64 bytes from mytomcat04 (172.17.0.6): icmp_seq=1 ttl=64 time=0.075 ms64 bytes from mytomcat04 (172.17.0.6): icmp_seq=2 ttl=64 time=0.043 ms# link的原理就是在host中添加别名,吧ip 和 容器名做了一个映射
复制代码

自定义网络

  • 优点自定义网络其实也是 bridge 模式,只不过两个容器之间可以通过名字来进行网络通信

  • 查看所有的 docker 网络模式 1、bridge:bridge 之使用默认网桥,搭桥的方式连接各个容器网络 (默认都使用桥接模式)bridge 各个容器之间只能通过 ip 地址来互相访问,如果 ip 修改了,则无法通信。因此需要使用引用,或者一个 name 的方式来通信比较好。 docker0 问题,他不支持容器名链接访问。2、bridge 之使用自定义网桥 3、host 模式 4、container 模式 5、None 模式

  • 5 种模式详细说明基于对 net namespace 的控制,docker 可以为在容器创建隔离的网络环境,在隔离的网络环境下,容器具有完全独立的网络栈,与宿主机隔离,也可以使容器共享主机或者其他容器的网络命名空间,基本可以满足开发者在各种场景下的需要


按 docker 官方的说法,docker 容器的网络有五种模式:1)bridge 模式,--net=bridge(默认)这是 dokcer 网络的默认设置,为容器创建独立的网络命名空间,容器具有独立的网卡等所有单独的网络栈,是最常用的使用方式。在 docker run 启动容器的时候,如果不加--net 参数,就默认采用这种网络模式。安装完 docker,系统会自动添加一个供 docker 使用的网桥 docker0,我们创建一个新的容器时,容器通过 DHCP 获取一个与 docker0 同网段的 IP 地址,并默认连接到 docker0 网桥,以此实现容器与宿主机的网络互通。


2)host 模式,--net=host 这个模式下创建出来的容器,直接使用容器宿主机的网络命名空间。将不拥有自己独立的 Network Namespace,即没有独立的网络环境。它使用宿主机的 ip 和端口。


3)none 模式,--net=none 为容器创建独立网络命名空间,但不为它做任何网络配置,容器中只有 lo,用户可以在此基础上,对容器网络做任意定制。这个模式下,dokcer 不为容器进行任何网络配置。需要我们自己为容器添加网卡,配置 IP。因此,若想使用 pipework 配置 docker 容器的 ip 地址,必须要在 none 模式下才可以。


4)其他容器模式(即 container 模式),--net=container:NAME_or_ID 与 host 模式类似,只是容器将与指定的容器共享网络命名空间。这个模式就是指定一个已有的容器,共享该容器的 IP 和端口。除了网络方面两个容器共享,其他的如文件系统,进程等还是隔离开的。


5)用户自定义:docker 1.9 版本以后新增的特性,允许容器使用第三方的网络实现或者创建单独的 bridge 网络,提供网络隔离能力。


[root@VM_0_17_centos /]# docker network ls  #查看所有的docker网络NETWORK ID     NAME      DRIVER    SCOPE479307d3d0a1   bridge    bridge    localcfc57d39c114   host      host      localb076eb847244   none      null      local
复制代码


  • 创建自定义网络


root@freeaihub:~# docker network create custom_networkb88fa50e25a2bc92517f353cf5c76e71a29eabc0ec19c3f8e60bbc8b8ad03340# 或者如下 
[root@VM_0_17_centos /]# docker network create --driver bridge --subnet 192.168.0.0/16 --gateway 192.168.0.1 mynet #创建自定义网络94bab7ee5dee508e1198189d8a0b873d9482a7dc6c393ea4ce6c5d636012ed9e[root@VM_0_17_centos /]# docker network lsNETWORK ID NAME DRIVER SCOPE479307d3d0a1 bridge bridge localcfc57d39c114 host host local94bab7ee5dee mynet bridge local[root@VM_0_17_centos /]# docker network inspect mynet[ { "Name": "mynet", "Id": "94bab7ee5dee508e1198189d8a0b873d9482a7dc6c393ea4ce6c5d636012ed9e", "Created": "2021-01-07T10:44:41.230831857+08:00", "Scope": "local", "Driver": "bridge", "EnableIPv6": false, "IPAM": { "Driver": "default", "Options": {}, "Config": [ { "Subnet": "192.168.0.0/16", "Gateway": "192.168.0.1" } ] }, "Internal": false, "Attachable": false, "Ingress": false, "ConfigFrom": { "Network": "" }, "ConfigOnly": false, "Containers": {}, "Options": {}, "Labels": {} }]
复制代码


  • 启动一个容器 指定 mynet 为独立的网络


@freeaihub:~# docker run  -it --name bbox05  busyboxUnable to find image 'busybox:latest' locallylatest: Pulling from library/busybox8ec32b265e94: Pull complete # 或者
[root@VM_0_17_centos /]# docker run -d -P --name mytomcat06-net --net mynet mytomcat efd84b353fdf77b6bf626c1a71103e7ef65c02982647c645c34237361d84c873[root@VM_0_17_centos /]# docker run -d -P --name mytomcat07-net --net mynet mytomcat #启动另一个容器e2f310e336b0e98457ec0371e2cc9cf6c86e7f430d2e509f2882b1e678f39f71[root@VM_0_17_centos /]# docker network inspect mynet #查看网络情况,发现新增了[ { ... ... "Containers": { "e2f310e336b0e98457ec0371e2cc9cf6c86e7f430d2e509f2882b1e678f39f71": { "Name": "mytomcat07-net", "EndpointID": "a15a172ce252af01bff6367d17a8a187f2152c83e4e483fbabd19e68694987ed", "MacAddress": "02:42:c0:a8:00:03", "IPv4Address": "192.168.0.3/16", "IPv6Address": "" }, "efd84b353fdf77b6bf626c1a71103e7ef65c02982647c645c34237361d84c873": { "Name": "mytomcat06-net", "EndpointID": "fa34004e05ad5fe8b1637e844a504731cdb9ab87384a7439082edfbdd2c7e05b", "MacAddress": "02:42:c0:a8:00:02", "IPv4Address": "192.168.0.2/16", "IPv6Address": "" } }, }]
复制代码


[root@VM_0_17_centos /]# docker exec -it mytomcat07-net ping mytomcat06-net # 通过自定义网络的方式,发现不需要使用--link ,两个容器之间可以直接通过容器名 ping 通了;推荐使用这种自定义的方式使用,比如一个 redis 集群,那么就是一个网络,mysql 集群 也是一个独立的网络,两个网络之间互相隔离。PING mytomcat06-net (192.168.0.2) 56(84) bytes of data.64 bytes from mytomcat06-net.mynet (192.168.0.2): icmp_seq=1 ttl=64 time=0.037 ms64 bytes from mytomcat06-net.mynet (192.168.0.2): icmp_seq=2 ttl=64 time=0.046 ms 如果两个不同的网络之间,需要互通怎么办呢?测试两个不同网络的容器互通 root@VM_0_17_centos /]# docker network connect mynet mytomcat04 #把 mytomcat04 加入到 mynet 网络中,就可以实现 mytomcat04 可以访问 mynet 网络的所在容器了[root@VM_0_17_centos /]# docker network inspect mynet[{"Name": "mynet","Id": "94bab7ee5dee508e1198189d8a0b873d9482a7dc6c393ea4ce6c5d636012ed9e","Created": "2021-01-07T10:44:41.230831857+08:00","Scope": "local","Driver": "bridge","EnableIPv6": false,"IPAM": {"Driver": "default","Options": {},"Config": [{"Subnet": "192.168.0.0/16","Gateway": "192.168.0.1"}]},"Internal": false,"Attachable": false,"Ingress": false,"ConfigFrom": {"Network": ""},"ConfigOnly": false,"Containers": {"0b30c016ed6fc5a278bd8a3fad4794c068b0ccd237f81d6b53af28d380d0af66": {"Name": "mytomcat04","EndpointID": "b33d960f70ba94a631969e507ddf42d1aed2b12331b4cfa427fbb221cdf3fd20","MacAddress": "02:42:c0:a8:00:04","IPv4Address": "192.168.0.4/16","IPv6Address": ""},"e2f310e336b0e98457ec0371e2cc9cf6c86e7f430d2e509f2882b1e678f39f71": {"Name": "mytomcat07-net","EndpointID": "a15a172ce252af01bff6367d17a8a187f2152c83e4e483fbabd19e68694987ed","MacAddress": "02:42:c0:a8:00:03","IPv4Address": "192.168.0.3/16","IPv6Address": ""},"efd84b353fdf77b6bf626c1a71103e7ef65c02982647c645c34237361d84c873": {"Name": "mytomcat06-net","EndpointID": "fa34004e05ad5fe8b1637e844a504731cdb9ab87384a7439082edfbdd2c7e05b","MacAddress": "02:42:c0:a8:00:02","IPv4Address": "192.168.0.2/16","IPv6Address": ""}},"Options": {},"Labels": {}}][root@VM_0_17_centos /]# docker exec -it mytomcat04 ping mytomcat07-net #测试验证确实可以互通 PING mytomcat07-net (192.168.0.3) 56(84) bytes of data.64 bytes from mytomcat07-net.mynet (192.168.0.3): icmp_seq=1 ttl=64 time=0.039 ms64 bytes from mytomcat07-net.mynet (192.168.0.3): icmp_seq=2 ttl=64 time=0.049 ms[root@VM_0_17_centos /]# docker exec -it mytomcat07-net ping mytomcat04 # 测试验证可以互通 PING mytomcat04 (192.168.0.4) 56(84) bytes of data.64 bytes from mytomcat04.mynet (192.168.0.4): icmp_seq=1 ttl=64 time=0.050 ms#结论:假设要跨网络互相访问,需要使用 以上命令 docker network connect mynet mytomcat04

nginx 搭建

root@VM_0_17_centos /]# docker pull nginx#拉取镜像[root@control-plane nginx]# docker run --name mynginx -p 80:80   -d nginx:latest # 启动镜像
[root@control-plane nginx]# ##导入的配置文件目录[root@control-plane nginx]# docker cp mynginx:/etc/nginx/conf.d /data/application/workflow/nginx[root@control-plane nginx]# docker cp mynginx:/etc/nginx/nginx.conf /data/application/workflow/nginx/nginx.conf[root@control-plane nginx]# docker cp mynginx:/usr/share/nginx/html /data/application/workflow/nginx/[root@control-plane nginx]# docker cp mynginx:/var/log/nginx /data/application/workflow/nginx/log
# 删除同名容器[root@control-plane nginx]# docker rm -f mynginxmynginx
#启动容器,并挂载对应目录[root@control-plane nginx]# docker run -d --name mynginx -p 6061:80 -v /data/application/workflow/nginx/conf.d:/etc/nginx/conf.d -v /data/application/workflow/nginx/nginx.conf:/etc/nginx/nginx.conf -v /data/application/workflow/nginx/html:/usr/share/nginx/html -v /data/application/workflow/nginx/log:/var/log/nginx nginx:latest
复制代码

nginx 搭建问题记录

记得如果应用程序搭建再宿主机,但是 nginx 是用的 docker 容器,那么 nginx 做后端请求转发的时候,务必要把 proxy 写成宿主机的 docker0 ip , 不能写 127.0.0.1 ,如下,docker0 的 ip 是 172.17.0.1 ,


[root@control-plane workflow]# ifconfigbr-e4574af0585c: flags=4099<UP,BROADCAST,MULTICAST>  mtu 1500        inet 192.168.49.1  netmask 255.255.255.0  broadcast 192.168.49.255        inet6 fe80::42:36ff:fea2:ac72  prefixlen 64  scopeid 0x20<link>        ether 02:42:36:a2:ac:72  txqueuelen 0  (Ethernet)        RX packets 807  bytes 5706427 (5.4 MiB)        RX errors 0  dropped 0  overruns 0  frame 0        TX packets 953  bytes 131430 (128.3 KiB)        TX errors 0  dropped 0 overruns 0  carrier 0  collisions 0
docker0: flags=4163<UP,BROADCAST,RUNNING,MULTICAST> mtu 1500 inet 172.17.0.1 netmask 255.255.0.0 broadcast 172.17.255.255 inet6 fe80::42:92ff:fea8:9e6f prefixlen 64 scopeid 0x20<link>
复制代码


那么就的吧 nginx 对应的转发 ip 写成 172.17.0.1


 server {     listen  80;     server_name   127.0.0.1;     location ~/api/ {        proxy_pass       http://172.17.0.1:3030;     }
复制代码

Redis 集群

root@VM_0_17_centos /]# docker network  create redis-net --subnet 172.38.0.0/16  # 新建redis集群的网络,名称为redis-net66d8cf51ec6c00b4c92db05552375f1816fb324723866cff389103c9deb1e756[root@VM_0_17_centos /]# docker network lsNETWORK ID     NAME        DRIVER    SCOPE479307d3d0a1   bridge      bridge    localcfc57d39c114   host        host      local94bab7ee5dee   mynet       bridge    localb076eb847244   none        null      local66d8cf51ec6c   redis-net   bridge    local[root@VM_0_17_centos /]# docker network inspect redis-net[    {        "Name": "redis-net",        "Id": "66d8cf51ec6c00b4c92db05552375f1816fb324723866cff389103c9deb1e756",        "Created": "2021-01-07T11:11:49.616037596+08:00",        "Scope": "local",        "Driver": "bridge",        "EnableIPv6": false,        "IPAM": {            "Driver": "default",            "Options": {},            "Config": [                {                    "Subnet": "172.38.0.0/16"                }            ]        },        "Internal": false,        "Attachable": false,        "Ingress": false,        "ConfigFrom": {            "Network": ""        },        "ConfigOnly": false,        "Containers": {},        "Options": {},        "Labels": {}    }]#执行脚本,生成 6个redis节点配置文件for port in $(seq 1 6); \do \mkdir -p /mydata/redis/node-${port}/conftouch /mydata/redis/node-${port}/conf/redis.confcat << EOF >/mydata/redis/node-${port}/conf/redis.confport 6379 bind 0.0.0.0cluster-enabled yes cluster-config-file nodes.confcluster-node-timeout 5000cluster-announce-ip 172.38.0.1${port}cluster-announce-port 6379cluster-announce-bus-port 16379appendonly yesEOFdone
[root@VM_0_17_centos conf]# docker run -p 6371:6379 -p 16371:16379 --name redis-1 -v /mydata/redis/node-1/data:/data -v /mydata/redis/node-1/conf/redis.conf:/etc/redis/redis.conf -d --net redis-net --ip 172.38.0.11 redis:5.0.9-alpine3.11 redis-server /etc/redis/redis.conf #启动redis 节点1容器
Unable to find image 'redis:5.0.9-alpine3.11' locally5.0.9-alpine3.11: Pulling from library/rediscbdbe7a5bc2a: Pull complete dc0373118a0d: Pull complete cfd369fe6256: Pull complete 3e45770272d9: Pull complete 558de8ea3153: Pull complete a2c652551612: Pull complete Digest: sha256:83a3af36d5e57f2901b4783c313720e5fa3ecf0424ba86ad9775e06a9a5e35d0Status: Downloaded newer image for redis:5.0.9-alpine3.118db128a0d4c6c53484fc2ea43c9397e11161c771ba5214200212edf47f8f24d3[root@VM_0_17_centos conf]# docker run -p 6372:6379 -p 16372:16379 --name redis-2 -v /mydata/redis/node-2/data:/data -v /mydata/redis/node-2/conf/redis.conf:/etc/redis/redis.conf -d --net redis-net --ip 172.38.0.12 redis:5.0.9-alpine3.11 redis-server /etc/redis/redis.conf #启动redis 节点2容器#其他四个节点同理[root@VM_0_17_centos conf]# docker run -p 6373:6379 -p 16373:16379 --name redis-3 -v /mydata/redis/node-3/data:/data -v /mydata/redis/node-3/conf/redis.conf:/etc/redis/redis.conf -d --net redis-net --ip 172.38.0.13 redis:5.0.9-alpine3.11 redis-server /etc/redis/redis.conf [root@VM_0_17_centos conf]# docker psCONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMESfacf9d559439 redis:5.0.9-alpine3.11 "docker-entrypoint.s…" 5 seconds ago Up 4 seconds 0.0.0.0:6376->6379/tcp, 0.0.0.0:16376->16379/tcp redis-623753ff70658 redis:5.0.9-alpine3.11 "docker-entrypoint.s…" 29 seconds ago Up 29 seconds 0.0.0.0:6375->6379/tcp, 0.0.0.0:16375->16379/tcp redis-5fcabadb47f28 redis:5.0.9-alpine3.11 "docker-entrypoint.s…" 53 seconds ago Up 53 seconds 0.0.0.0:6374->6379/tcp, 0.0.0.0:16374->16379/tcp redis-4c355b387c1e1 redis:5.0.9-alpine3.11 "docker-entrypoint.s…" 3 minutes ago Up 3 minutes 0.0.0.0:6373->6379/tcp, 0.0.0.0:16373->16379/tcp redis-399d867807d1e redis:5.0.9-alpine3.11 "docker-entrypoint.s…" 4 minutes ago Up 4 minutes 0.0.0.0:6372->6379/tcp, 0.0.0.0:16372->16379/tcp redis-2ad34225fee1f redis:5.0.9-alpine3.11 "docker-entrypoint.s…" 5 minutes ago Up 5 minutes 0.0.0.0:6371->6379/tcp, 0.0.0.0:16371->16379/tcp redis-1/data # redis-cli --cluster create 172.38.0.11:6379 172.38.0.12:6379 172.38.0.13:6379 172.38.0.14:6379 172.38.0.15:6379 172.38.0.16:6379 --cluster-replicas 1 #进入一个容器创建redis集群/data # redis-cli -c127.0.0.1:6379> set a aaaa-> Redirected to slot [15495] located at 172.38.0.13:6379OK172.38.0.13:6379> get a"aaaa"172.38.0.13:6379> cluster info # 查看集群信息cluster_state:okcluster_slots_assigned:16384cluster_slots_ok:16384cluster_slots_pfail:0cluster_slots_fail:0cluster_known_nodes:6cluster_size:3cluster_current_epoch:6cluster_my_epoch:3cluster_stats_messages_ping_sent:169cluster_stats_messages_pong_sent:175cluster_stats_messages_meet_sent:4cluster_stats_messages_sent:348cluster_stats_messages_ping_received:174cluster_stats_messages_pong_received:173cluster_stats_messages_meet_received:1cluster_stats_messages_received:348172.38.0.13:6379> cluster nodes # 查看节点 a24f7707237aaf0e08695a73c0625f8580e92a05 172.38.0.15:6379@16379 slave 549e6d070cba073488cb6d82e130be728b4618e5 0 1609990494000 5 connected549e6d070cba073488cb6d82e130be728b4618e5 172.38.0.11:6379@16379 master - 0 1609990494000 1 connected 0-5460904bb967518976a005741c2bc0b653f721d635ee 172.38.0.14:6379@16379 slave 96709c4566cbede13a4c258287c4072f0c988543 0 1609990495191 4 connected96709c4566cbede13a4c258287c4072f0c988543 172.38.0.13:6379@16379 myself,master - 0 1609990493000 3 connected 10923-163837acda5adad75068f1e3ee3d9660415b7200e8fc2 172.38.0.16:6379@16379 slave ff7bae21120ab3f05d0153d7929f1c09eb26b9fd 0 1609990495091 6 connectedff7bae21120ab3f05d0153d7929f1c09eb26b9fd 172.38.0.12:6379@16379 master - 0 1609990494190 2 connected 5461-10922
# 验证成功[root@VM_0_17_centos conf]# docker stop c355b387c1e1 #停掉其中一个容器节点,验证高可用
c355b387c1e1[root@VM_0_17_centos conf]# docker exec -it facf9d559439 /bin/sh/data # redis-cli -c127.0.0.1:6379> cluster nodes # 其中给一个节点停掉之后,node-4 slave自动转master549e6d070cba073488cb6d82e130be728b4618e5 172.38.0.11:6379@16379 master - 0 1609990637048 1 connected 0-546096709c4566cbede13a4c258287c4072f0c988543 172.38.0.13:6379@16379 master,fail - 1609990604492 1609990603587 3 connecteda24f7707237aaf0e08695a73c0625f8580e92a05 172.38.0.15:6379@16379 slave 549e6d070cba073488cb6d82e130be728b4618e5 0 1609990636047 5 connected904bb967518976a005741c2bc0b653f721d635ee 172.38.0.14:6379@16379 master - 0 1609990637048 7 connected 10923-163837acda5adad75068f1e3ee3d9660415b7200e8fc2 172.38.0.16:6379@16379 myself,slave ff7bae21120ab3f05d0153d7929f1c09eb26b9fd 0 1609990635000 6 connectedff7bae21120ab3f05d0153d7929f1c09eb26b9fd 172.38.0.12:6379@16379 master - 0 1609990636000 2 connected 5461-10922127.0.0.1:6379> get a-> Redirected to slot [15495] located at 172.38.0.14:6379"aaaa"
复制代码

案例-打包


#Dockerfile 编写FROM java:8COPY *.jar /app.jarCMD ["--server.port=8099"]EXPOSE 8099ENTRYPOINT ["java","-jar","/app.jar"]
[root@localhost idea]# docker build -t admin . # 生成镜像[root@localhost idea]# Docker images #查看镜像[root@localhost idea]# Docker run -d -P --name myapp admin #启动容器
复制代码

个人阿里云


用户头像

小麦

关注

还未添加个人签名 2019.08.15 加入

还未添加个人简介

评论

发布
暂无评论
docker基础