atwood-pan

 

2021-10-13Docker

一、简介

1.技术前提

了解linux

修改虚拟机ip为静态:

  • vim /etc/sysconfig/network-scripts/ifcfg-ens33
    • BOOTPROTO=“static”
    • IPADDR=“192.168.188.107”
    • NETMASK=255.255.255.0
    • GATEWAY=192.168.188.2
    • DNSI=192.168.188.2
  • 重启网络服务:systemctl restart network

2.应用背景

软件在windows上开发完成后,把jar或war包交给运维,运维部署到linux或云服务器上时,可能会因为环境不同或配置不同,而导致不能正常工作。用docker就可能方便的解决该问题。

3. 工作原理

如果到宠物店只买回一条鱼,回家后可能因为环境不适应而死亡,而从宠物店买回的是带鱼缸和鱼这一整套环境就不会出问题。也就是从系统底层至上层整体打包成镜像文件,从而达到完全跨平台的到处运行。

4.Docker与虚拟机的区别

Docker是一个精简版的虚拟机,只是少了对操作系统和硬件的虚拟,所以启动速度是秒级的,而虚拟机的启动则是分钟级的

5.Docker的组成

  • 镜像:相当于java中的类,如Person。应用程序和配置及依赖打包成一个可运行的环境,这个包就是镜像文件。

  • 容器:相当于new Person产生对象,容器是以镜像为模板产生,可把容器看成镜像一个简化版的linux环境和若干运行在其中的应用程序。

  • 仓库:是集中存放镜像的地方,docker三要素:镜像、容器、仓库

  • 仓库注册服务器:放着多个仓库。

二、安装

1.下载Dcoker的依赖环境

yum install -y yum-utils device-mapper-persistent-data lvm2

2.指定Docker镜像源

yum-config-manager --add-repo http://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo

3. 安装Docker

yum makecache fast   #为加快安装速度,对缓存加速
yum -y install docker-ce

4.查看版本

docker version

5.启动Docker并测试

  • 启动docker: systemctl start docker
  • 重启: systemctl restart docker
  • 卸载docker: yum remove docker
  • 设置开机启动: systemctl enable docker

6. 云镜像仓库

是一个代理仓库,放了一些镜像,因为中央仓库https://hub.docker.com是国外网站,非常慢,有两个云可用,网易云和阿里云,推荐使用阿里云,更全面,其镜像地址:https://www.aliyun.com/product/acr

获取加速器地址的方法如下:

  • 注册–>可使用淘宝帐号注册,搜索容器镜像服务

  • 获取加速器地址:通过网址https://cr.console.aliyun.com/cn-hangzhou/instances/mirrors获取

  • 配置加速器

    • mkdir /etc/docker

    • vim /etc/docker/daemon.json

    • 内容如下:每个帐号都不同,使用下面一个也可以。

      {
        "registry-mirrors": ["https://f1z25q5p.mirror.aliyuncs.com"]
      }
      
    • 使配置生效:

      • systemctl daemon-reload
      • systemctl restart docker
  • helloworld镜像生成容器:docker run hello-world,默认先从本地的镜像中找,没找到就从阿里云中找其镜像并拉取。

三、docker常用命令

1. 帮助命令

  • docker info—查看docker的总体信息

  • docker help—查看docker有哪些命令

2. 镜像操作

  • 查看镜像
    • docker images—查看有哪些镜像,repository表示镜像的仓库源,tag是版本,image id是镜像的唯一ID,created是创建时间,size是镜像大小。
    • docker images -a—查看镜像及中间映像层,也就是一个表面镜像内部还包含了哪些镜像。
    • docker images -q—只显示镜像ID
  • 下载镜像 docker pull xxx
    • docker pull nginx,相当于docker pull nginx:latest下载最新版本。
    • docker pull tomcat:8.5.32
  • 删除镜像 docker rmi xxx
    • docker rmi hello-world—失败,因为提示说该镜像的容器正在运行,
    • docker rmi -f hello-world—强制删除

