Docker-制作镜像的两种方式=》基于容器制作&基于Dockerfile制作

本文主要是基于Docker如何制作一个Java镜像,而一个Java镜像想要运行需要系统环境,JDK。所以我们要先有一个系统环境,本文使用的是centos7,JDK选择版本是8,而我使用的Java程序是一个简易的springBoot项目,你可以选择使用本地的Java程序。我了解docker制作镜像有两种方式,一种是Docker Commit基于容器构建镜像;一种是Docker Build基于Dockerfile构建镜像。我接下来都会讲一下这两种方式的使用

Docker Commit基于容器构建镜像

1.拉取centos7镜像

# 拉取镜像
sudo docker pull centos:7
# 创建容器
sudo docker -di --name centos7 centos:7

2.拷贝Java jar程序到容器

项目源码:简易springboot项目

# 拷贝Java jar包到容器
sudo docker cp demo-0.0.1-SNAPSHOT.jar centos7:/usr/local/data

3.安装jdk和验证Java程序是否正常运行

# 进入容器
sudo docker exec -it  centos7 /bin/bash
# 安装jdk
yum -y install java-1.8.0-openjdk.x86_64
# 验证Java是否成功安装
java -version
# 运行Java 程序
nohup java -jar /usr/local/data/demo-0.0.1-SNAPSHOT.jar > nohup.out 2>&1 &
# 验证程序是否正常运行,输出hello java即成功
curl localhost:9080/index
# 验证成功后退出该容器
exit

4.构建镜像

# 执行下面命令会生成镜像
docker commit -a="cyl" -m="simple springboot" centos7 mycentos:7

docker commit构建镜像指令格式

docker commit [OPTIONS] CONTAINER [REPOSITORY[:TAG]]

-a:提交的镜像作者;
-c:使用 Dockerfile 指令来创建镜像;
-m:提交时的说明文字;
-p:在 commit 时,将容器暂停。

# 查看景象是否生成
sudo docker images

REPOSITORY TAG IMAGE ID CREATED SIZE
mycentos 7 2ae82069a24b 51 minutes ago 726MB
centos 7 eeb6ee3f44bd 2 years ago 204MB

我们构建的景象mycentos比centos大,因为里面有jdk和Java程序

5.启动容器

# 启动容器
sudo docker run -di --name mycentos7 -p 9080:9080 mycentos:7
# 进入容器
sudo docker exec -it  mycentos7 /bin/bash
# 运行Java 程序
nohup java -jar /usr/local/data/demo-0.0.1-SNAPSHOT.jar > nohup.out 2>&1 &
# 退出容器
exit
# 主机直接调用Java程序接口,输出hello java即成功
curl ip:9080/index

这种镜像制作的方式就介绍完了,但是执行过程中发现它有些复杂,制作镜像启动后还需要再次进入容器,手动启动Java程序。是否有更简便的方式,启动容器时直接就运行Java程序了呢。接下来我就要讲这种更优的方式,是构建镜像中最常用的方式就是Dockerfile。

Dockerfile

Dockerfile它是一种构建镜像的文本文件,文本内容中包含了一条条镜像所需的指令和说明。可以参考Dockerfile官方文档

Dockerfile介绍常用指令

FROM

语法:FROM <image>:<tag>
指明构建的新镜像是来自于哪个基础镜像,如果没有选择 tag,那么默认值为 latest。
FROM centos:7

MAINTAINER

语法:MAINTAINER <name>
指明镜像维护者及其联系方式(一般是邮箱地址)。官方说明已过时,推荐使用 LABEL。

MAINTAINER cyl <cyl@cyl.com>

LABEL

语法:LABEL <key>=<value> <key>=<value> <key>=<value> ...
功能是为镜像指定标签。也可以使用 LABEL 来指定镜像作者。

LABEL maintainer="cyl.com"

RUN

语法:RUN <command>
构建镜像时运行的 Shell 命令,比如构建的新镜像中我们想在 /usr/local 目录下创建一个 java 目录。

RUN mkdir -p /usr/local/java

