zoukankan      html  css  js  c++  java
  • docker构建镜像

    1 What & Why

    What: 什么是构建docker镜像?

    构建docker镜像在现有镜像的基础上,修改或添加个人的功能后,重新打包成新镜像的过程

    Why: 为什么要构建docker镜像?

    docker镜像方便部署及分享他人

    2 Hello World

    2.1 目标

    1. 利用现有镜像ubuntu构建新镜像
    2. 镜像的功能是利用ubuntu的echo命令打印Hello world

    2.2 创建文件夹

    mkdir demo01-helloworld
    cd demo01-helloworld
    

    2.3 创建配置文件

    Docker以文件Dockerfile作为配置文件,内容如下

    Dockerfile

    FROM ubuntu:latest
    
    CMD ["/bin/echo", "Hello world!"]
    

    以上内容非常简单

    • FROM用来配置基础镜像,这里以ubuntu的最新版本的镜像作为基础镜像
    • CMD表示镜像中执行的命令,这里等同于执行命令/bin/echo "Hello World!"
      • 当前的格式为Exec格式
      • 后面会介绍shell格式

    2.4 构建镜像

    命令

    docker image build . -t demo01-helloworld:0.0.1
    
    • .表示当前文件夹里的所有文件

    • -t等同于--tag,作用是给镜像打标签,这里的标签名为demo01-helloworld

    • :后是镜像的版本号,如果省略则默认为latest

    构建过程如下,当打印Successfully tagged demo01-helloworld:0.0.1表明镜像构建成功

    $ docker image build . -t demo01-helloworld
    Sending build context to Docker daemon  2.048kB
    Step 1/2 : FROM ubuntu:latest
     ---> 4e2eef94cd6b
    Step 2/2 : CMD ["/bin/echo", "Hello world!"]
     ---> Running in 581995f3af46
    Removing intermediate container 581995f3af46
     ---> afa0f6e8fc94
    Successfully built afa0f6e8fc94
    Successfully tagged demo01-helloworld:0.0.1
    

    可以用命令docker image ls查询所有镜像,再次确认已经构建完成

    $ docker image ls
    REPOSITORY          TAG                 IMAGE ID            CREATED             SIZE
    demo01-helloworld   0.0.1               afa0f6e8fc94        19 seconds ago      73.9MB
    

    运行镜像,先生成容器,再启动容器

    $ docker container run demo01-helloworld:0.0.1
    Hello world!
    

    docker启动时先判断有没有该容器,如果不存在则通过镜像创建相应的容器,然后执行容器

    2.5 注意

    需要说明的是CMD可以在构造镜像的时候不指定,启动容器的时候执行。如果启动时指定了命令,则CMD中指定的命令将不会执行,即被覆盖,现象如下。你看懂了吗?

    $ docker container run demo01-helloworld:0.0.1 /bin/echo "Hello world! v2"
    Hello world! v2
    

    3 java应用

    3.1 目标

    1. 利用现有镜像openjdk构建新镜像
    2. 镜像的功能是运行java程序打印Hello java

    3.2 创建文件夹

    mkdir demo02-hellojava
    cd demo02-java
    

    3.3 创建java工程

    选择你喜欢的方式创建一个maven工程,可以从通过网页下载模板,可以利用eclipse和idea等等

    这里采用mvn命令的方式创建

    mvn archetype:generate -DgroupId=org.zwx.hellojava -DartifactId=demo02-hellojava -DinteractiveMode=false
    

    结果如下

    $ mvn archetype:generate -DgroupId=org.zwx.hellojava -DartifactId=demo02-hellojava -DinteractiveMode=false
    [INFO] Scanning for projects...
    [INFO]
    [INFO] ------------------< org.apache.maven:standalone-pom >-------------------
    [INFO] Building Maven Stub Project (No POM) 1
    [INFO] --------------------------------[ pom ]---------------------------------
    [INFO] ...省略一些内容
    [INFO] Parameter: basedir, Value: /Users/zhouweixin/docker-demos
    [INFO] Parameter: package, Value: org.zwx.hellojava
    [INFO] Parameter: groupId, Value: org.zwx.hellojava
    [INFO] Parameter: artifactId, Value: demo02-hellojava
    [INFO] Parameter: packageName, Value: org.zwx.hellojava
    [INFO] Parameter: version, Value: 1.0-SNAPSHOT
    [INFO] project created from Old (1.x) Archetype in dir: /Users/zhouweixin/docker-demos/demo02-hellojava
    [INFO] ------------------------------------------------------------------------
    [INFO] BUILD SUCCESS
    [INFO] ------------------------------------------------------------------------
    [INFO] Total time:  16.557 s
    [INFO] Finished at: 2020-09-28T17:55:09+08:00
    [INFO] ------------------------------------------------------------------------
    

    文件目录

    .
    ├── pom.xml
    └── src
        ├── main
        │   └── java
        │       └── org
        │           └── zwx
        │               └── hellojava
        │                   └── App.java
        └── test
            └── java
                └── org
                    └── zwx
                        └── hellojava
                            └── AppTest.java
    

    3.4 编译执行

    在打包之前先确定java应用可以正常执行

    首先,修改文件src/main/java/org/zwx/hellojava/App.java

    package org.zwx.hellojava;
    
    /**
     * Hello world!
     *
     */
    public class App
    {
        public static void main( String[] args )
        {
            System.out.println( "Hello java!" );
        }
    }
    

    然后,用mvn命令编译打包

    $ mvn package
    [INFO] Scanning for projects...
    [INFO]
    [INFO] -----------------< org.zwx.hellojava:demo02-hellojava >-----------------
    [INFO] Building demo02-hellojava 1.0-SNAPSHOT
    [INFO] --------------------------------[ jar ]---------------------------------
    [INFO] ...省略一些内容
    [INFO] --- maven-jar-plugin:2.4:jar (default-jar) @ demo02-hellojava ---
    [INFO] Building jar: /Users/zhouweixin/docker-demos/demo02-hellojava/target/demo02-hellojava-1.0-SNAPSHOT.jar
    [INFO] ------------------------------------------------------------------------
    [INFO] BUILD SUCCESS
    [INFO] ------------------------------------------------------------------------
    [INFO] Total time:  1.531 s
    [INFO] Finished at: 2020-09-28T17:59:40+08:00
    [INFO] ------------------------------------------------------------------------
    

    文件目录

    .
    ├── pom.xml
    ├── src
    │   └── ...省略一些内容
    └── target
        ├── demo02-hellojava-1.0-SNAPSHOT.jar
        └── ...省略一些内容
    
    

    当你执行完命令mvn package后,首先会编译生成一些class文件,然后打包成demo02-hellojava-1.0-SNAPSHOT.jar,生成的文件都在目录target下

    该jar文件是执行文件,具体执行命令如下

    $ java -cp target/demo02-hellojava-1.0-SNAPSHOT.jar org.zwx.hellojava.App
    Hello java!
    

    3.5 拉取基础镜像

    如前文所述构建镜像需要一个基础镜像,基础镜像也可以不提前拉取,构建的时候如果不存在也会自动拉取

    该例子中要想启动java应用,你知道需要哪个环境吗?

    你应该是猜对了,仅仅需要java的运行时环境(jre)

    首先到hub.docker.com上检索jre的相关tag,这里我们选择的是8u265-jre

    二话不说,先拉取镜像(也可以不提前拉取)

    $ docker pull openjdk:8u265-jre
    8u265-jre: Pulling from library/openjdk
    57df1a1f1ad8: Pull complete
    71e126169501: Pull complete
    1af28a55c3f3: Pull complete
    a9777c2d5c29: Pull complete
    9248106993db: Pull complete
    1f74ab5b5b3e: Pull complete
    Digest: sha256:e98dece4606dc1ec47c0c9ab6aa43931577232a5b7d6fd46f3ead7377727b412
    Status: Downloaded newer image for openjdk:8u265-jre
    docker.io/library/openjdk:8u265-jre
    

    用交互的方式运行该镜像并确定java的版本

    $ docker container run -it openjdk:8u265-jre
    root@0687c67dccd0:/# java -version
    openjdk version "1.8.0_265"
    OpenJDK Runtime Environment (build 1.8.0_265-b01)
    OpenJDK 64-Bit Server VM (build 25.265-b01, mixed mode)
    

    参数说明

    • -it-i-t的缩写
    • -i全称是--interactive,即交互模式,可以正常的输入输出
    • -t是一个伪TTY,即伪终端

    3.6 构建镜像

    创建配置文件Dockerfile

    FROM openjdk:8u265-jre
    
    COPY target/demo02-hellojava-1.0-SNAPSHOT.jar /usr/src/demo02-hellojava-1.0-SNAPSHOT.jar
    
    CMD java -cp /usr/src/demo02-hellojava-1.0-SNAPSHOT.jar org.zwx.hellojava.App
    

    参数说明

    • COPY命令用于将本地文件拷贝到基础镜像中,并且这个基础镜像中有java运行时环境,两者结合满足正常运行程序
      • 第一个参数为本地文件目录
      • 第二个参数为基础镜像中的目录
    • CMD命令表示在基础镜像中执行的命令(可以不写数组的形式)

    执行镜像构建命令

    $ docker image build . -t demo02-hellojava:0.0.1
    Sending build context to Docker daemon  38.91kB
    Step 1/3 : FROM openjdk:8u265-jre
     ---> d9d1d3243082
    Step 2/3 : COPY target/demo02-hellojava-1.0-SNAPSHOT.jar /usr/src/demo02-hellojava-1.0-SNAPSHOT.jar
     ---> Using cache
     ---> 6c34d345bb51
    Step 3/3 : CMD java -cp /usr/src/demo02-hellojava-1.0-SNAPSHOT.jar org.zwx.hellojava.App
     ---> Running in 0d9a33ea0ae1
    Removing intermediate container 0d9a33ea0ae1
     ---> fc3cd9ee5218
    Successfully built fc3cd9ee5218
    Successfully tagged demo02-hellojava:0.0.1
    

    启动

    $ docker container run demo02-hellojava:0.0.1
    Hello java!
    

    4 Dockfile中的命令

    命令 功能
    FROM 指定基础镜像
    COPY 复制文件或文件夹
    ENV 设置环境变量
    RUN 执行一个命令,可以写多个,通常用于安装软件包
    CMD 执行一个命令,只有一个被执行,可被docker run后面的命令所覆盖,即如果命令行中有该命令,CMD中的将不会执行
    ENTRYPOINT 配置容器启动时的命令,一定会执行
    EXPOSE 暴露的端口号

    参考

  • 相关阅读:
    手机游戏开发中如何选择适合的纹理格式
    站在巨具的肩膀上:使用现有工具搭建自己的工作流
    游戏引擎不仅是代码,更多的是完善的工具
    Android下/data/data/<package_name>/files读写权限
    Unity3D中灵活绘制进度条
    为什么X86汇编中的mov指令不支持内存到内存的寻址?
    【吐血推荐】简要分析unity3d中剪不断理还乱的yield
    解释型语言和编译型语言如何交互?以lua和c为例
    char,wchar_t,WCHAR,TCHAR,ACHAR的区别----LPCTSTR
    游戏关卡是酱紫加载的,你造吗?
  • 原文地址:https://www.cnblogs.com/zhouweixin/p/13746967.html
Copyright © 2011-2022 走看看