3. 容器操作

3.1 创建并启动容器

以centos镜像为例演示

  • docker pull centos—从阿里上拉取centos镜像
  • docker run -it centos—创建容器,i为交换模式,t为使用终端,it常常一起使用表示使用终端进入交互模式,exit退出
  • docker run -it --name mycts centos–启动并指定容器名称,上面没指定都会随机给个名字

3.2 查看有哪些容器

  • docker ps ** 查看正在运行**的容器
  • docker ps -q —只显示容器id
  • docker ps -qa 查看所有,包括没有运行的容器

3.3 停止和启动容器

  • exit—从终端退出并可能停止容器,ctrl+p+q退出但容器仍然运行。
  • docker stop aea7a56b0c7d或容器名—停止容器
  • docker start 容器名或容器id 重新启动被停止的容器

3.4 删除容器

不是停止,停止后容器还在,只是不运行了

  • docker rm 容器id或名称—注意,必须先关闭容器才能删除,rmi是删除镜像
  • docker rm -f $(docker ps -aq)—批量删除

3.5 进入容器的内部进行操作

docker exec -it 容器id bash

3.6 容器与宿主机间拷贝文件

  • 从容器中拷贝到宿主机

    docker run -it centos-->cd /tmp–>vi hello.txt—>ctrl+p+q–>docker ps–>docker cp 容器id:/tmp/hello.txt /opt

  • 从宿主机拷贝到容器

    docker cp /opt/a.txt 容器id:/tmp

四. 数据卷/目录挂载

1. 有什么用

  • 目录映射:

    为方便宿主机与容器间传递数据,产生目录映射,使两者共享同一目录。使用数据卷可将宿主机上的一个目录映射到容器的一个目录中。

  • 持久化容器数据

    容器运行中所产生的数据,如果不通过commit生成新镜像,当容器被删除后数据就丢失了。使用数据卷可在不产生新镜像的前提下保存数据在磁盘上,有点像redis中的持久化。

  • 部署项目方便

    为了部署项目,需要使用到cp命令将宿主机内的war包复制到容器内部。

    使用数据卷可以在宿主机中操作目录中内容,那么容器内部映射的文件,也会跟着一起改变

2. 特点

  • 数据卷可在容器之间共享
  • 修改卷中数据可以直接生效,并且对卷的修改不会引起镜像的更新。
  • 卷的生命周期一直持续到没有容器使用它为止。

3. 产生数据卷

docker run -di -v /myData:/myContainerData --name myc1 centos

参数说明:

  • -di:产生交互式后台进程
  • -v:目录挂载,myData是宿主机中目录,myContainerData是容器中目录
  • –name:给容器启一名称为myc1

4. 测试

  • vim /myData/a.txt
  • docker exec -it myc1 bash
  • cat /myContainerData/a.txt

五. docker应用部署

1. MYSQL部署

a. 拉取镜像

  • 搜索mysql镜像:docker search mysql

  • 拉取镜像:docker pull centos/mysql-57-centos7 ,镜像选择的是centos/mysql-57-centos7

b. 创建mysql容器

docker run -di --name=mysql5.7 -p 3307:3306 -e MYSQL_ROOT_PASSWORD=123 centos/mysql-57-centos7
注意:如果宿言主机上已经安装mysql,则这里宿主机就不能还使用3306

参数说明:

  • -di: 以守护进程交互式启动容器
  • –name: 给容器启名为mysql5.7
  • -p: 端口映射,格式为:宿主机端口:容器端口,为什么要映射?因为容器的ip地址跟windows的ip不在一个网段,无法通信。从win7访问容器就只能通过win7访问宿主机(虚拟机)的ip+映射的端口。
  • -e: 当从win7远程连接容器mysql时,要设置root帐号的密码,这里设置远程连接密码为root,但要注意:在进入容器内访问时,密码是空的。
  • 最后一个参数:是上面下载的镜像名.

c. 连接mysql