ADD

语法:ADD <src>... <dest>
拷贝文件或目录到镜像中。src 可以是一个本地文件或者是一个本地压缩文件,压缩文件会自动解压。还可以是一个 url,如果把 src 写成一个 url,那么 ADD 就类似于 wget 命令,然后自动下载和解压。

ADD jdk-11.0.6_linux-x64_bin.tar.gz /usr/local/java

COPY

语法: COPY <src>... <dest>
拷贝文件或目录到镜像中。用法同 ADD,只是不支持自动下载和解压。

COPY jdk-11.0.6_linux-x64_bin.tar.gz /usr/local/java

EXPOSE

语法:EXPOSE <port> [<port>/<protocol>...]
暴露容器运行时的监听端口给外部,可以指定端口是监听 TCP 还是 UDP,如果未指定协议,则默认为 TCP。

EXPOSE 80 443 8080/tcp

如果想使得容器与宿主机的端口有映射关系,必须在容器启动的时候加上 -p 参数。

ENV

语法:ENV <key> <value> 添加单个,ENV <key>=<value> ... 添加多个。
设置容器内环境变量。

ENV JAVA_HOME /usr/local/java/jdk-11.0.6/

CMD

语法:

  • CMD ["executable","param1","param2"],比如:CMD ["/usr/local/tomcat/bin/catalina.sh", "start"]
  • CMD ["param1","param2"],比如:CMD [ "echo", "$JAVA_HOME" ]
  • CMD command param1 param2,比如:CMD echo $JAVA_HOME
    启动容器时执行的 Shell 命令。在 Dockerfile 中只能有一条 CMD 指令。如果设置了多条 CMD,只有最后一条 CMD 会生效。
CMD echo $JAVA_HOME

如果创建容器的时候指定了命令,则 CMD 命令会被替代。假如镜像叫 centos:7,创建容器时命令是:docker run -it --name centos7 centos:7 echo “helloworld” 或者 docker run -it --name centos7 centos:7 /bin/bash,就不会输出 $JAVA_HOME 的环境变量信息了,因为 CMD 命令被 echo “helloworld”、/bin/bash 覆盖了。

ENTRYPOINT

语法:

  • ENTRYPOINT ["executable", "param1", "param2"],比如:ENTRYPOINT ["/usr/local/tomcat/bin/catalina.sh", "start"]
  • ENTRYPOINT command param1 param2,比如:ENTRYPOINT ehco $JAVA_HOME

启动容器时执行的 Shell 命令,同 CMD 类似,不会被 docker run 命令行指定的参数所覆盖。在 Dockerfile 中只能有一条 ENTRYPOINT 指令。如果设置了多条 ENTRYPOINT,只有最后一条 ENTRYPOINT 会生效。

ENTRYPOINT echo $JAVA_HOME

如果在 Dockerfile 中同时写了 ENTRYPOINT 和 CMD,并且 CMD 指令不是一个完整的可执行命令,那么 CMD 指定的内容将会作为 ENTRYPOINT 的参数;
如果在 Dockerfile 中同时写了 ENTRYPOINT 和 CMD,并且 CMD 是一个完整的指令,那么它们两个会互相覆盖,谁在最后谁生效

WORKDIR

语法:WORKDIR /path/to/workdir
RUNCMDENTRYPOINT 以及 COPY AND 设置工作目录。

WORKDIR /usr/local

指定容器挂载点到宿主机自动生成的目录或其他容器。一般的使用场景为需要持久化存储数据时。

VOLUME

语法:VOLUME ["/var/lib/mysql"]

容器的 /var/lib/mysql 目录会在运行时自动挂载为匿名卷,匿名卷在宿主机的 /var/lib/docker/volumes 目录下

一般不会在 Dockerfile 中用到,更常见的还是在 docker run 的时候通过 -v 指定数据卷。

Docker Build基于Dockerfile构建镜像

1.根据指令编写Dockerfile文件

