Dockerfile ENTRYPOINT指令 语法解析

2023-11-11 23:18

本文主要是介绍Dockerfile ENTRYPOINT指令 语法解析,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

  系列博文之前讲解过RUNCMD,其中CMD可以作为容器启动时的默认命令使用,而ENTRYPOINT是位于CMD之上的命令,同样可以可以设置容器启动时的入口点,可以使用ENTRYPOINT做许多系统初始化级别的工作。

  ENTRYPOINT 语法

# exec形式,首选形式.
ENTRYPOINT ["executable", "param1", "param2"]
# shell形式.
ENTRYPOINT command param1 param2

  ENTRYPOINT 语义

  · ENTRYPOINT允许配置以可执行文件方式运行的容器。

  · 示例:

  如下命令使用默认内容启动Nginx,监听80端口:

docker run -i -t --rm -p 80:80 nginx

  · docker run <image>的命令行参数将追加到ENTRYPOINT中的所有参数之后,并将重写使用CMD指定的所有参数。这允许将参数传递到入口点,即docker run <image> -d将把-d参数传递给入口点。可以使用docker run --entrypoint来重写ENTRYPOINT指令。

  · shell形式禁止使用任何CMDRUN命令行参数,缺点是ENTRYPOINT作为/bin/sh -c的子命令启动,其不会传递信号。这意味着可执行文件将不是容器的PID 1,也不会接收Unix信号,因此可执行文件将不会从docker stop <container>接收SIGTERM

  · dockerfile中允许存在多个ENTRYPOINT指令,但仅最后一个ENTRYPOINT指令才会起作用。

  ENTRYPOINT exec形式 示例

  · 使用ENTRYPOINTexec形式设置相当稳定的默认命令和参数,使用CMD的任一形式设置额外的默认参数。

FROM ubuntu
ENTRYPOINT ["top", "-b"]
CMD ["-c"]

  · 当容器运行时,可以看到top是唯一的进程:

docker run --name securitit-nginx-entrypoint -it securitit-nginx-entrypoint:1.0.0.1

在这里插入图片描述

  · 为进一步确认结果,可以使用docker exec查看:

docker exec -it 285188694a00 ps aux

在这里插入图片描述

  · 可以优雅地查看top,并使用docker stop关闭。

  · 通过ENTRYPOINT运行Aapche

​  1) dockerfile配置如下,配置中安装内容较多,会比较慢。

FROM debian:stable
RUN apt-get update && apt-get install -y --force-yes apache2
EXPOSE 80 443
VOLUME ["/var/www", "/var/log/apache2", "/etc/apache2"]
ENTRYPOINT ["/usr/sbin/apache2ctl", "-D", "FOREGROUND"]

  2) 如果需要为可执行文件编写启动程序脚本,可以使用execgosu命令确保最终可执行文件接收到Unix信号。

#!/usr/bin/env bash
set -eif [ "$1" = 'postgres' ]; thenchown -R postgres "$PGDATA"if [ -z "$(ls -A "$PGDATA")" ]; thengosu postgres initdbfiexec gosu postgres "$@"
fiexec "$@"

  3) 最后,如果需要在关闭时执行一些额外的清理(或与其他容器通信),或者正在协调多个可执行文件,则需要确保ENTRYPOINT脚本接收到Unix信号,将其传递,然后执行更多的工作。

#!/bin/sh
# Note: I've written this using sh so it works in the busybox container too# USE the trap if you need to also do manual cleanup after the service is stopped,
#     or need to start multiple services in the one container
trap "echo TRAPed signal" HUP INT QUIT TERM# start service in background here
/usr/sbin/apachectl startecho "[hit enter key to exit] or run 'docker stop <container>'"
read# stop service and clean up here
echo "stopping apache"
/usr/sbin/apachectl stopecho "exited $0"

  · 可以使用--entrypoint重写ENTRYPOINT设置,但这只能将二进制文件设置为exec(不使用sh -c)。

  · exec 形式是按照JSON Array格式解析,意味着必须是使用双引号(")包含参数,而不能使用单引号(’)。

  ·shell形式不同,exec形式不会调用shell命令行,意味着不会进行shell处理。例如:运行RUN [ "echo", "$HOME" ]不会对$HOME进行变量替换。如果需要shell处理,那么可以使用shell形式或直接执行shell,例如:ENTRYPOINT["sh","-c","echo $HOME"]。当使用exec形式直接执行shell时,与shell形式类似,应用的shell是宿主机而非Docker。

  ENTRYPOINT shell形式 示例

  · shell形式可以为ENTRYPOINT指定文本,运行在/bin/sh -c中。这种形式将使用shell处理,替换掉shell环境变量,同时会忽略掉所有CMDdocker run命令行参数。

  · 为确保docker stop能够正确地向任何长时间运行的ENTRYPOINT 可执行文件发出信号,谨记用exec启动它,例如:

FROM ubuntu
ENTRYPOINT exec top -b

  · 当运行上面dockerfile生成的镜像时,将会看到唯一的PID 1的进程:

docker run --name securitit-nginx-entrypoint -it securitit-nginx-entrypoint-shell:1.0.0.1

在这里插入图片描述

  · 如果ENTRYPOINT后忘了加exec,那么ENTRYPOINT可能会不是PID 1进程。

  CMD与ENTRYPOINT协作

​  · CMDENTRYPOINT指令都定义了运行容器时执行的命令。关于CMDENTRYPOINT的协作描述很少。

  1) dockerfile应至少指定一个CMDENTRYPOINT命令。

  2) 将容器用作可执行文件时,应定义ENTRYPOINT

  3) CMD应该用作定义ENTRYPOINT指令或ad-hoc指令的默认参数。

  4) 使用可替代参数运行容器时,CMD会被重写。

  · 下表列举了对不同的CMDENTRYPOINT组合执行的命令:

无ENTRYPOINT指令ENTRYPOINT exec_entry p1_entryENTRYPOINT [“exec_entry”, “p1_entry”]
无CMD指令错误,必须包含CMD和ENTRYPOINT其中一个/bin/sh -c exec_entry p1_entryexec_entry p1_entry
CMD [“exec_cmd”, “p1_cmd”]exec_cmd p1_cmd/bin/sh -c exec_entry p1_entryexec_entry p1_entry exec_cmd p1_cmd
CMD [“p1_cmd”, “p2_cmd”]p1_cmd p2_cmd/bin/sh -c exec_entry p1_entryexec_entry p1_entry p1_cmd p2_cmd
CMD exec_cmd p1_cmd/bin/sh -c exec_cmd p1_cmd/bin/sh -c exec_entry p1_entryexec_entry p1_entry /bin/sh -c exec_cmd p1_cmd

  总结

  RUNCMDENTRYPOINT是比较主要的操作指令,可以在构建镜像时,根据需求进行定制。本文是参考Docker官网文档所写。

  若文中存在错误和不足,欢迎指正!

这篇关于Dockerfile ENTRYPOINT指令 语法解析的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/393474

相关文章

R语言中的正则表达式深度解析

《R语言中的正则表达式深度解析》正则表达式即使用一个字符串来描述、匹配一系列某个语法规则的字符串,通过特定的字母、数字及特殊符号的灵活组合即可完成对任意字符串的匹配,:本文主要介绍R语言中正则表达... 目录前言一、正则表达式的基本概念二、正则表达式的特殊符号三、R语言中正则表达式的应用实例实例一:查找匹配

java中的Supplier接口解析

《java中的Supplier接口解析》Java8引入的Supplier接口是一个无参数函数式接口,通过get()方法延迟计算结果,它适用于按需生成场景,下面就来介绍一下如何使用,感兴趣的可以了解一下... 目录1. 接口定义与核心方法2. 典型使用场景场景1:延迟初始化(Lazy Initializati

C#中预处理器指令的使用小结

《C#中预处理器指令的使用小结》本文主要介绍了C#中预处理器指令的使用,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧... 目录 第 1 名:#if/#else/#elif/#endif✅用途:条件编译(绝对最常用!) 典型场景: 示例

Springboot配置文件相关语法及读取方式详解

《Springboot配置文件相关语法及读取方式详解》本文主要介绍了SpringBoot中的两种配置文件形式,即.properties文件和.yml/.yaml文件,详细讲解了这两种文件的语法和读取方... 目录配置文件的形式语法1、key-value形式2、数组形式读取方式1、通过@value注解2、通过

C++ 右值引用(rvalue references)与移动语义(move semantics)深度解析

《C++右值引用(rvaluereferences)与移动语义(movesemantics)深度解析》文章主要介绍了C++右值引用和移动语义的设计动机、基本概念、实现方式以及在实际编程中的应用,... 目录一、右值引用(rvalue references)与移动语义(move semantics)设计动机1

MySQL 筛选条件放 ON后 vs 放 WHERE 后的区别解析

《MySQL筛选条件放ON后vs放WHERE后的区别解析》文章解释了在MySQL中,将筛选条件放在ON和WHERE中的区别,文章通过几个场景说明了ON和WHERE的区别,并总结了ON用于关... 今天我们来讲讲数据库筛选条件放 ON 后和放 WHERE 后的区别。ON 决定如何 "连接" 表,WHERE

Mybatis的mapper文件中#和$的区别示例解析

《Mybatis的mapper文件中#和$的区别示例解析》MyBatis的mapper文件中,#{}和${}是两种参数占位符,核心差异在于参数解析方式、SQL注入风险、适用场景,以下从底层原理、使用场... 目录MyBATis 中 mapper 文件里 #{} 与 ${} 的核心区别一、核心区别对比表二、底

Agent开发核心技术解析以及现代Agent架构设计

《Agent开发核心技术解析以及现代Agent架构设计》在人工智能领域,Agent并非一个全新的概念,但在大模型时代,它被赋予了全新的生命力,简单来说,Agent是一个能够自主感知环境、理解任务、制定... 目录一、回归本源:到底什么是Agent?二、核心链路拆解:Agent的"大脑"与"四肢"1. 规划模

MySQL字符串转数值的方法全解析

《MySQL字符串转数值的方法全解析》在MySQL开发中,字符串与数值的转换是高频操作,本文从隐式转换原理、显式转换方法、典型场景案例、风险防控四个维度系统梳理,助您精准掌握这一核心技能,需要的朋友可... 目录一、隐式转换:自动但需警惕的&ld编程quo;双刃剑”二、显式转换:三大核心方法详解三、典型场景

JAVA项目swing转javafx语法规则以及示例代码

《JAVA项目swing转javafx语法规则以及示例代码》:本文主要介绍JAVA项目swing转javafx语法规则以及示例代码的相关资料,文中详细讲解了主类继承、窗口创建、布局管理、控件替换、... 目录最常用的“一行换一行”速查表(直接全局替换)实际转换示例(JFramejs → JavaFX)迁移建