1. 容器本地连接

  • docker exec -it -u root mysql5.7 bash

    -u root:表示以root身份进入容器

  • mysql -uroot -p ,密码为空,回车

2. win7远程连接

mysql -uroot -p123 -h192.168.188.107,默认连接的是3306,如果映射的宿主机不是3306,则后面添加 -P3306

2. tomcat部署

2.1 拷贝war包

从宿主机上拷贝war包到容器中

  • 运行tomcat8.5.32镜像

    docker run -d --name mytom1 -p 9000:8080 tomcat:8.5.32

    参数说明:

    • -p是端口映射,9000为宿主机端口,8080为容器中tomcat端口,没办法直接访问容器的8080,就直接访问宿主机的9000,映射到容器的8080
    • -d是后台启动,换成-it则是前台启动tomcat
  • 测试tomcat:192.168.188.107:9000
  • 直接拷贝war包到容器

    docker cp /opt/data/day1.war 容器id:/usr/local/tomcat/webapps/

  • 测试:192.168.188.107:9000/day1/showSuc

2.2 使用目录挂载

  • 挂载命令

    docker run -di -p 8888:8080 -v /opt/data:/usr/local/tomcat/webapps/ --name mytom2 tomcat:8.5.32

  • 向/opt/data中放入day1.war

  • 测试:192.168.188.107:8888/day1/showSuc

3. nginx部署

3.1 拉取镜像

docker pull nginx

3.2 创建容器

  • docker run -it --name mynginx1 -p 80:80 nginx bash

  • 配置文件在/etc/nginx/nginx.conf,默认没有vi命令

  • 拷贝nginx目录到宿主机:

    • ctr+p+q
    • docker ps
    • docker cp mynginx1:/etc/nginx /opt/data
  • 删除容器:docker rm -f mynginx1

  • 启动容器并添加数据卷:

    docker run -v /opt/data/nginx:/etc/nginx -di --name mynginx2 -p 80:80 nginx

3.3 测试

192.168.188.107/

4. redis部署

4.1. 拉取redis

docker pull redis

4.2 创建容器

以aof方式持久化,如果用rdb则不加–appendony yes

docker run -d --name myredis -p 6379:6379 redis --appendonly yes

4.3 进入redis容器

  • 进入容器

    docker exec -it myredis bash

  • 启动客户端

    • cd /usr/local/bin
    • redis-cli

六、自定义镜像

##1.Dockerfile方式

###a. Dockerfile介绍

  1. 有什么用?

    使用Dockerfile可以根据需求开发一个自定义的镜像,其实就是一个文本文件,由一系列命令和参数构成,Docker可读取这个文件构建一个镜像。

  2. dockerfile常用指令

from 基于哪个镜像
  
  MAINTAINER 作者

  COPY 复制文件进入镜像(只能用相对路径,不能用绝对路径)

  ADD 复制文件进入镜像(压缩包会解压)

  WORKDIR 指定工作目录,不存在会创建路径

  ENV 设置环境变量

  EXPOSE 暴露容器端口

  ENTRYPOINT 在容器启动的后执行,作用于容器层,dockerfile里有多条时只执行最后一条

  RUN 构建镜像的时候执行其后的命令,作用于镜像层面,命令格式:
shell命令格式:RUN yum install -y net-tools
  exec命令格式:RUN [“yum”,“install”,"-y",“net-tools”

###b. 创建jdk镜像

+ 向/opt/data/jdk目录添加jdk压缩文件

+ 在/opt/data/jdk目录中创建并编辑Dockerfile文件, vim Dockerfile   ,添加下面内容:

  ```dockerfile
    FROM centos:7
    MAINTAINER lly
    WORKDIR /usr
    RUN mkdir /usr/local/java
    ADD jdk1.8.0_144.tar.gz /usr/local/java/
    ENV JAVA_HOME /usr/local/java/jdk1.8.0_144
    ENV JRE_HOME $JAVA_HOME/jre
    ENV CLASSPATH $JAVA_HOME/lib/dt.jar:$JAVA_HOME/lib/tools.jar:$JAR_HOME/lib:$CLASSPATH
    ENV PATH $JAVA_HOME/bin:$PATH
  • 编译并构建镜像,镜像名为jdk1.8

    docker build -t=‘jdk1.8’ ./

  • 查看镜像

    docker images

  • 通过镜像jdk1.8创建容器myjdk

    docker run -it --name myjdk jdk1.8 bash

###c. 微服务部署

  1. 上传jar包

    在/opt/data/eureka目录中添加eureka_7001.jar

  2. 查找jdk镜像

    docker search jdk 得到ascdc/jdk8镜像,也可使用前面创建的镜像jdk1.8

  3. 编辑Dockerfile

    • 在/opt/data/eureka中创建并编辑Dockerfile文件

      #基于哪个镜像
      #FROM ascdc/jdk8
      FROM jdk1.8
      #目录挂载,将本地文件夹挂载到当前容器,这里用不着,了解
      VOLUME /tmp
      #将文件复制到容器指定目录
      ADD eureka_7001.jar /usr/local/java/
      #暴露服务的端口
      EXPOSE 7001
      #设置容器启动后要自动执行的命令
      ENTRYPOINT ["java","-jar","/usr/local/java/eureka_7001.jar"]
      
      
  4. 生成镜像并测试

    • 编译并创建镜像

      docker build -t=‘eureka-server’ ./

    • 查看生成的镜像:docker images

    • 启动容器:

      • 前台启动:docker run -p 7001:7001 eureka-server
      • 后台启动:docker run -di -p 7001:7001 eureka-server
    • 192.168.188.107:7001

2. commit方式

a. 创建使用redis的微服务

  1. static 的js子目录下添加vue.js和axios.js

  2. 在static目录下添加下面两个前端页面,注意给每个页面导入vue和axios

    • login.html

      <div id="d">
          <input name="username" v-model='name'><br>
          <button  @click="f">登录</button>
      </div>
      <script>
          new Vue({
              el:"#d",
              data:{
                  name:""
              },
              methods:{
                  f:function () {
                      axios.get('http://localhost/login',{
                          params:{
                              username:this.name
                          }
                      }).then(ret=> {
                          location.href='http://localhost/main.html'
                      });
                  }
              }
          });
      </script>
      
    • main.html

      <div id="d">
          <h1>欢迎你:{{name}}</h1>
      </div>
      <script>
          new Vue({
              el:"#d",
              data:{
                  name:""
              },
              mounted: function(){
                  axios.get(
                      '/getuserName'
                  ).then(rs => {
                      if(rs.data){
                         this.name=rs.data;
                      }
                  });
              }
          });
      </script>
      
  3. 导入依赖

    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-data-redis</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.boot</groupId>
        <artifactId>spring-boot-starter-web</artifactId>
    </dependency>
    <dependency>
        <groupId>org.springframework.session</groupId>
        <artifactId>spring-session-data-redis</artifactId>
        <version>2.0.4.RELEASE</version>
    </dependency>
    
  4. 配置类上添加redisSession的注解

    @EnableRedisHttpSession(maxInactiveIntervalInSeconds = 300)
    
  5. 添加控制器类

    @RestController
    public class UserCtl {
        @RequestMapping("/login")
        public String login(HttpSession session, String username){
            session.setAttribute("username",username);
            System.out.println("name:"+username+",sessionID:"+session.getId());
            return "success";
        }
        @RequestMapping("/getuserName")
        public String getName(HttpSession session){
            return (String)session.getAttribute("username");
        }
    }
    

b. 把容器生成新镜像

docker commit -a "lly" -m "注释" 容器id 镜像名:版本号,如
docker commit -a "lly" -m "这是运行了redis服务,tmp目录下存放微服务" myredis  redis:1.0

posted on 2021-10-13 08:43  JavaCoderPan  阅读(7)  评论(0编辑  收藏  举报  来源

导航