# 创建宿主机文件目录
sudo mkdir -p /docker/dockerfile
# 到目录下
cd /docker/dockerfile
# 编写Dockerfile文件
vim Dockerfile

Dockerfile文件内容如下:

# 指明构建的新镜像是来自于 centos:7 基础镜像
FROM centos:7
# 通过镜像标签声明了作者信息
LABEL maintainer="cyl.com"
# 设置工作目录
WORKDIR /usr/local
# 新镜像构建成功以后创建指定目录
RUN mkdir -p /usr/local/java && mkdir -p /usr/local/soft
# 拷贝文件到镜像中并解压
ADD  jdk-8u411-linux-x64.tar.gz /usr/local/java
COPY  demo-0.0.1-SNAPSHOT.jar /usr/local/soft
# 暴露容器运行时的 8080 监听端口给外部
EXPOSE 9080
# 设置容器内 JAVA_HOME 环境变量
ENV JAVA_HOME /usr/local/java/jdk-11.0.8/
ENV PATH $PATH:$JAVA_HOME/bin
# 指定容器启动时运行Java程序
CMD ["java","-jar","/usr/local/soft/demo-0.0.1-SNAPSHOT.jar"]

其中jdk-8u411-linux-x64.tar.gz和demo-0.0.1-SNAPSHOT.jar我都放在了/docker/dockerfile目录下,和Dockerfile同一个目录

2.构建镜像

Dockerfile 文件编写好以后,真正构建镜像时需要通过 docker build 命令。

# 使用当前目录的 Dockerfile 创建镜像
sudo docker build -t mycentos-01:7 .

在这里插入图片描述
执行sudo docker images可以查看制作的镜像,mycentos-01是我刚刚使用Dockerfile制作的
在这里插入图片描述
还可以通过执行以下命令构建镜像

# 通过 -f Dockerfile 文件的位置创建镜像
docker build -f /docker/dockerfile/Dockerfile -t mycentos:7 .

-f:指定要使用的 Dockerfile 路径;
–tag, -t:镜像的名字及标签,可以在一次构建中为一个镜像设置多个标签。

最后的 . 号含义是什么?

若是.号则意味着宿主机中的Dockerfile文件和Dockerfile其它文件是同在一个目录下,比如jdk-8u411-linux-x64.tar.gz和demo-0.0.1-SNAPSHOT.jar,由于它们都在一个目录下,所以最后加一个.
若是不在一个目录,比如我的宿主机 jdk 文件在 /root 目录下,Dockerfile 文件在 /usr/local/dockerfile 目录下,文件内容如下:

ADD jdk-8u411-linux-x64.tar.gz /usr/local/java

那么构建镜像时的命令就该这样写:

docker build -f /usr/local/dockerfile/Dockerfile -t mycentos:7 /root

3.启动容器

# 启动容器
sudo docker run -di --name mycentos1 -p 9080:9080  mycentos-01:7
# 主机直接调用Java程序接口,输出hello java即成功
curl ip:9080/index

总结

