运行 bash dockerfile 中的脚本

Running bash script in a dockerfile

我正尝试在一个 bash 脚本中 运行 多个 js 文件,就像这样。这是行不通的。容器出现但没有 运行 脚本。然而,当我 ssh 到容器和 运行 这个脚本时,脚本 运行 很好,节点服务出现了。谁能告诉我我做错了什么?

Docker 文件

FROM node:8.16

MAINTAINER Vivek

WORKDIR /a

ADD . /a
RUN cd /a && npm install

CMD ["./node.sh"]

脚本如下

node.sh

#!/bin/bash

set -e

node /a/b/c/d.js &

node /a/b/c/e.js &

正如@hmm 提到的,您的脚本可能是 运行,但您的容器并没有等待您的两个子进程完成。

您可以将 node.sh 更改为:

#!/bin/bash

set -e

node /a/b/c/d.js &
pid1=$!

node /a/b/c/e.js &
pid2=$!

wait pid1
wait pid2

查看 以获得更通用的等待子流程完成的解决方案。

正如@DavidMaze 所提到的,容器通常应该 运行 一个 "service"。当然,由您决定在您的系统中什么构成服务。正如 docker 官方描述的那样:

It is generally recommended that you separate areas of concern by using one service per container. That service may fork into multiple processes (for example, Apache web server starts multiple worker processes). It’s ok to have multiple processes, but to get the most benefit out of Docker, avoid one container being responsible for multiple aspects of your overall application.

有关详细信息,请参阅 https://docs.docker.com/config/containers/multi-service_container/

通常您应该 运行 容器中只有一个进程。但是,您可以 运行 来自单个图像的任意数量的容器,并且很容易设置容器启动时 运行 的命令。

将图像的 CMD 设置为您认为最常见的路径:

CMD ["node", "b/c/d.js"]

如果您为此使用 Docker Compose,您可以为两个容器指定 build: .,但在第二个容器中,指定备用 command:.

version: '3'
services:
  node-d:
    build: .
  node-e:
    build: .
    command: node b/c/e.js

使用 bare docker run 你可以在图像名称后指定一个备用命令

docker build -t me/node-app .
docker run -d --name node-d me/node-app
docker run -d --name node-e me/node-app \
  node b/c/e.js

这让您可以为每个容器独立设置重启策略;如果你 运行 在像 Docker Swarm 或 Kubernetes 这样的集群环境中,你也可以独立地扩展这两个 containers/pods/processes。