English 中文(简体)
CTRL+ C 难道没有杀死“谁跑”指挥?
原标题:Why with some docker images, CTRL+C doesn t kill the "docker run" command?
  • 时间:2023-06-12 14:25:51
  •  标签:
  • docker
The bounty expires in 6 days. Answers to this question are eligible for a +500 reputation bounty. gremo is looking for an answer from a reputable source:
Please provide a source and maybe a solution

有了这一形象(Cady网络服务器):

docker run --rm -p 80:80 caddy:latest 

我可以停止在终端内发送CTRL+C。

其他一些图像以这种方式取得了成功。 MariaDB:

docker run -it --rm -p 3306:3306 -e MARIADB_ALLOW_EMPTY_ROOT_PASSWORD=true mariadb:latest

I m 无法用CTRL+C停止。

I ve notesd that in Caddy Dockerfile 没有ENTRYPOINT,但只有CMD/code>,而Maria 亚洲开发银行有<条码>ENTRYPOINT和<条码>。

为什么? 是否有任何理由支持处理杀人信号:? 如果是原因,怎么能支持cker锁切入点的<代码>SIGTERM?

问题回答

但是,我很想知道官方形象如何解决问题。

Don tabes: Docker 1.13 。

Any image run with docker run --init would include an init inside the container that forwards signals and reaps processes.
As mentioned here, tini works transparently, Dockerfiles don t need to be modified in any way.

因此,在Unix系统中,当你在码头上报CTRL+C时,将“SIG(Signal Interrupt)发给地下加工组,在这种情况下,是Docker集装箱。 如果您使用<条码>CTRL+,则发送<条码>SIGQUIT,如果您使用<条码>CTRL+Z,则发送<条码>SIGTSTP(传真号码)。

Docker containers run a single main process, and this process runs in PID 1.
PID 1 is special on Linux: it is the first process that runs and is the ancestor of all other processes.
It also has a special relationship with Unix signals: it is the only process that can choose to ignore SIGINT and SIGTERM. Other processes cannot ignore these signals, but they can have handlers that execute when they receive them.

In Docker, when you use CMD to specify the process to run, Docker will wrap that process with a small init system (like tini), which properly handles Unix signals and forwards them to the main process (I mentioned it originally here).
This is why your caddy image, which does not have an ENTRYPOINT and only has CMD, can handle the CTRL+C.

然而,当你使用<条码>ENTRYPOINT时,Docker没有用这个小型<代码>in系统对这一过程进行总结,而这一过程则作为PID 1进行。

如果程序没有为<代码>SIGINT或SIGTERM建立,则不会对<代码>CTRL+C做出答复。 因此,mariadbindex, which has an ENTRYPOINT, do not end when You press CTRL+C