本文主要讲解了Docker Commit基于容器构建镜像和Docker Build基于Dockerfile构建镜像的两种方式,同时也介绍了Dockerfile的常用指令操作,一般推荐Dockerfile这种方式构建镜像,只需要在Dockerfile中写好构建所需的指令,非常灵活和方便!

  • 10
    点赞
  • 23
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
### 回答1: Docker是一种容器化技术,用于隔离应用程序和它们的依赖,并以轻量级和可移植的方式进行分发和部署。而Docker Compose和DockerfileDocker生态系统中常用的工具,用于管理和构建多个容器化应用程序。 Docker Compose是一个命令行工具,通过一个简单的文本文件(通常是YAML格式)来定义、配置和运行多个Docker容器。它提供了一种非常简便的方式来描述和管理各个容器之间的关联性,同时还能够一次性启动、停止和删除整个应用程序的所有容器。通过Docker Compose,我们可以轻松地创建和管理包含多个服务的复杂应用程序,例如前端应用程序和后端数据库。 Dockerfile是一个用于定义Docker镜像的文本文件,其中包含了构建镜像所需的指令和配置。通过编写Dockerfile,我们可以描述应用程序的运行环境、依赖关系和启动命令等信息。Docker通过读取Dockerfile并按照其中的指令逐步构建镜像,最终生成一个可执行的容器化应用程序。对于一个基于Nginx的Web应用程序,我们可以使用Dockerfile来定义Nginx的配置和静态资源,然后通过构建镜像来打包应用程序。 综上所述,docker-compose、Dockerfile和Nginx可以结合使用,实现多个容器之间的协同工作和复杂应用程序的构建。我们可以使用Docker Compose来管理包含Nginx容器的应用程序,通过Dockerfile来定义Nginx镜像的构建过程,最终实现一个可部署的Nginx容器化应用程序。这种方式能够提高应用程序的可移植性、可复用性和易于管理性,为开发人员和运维人员带来许多便利。 ### 回答2: docker-compose是一个可以管理多个容器的工具,它使用一个YAML文件来定义容器的配置信息。dockerfile是用来构建镜像的脚本文件,它包含了一系列的命令来描述容器的构建过程。nginx是一个开源的高性能的Web服务器和反向代理服务器。 使用docker-compose可以很方便地定义和管理多个容器之间的关系和依赖。可以在docker-compose.yaml文件中定义多个服务,每个服务对应一个容器,而这些容器可以通过互联网络进行通信。例如,可以定义一个nginx服务,同时还可以定义一个后端应用程序的服务,并且将两个服务连接在一起。使用docker-compose up命令可以启动所有定义的服务,并且可以使用docker-compose logs命令来查看日志信息。 dockerfile是一个用来描述构建镜像过程的文件,它包含了一系列的命令来指定容器中的操作。在dockerfile中可以使用FROM命令指定基础镜像,然后使用RUN命令来执行一些操作,比如安装软件包、配置环境等。对于nginx这个容器,可以使用dockerfile来构建自定义的镜像,并且可以在其中配置nginx的相关设置,例如端口、路由规则等。 通过使用docker-compose和dockerfile,可以很轻松地将nginx部署到容器中,并且可以定义nginx和其他服务之间的联系和依赖关系。这样可以更加方便地进行应用程序的部署和管理,同时也可以通过容器的隔离性和易于移植性来提高应用程序的安全性和可靠性。 ### 回答3: Docker Compose和Dockerfile是两个与Docker相关的重要概念,而Nginx则是一款常用的高性能Web服务器和反向代理服务器软件。 Docker Compose是一个用于定义和运行多个Docker容器的工具。它通过一个单独的YAML配置文件,可以定义容器之间的关系和依赖,并且可以一键式地启动、停止和管理这些容器。使用Docker Compose,我们可以方便地把多个服务组合在一起,比如前端应用、后端应用和数据库等。 Dockerfile是一个用于构建Docker镜像的文本文件。它包含一系列的指令,用于告诉Docker引擎如何构建镜像。通过Dockerfile,我们可以自定义镜像的内容和配置,包括基础镜像选择、软件安装、文件复制、环境变量设置等。Dockerfile的编写可以帮助我们实现镜像的自动化构建和版本管理。 Nginx是一款轻量级的高性能Web服务器和反向代理服务器软件。它具有占用资源少、处理并发请求能力强等特点,被广泛用于构建高性能的Web应用架构。通过使用Nginx,我们可以实现负载均衡、反向代理、静态文件缓存、SSL加密等功能。 结合这三个概念,我们可以运用Docker Compose来定义和管理多个容器,比如前端应用容器和Nginx容器。通过Dockerfile,我们可以定义Nginx容器的自定义镜像,包括选择基础镜像、安装Nginx和相关依赖、设置Nginx配置文件等。然后,通过Docker Compose一键式地启动这些容器,实现前端应用和Nginx服务器的整合。 总之,Docker Compose、Dockerfile和Nginx是三个在Docker应用开发和部署中非常重要的概念和工具。它们可以帮助我们方便地管理和构建容器,实现应用的快速部署和扩展。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值