V2EX = way to explore
V2EX 是一个关于分享和探索的地方
现在注册
已注册用户请  登录
chaker
V2EX  ›  Docker

docker exec 执行和在 ENTRYPOINT 里执行有什么区别

  •  
  •   chaker · 2021-08-12 09:09:08 +08:00 · 2306 次点击
    这是一个创建于 1231 天前的主题,其中的信息可能已经有所发展或是发生改变。

    做了个镜像,尝试两种启动方式,一种正常启动,一种启动到一半就直接退出了,啥原因呢?

    不能正常启动的方式

    `$ cat Dockerfile

    ...

    WORKDIR /WORKSPACE

    ...

    ENTRYPOINT ./start_server.sh `

    执行启动命令

    docker run --gpus all --name=XXX -it XXXIMG

    服务初始化到一半就直接崩掉了,日志里看不到错误信息

    可以正常启动的方式

    `$ cat Dockerfile

    ...

    WORKDIR /WORKSPACE

    ...

    #ENTRYPOINT ./start_server.sh `

    执行两步启动命令

    docker run --gpus all --name=XXX -it XXXIMG

    docker exec -it xx /bin/bash -c /workspace/start_server.sh

    服务一切正常,如预期。

    想问下这两种方式有什么区别呢? docker inspect 也看不出异常。和 stdin 、stdout 之类的有关系吗? 谢谢。

    20 条回复    2021-08-12 18:34:47 +08:00
    gux928
        1
    gux928  
       2021-08-12 09:14:43 +08:00 via iPhone
    我之前遇到过从 entrypoint 启动脚本,程序代码中的相对目录会有问题。
    chaker
        2
    chaker  
    OP
       2021-08-12 09:21:54 +08:00
    @gux928 不是相对目录的问题,我后来把这些目录都写成绝对路径也不行
    passerbytiny
        3
    passerbytiny  
       2021-08-12 09:29:24 +08:00 via Android
    ENTRYPOINT 不定义的时候,容器启动起来就是个操作系统;定义的时候,容器启动时是先启动操作系统再执行 ENTRYPOINT 。你的两种方式在启动顺序上一样,但是执行脚本时的${PWD} 不一样。
    thet
        4
    thet  
       2021-08-12 09:32:07 +08:00
    ENTRYPOINT 是在 docker run 后就会在容器执行的命令,后续的追加的命令只能作为参数,比如我把 redis-server 作为 ENTRYPOINT,那么 docker run 后只能追加 --port 之类的参数了,新的二进制命令是执行不了的。k8s 中 Command 可以替换 ENTRYPOINT
    freevioce
        5
    freevioce  
       2021-08-12 09:33:05 +08:00
    @chaker 肯定是第一种好点 就一步 ,猜测是第二种 加载 bash 加载了必须的环境变量 对比下两种的环境变量看看
    lcdtyph
        6
    lcdtyph  
       2021-08-12 09:35:34 +08:00 via iPhone
    shell 形式的 entrypoint 等价于
    [ /bin/sh, -c, xxx.sh ]
    /bin/sh 不一定是 bash
    amrnxcdt
        7
    amrnxcdt  
       2021-08-12 09:52:36 +08:00 via Android
    用“bash -x ./start_serve.sh”启动,看停止在哪一行。
    chaker
        8
    chaker  
    OP
       2021-08-12 09:53:48 +08:00
    @lcdtyph 用 docker inspect 看了下,ERTRYPOINT 里默认写的确实是 /bin/bash,我用的 tensorflow 的官方镜像
    chaker
        9
    chaker  
    OP
       2021-08-12 09:55:55 +08:00
    @passerbytiny @freevioce 对比了下,第一种方式里少了 PWD 、SHLVL 、PS1 、_和 LS_COLOR 这几个量,其他变量都是一样的,感觉不是他们的问题
    chaker
        10
    chaker  
    OP
       2021-08-12 09:58:00 +08:00
    @amrnxcdt start_serve.sh 里面其实就执行了一行 python server.py start,停在了一个加载 cdll 的地方,但是这个程序不应该在这里停,路径都是绝对路径,毕竟第二种方式都能起来。
    freevioce
        11
    freevioce  
       2021-08-12 10:06:04 +08:00
    @chaker 你把 ENTRYPOINT 改成 /bin/sh 再 docker run -it .... 进入到 sh 执行 start_server.sh 看看能执行不
    chaker
        12
    chaker  
    OP
       2021-08-12 10:13:29 +08:00
    @freevioce 没有问题,可以运行,好像是只要分成两步就没问题,想一步起来就是不可以
    AoEiuV020
        13
    AoEiuV020  
       2021-08-12 11:13:25 +08:00
    我一般不配置 ENTRYPOINT 而是配置 CMD,可以试一下 CMD,
    ENTRYPOINT 就默认的 bash -c,
    Symo
        14
    Symo  
       2021-08-12 11:19:46 +08:00
    主要是用途不一样, ENTRYPOINT 可以做一些初始化的工作, 但是也需要有能力处理 CMD 传进来的参数.

    #!/usr/bin/env sh

    set -e
    if [ "$1" = '/etc/init/docker-entrypoint.sh' ] && [ "$(id -u)" = '0' ]; then
    dbus-daemon --config-file=/usr/share/dbus-1/system.conf --print-address
    echo "☆☆☆☆☆ base service has started. ☆☆☆☆☆"
    exec gosu www-data "$0" "$@"
    fi
    exec "$@"

    比如说我想在容器启动的时候预先运行 dbus, 那这个就可以写在 ENTRYPOINT, 然后容器执行的 CMD 也会传递到里面, 所以判断一下如果不是来自 docker-entrypoint.sh 执行的命令, 就直接执行
    maxbon
        15
    maxbon  
       2021-08-12 11:41:53 +08:00
    docker 需要一个持久侦听的命令,你可以在脚本里面加个死循环来实现,不然就会挂掉
    jingslunt
        16
    jingslunt  
       2021-08-12 12:15:52 +08:00
    我是这么做的,用 shc 先把 shell 文件压缩成二进制执行文件,这时候执行旧无需考虑 sh 环境变量问题
    luhuisicnu
        17
    luhuisicnu  
       2021-08-12 12:20:11 +08:00
    区别在于守护进程不一样,dockerd, k8s 通过 entripoint 启动的进程来判断应用健康,这里面有很多自动化的东西可以做
    chaker
        18
    chaker  
    OP
       2021-08-12 13:25:56 +08:00
    @AoEiuV020 尝试过了,不行;D
    chaker
        19
    chaker  
    OP
       2021-08-12 13:27:35 +08:00
    @Symo 是这样,也做了些尝试,exec 和 shell 模式都尝试过,也试过只用 cmd,都不行
    NathanInMac
        20
    NathanInMac  
       2021-08-12 18:34:47 +08:00
    printenv 对比一下就知道了
    关于   ·   帮助文档   ·   博客   ·   API   ·   FAQ   ·   实用小工具   ·   1731 人在线   最高记录 6679   ·     Select Language
    创意工作者们的社区
    World is powered by solitude
    VERSION: 3.9.8.5 · 25ms · UTC 16:37 · PVG 00:37 · LAX 08:37 · JFK 11:37
    Developed with CodeLauncher
    ♥ Do have faith in what you're doing.