处理杀人信号是gracefuldown的一个重要部分。 当一个过程收到<代码>SIGTERM(或<编码>SIGINT时,它就应停止接受新的工作,完成其目前的工作,然后退出。 这使它能够清理它使用的任何资源,并确保数据的一致性。

如果程序没有处理这些信号,而且只是被杀(有<代码>SIGKILL),那么它就没有机会清理,并且可能将资源留给一个不一致的国家。 在MariaDB这样的数据库中,这种情况可能有害,因为MariaDB可能会有未经处理的交易或部分书面数据。

为了支持在Docker入境点处理杀人信号,你可以:

  1. 在条目编号上添加处理信号。 这需要修改文字,如果切入点是双亲,则可能不可行。

  2. 利用<代码>in系统处理信号并将其传送到主要程序。 为此设计的有小的<代码>init/code>,如tini。 您可在您的Dockerfile中加以利用。

    FROM your-base-image
    RUN apt-get update && apt-get install -y tini
    ENTRYPOINT ["/usr/bin/tini", "--", "your-command"]
    

    这将作为PID1运行tini,处理信号并将信号转交你指挥。

  3. 使用Dockers的内装,这是最低限度的tini执行。 您可使用<代码>-init。 您经营集装箱时的选择:

    docker run --init -it --rm -p 3306:3306 -e MARIADB_ALLOW_EMPTY_ROOT_PASSWORD=true mariadb:latest
    

    这将把Docker的内装成PID1,处理信号并将其转发给MariaDB。

这些方法确保你的Docker入境点能够处理杀人信号,并在必要时进行可耻的关闭。


NOT是否有理由支持处理杀人信号?

勿庸置疑,除非你希望你的形象真实:

  • simple, for a very simple or short-lived processes, with no need of signal handling
  • fast, to avoid any shutdown signals during critical sections of their code
  • resilient, when you want to prevent unwanted or unauthorized shutdown.

但一般来说,无视终止信号可能导致诸如数据损失、资源流失或立案程序等问题,应当避免。


剩下的唯一事情是:如果不支持关闭信号,那么像MariaDB一样,服务就有些危险,为什么MariaDB本身不直接支持它?

This could be for a legacy reason, inherited from MySQL, which MariaDB is a fork of. MySQL was developed before Docker existed, and in a traditional server environment, it s less common for a process to receive a SIGINT. It s more common for a process to receive a SIGTERM when the system is shutting down, which MySQL and MariaDB do handle.
Its entrypoint reflects that, and you run it with --init to ensure a basic SIGINT support.

But keep in mind it is not the only issue. I made the mistake of running a MariaDB instance on an Azure ACI (container) instead of AKS (Kubernetes).
When an ACI closes (at least when I used it in 2021), it sends... a SIGKILL (a signal which cannot be caught, blocked, or ignored). When the kernel sends a SIGKILL to a process, that process is immediately terminated, and it doesn t get a chance to clean up or do any other work before it s killed.

因此,不管你的形象是否支持可耻的关闭,都铭记你的执行环境,这首先可能不允许任何可耻的关闭。

MariaDB忽略了SIGINT,用<代码>掩盖其向程序交付的内容。

很久以前,就是因为一些假设可能围绕着在终点站启动时意外触发关闭。 在旧学校史册中可能会出现这样的情况,即:在<条码>后一个封闭的终点站可能已经交付了一个SIGINT到<条码>。 我可以参看任何要求去除SIGINT罩。

在集装箱内,条目编号execsmariadbd 服务器在基本安装后可执行,因此忽视<条码>SIGINT的行为是历史上的,而不是明确的决定。

-gdb关于指挥线(服务器或集装箱)的选择将防止无视SIGINT,并使SIGINT安全终止MariaDB。 也可在档案中提供。

MariaDB可以在任何时候处理解雇问题,包括SIGKILL(除非是疏忽过程)或权力失败。 这是交易数据库的耐久性的一部分(ACID的D)。 重新启动后,清理了未结算的交易。 令人宽慰的终止并不意味着起步就不需要一次坠毁的恢复,而是需要更快的时间。





相关问题
Unable to connect to docker container inside windows server

As title. I am developing a system with many docker images with ASP.Net MVC core projects. I am publishing these docker images into a docker engine installed on Windows Server OS, and I found that I ...

Only can see postgreSQL as an admin

After installed Wsl and Docker, can t access PSQL and other things. I was studying Docker, and installed the latest version. So far so good, I received an error about the WSL version, saw some ...

make docker-compose block until healthy without `depends_on`

I am working with a team that uses docker-compose to start a set of helper services, but does not use docker when the code is being developed. Here, docker-compose is just a convenient way to run the ...

change grafana port using docker host network

I am trying to spin up a grafana container in docker, however my setup in docker does not allow ipv4 forwarding and thus I cannot use the default bridge network in docker. All I can use is the host ...

Pip instalation for Python 3.11 in docker

I have Dockerfile to build image for Django project that uses Python 3.11 and runs in poetry environment (see content below). Problem is when I try to donwload get-pip.py file and run it using Python, ...

在 Dockerfile 中运行 composer install

我正在尝试将我的Laravel应用程序进行Docker化。 该应用程序已经构建并在Git中,但我将vendor文件夹添加到了.gitignore中。 我添加了一个Dockerfile,看起来像这样: FROM php:7.1-fpm-alpine RUN apk update ...

热门标签