You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在GitHub Action中调用前序步骤启动的Docker容器执行命令?

GitHub Action中Docker容器复用与测试命令执行问题解决

问题场景

我在构建GitHub Action工作流时,希望启动WildFly Docker容器后,执行Python脚本向容器发送HTTP请求做集成测试,但推送代码后发现Docker镜像构建成功,后续的Python脚本步骤始终无法执行,推测是因为WildFly容器一直处于运行状态,导致前序步骤无法结束。

原工作流配置:

on: [push]

jobs:
  ci_test_job:
    runs-on: ubuntu-latest
    name: CI Test
    steps:
    - name: Start Wildfly container for integration test
      id: start-wildfly
      uses: user/dict/ci-test@master
    - name: Run Python script
      run: python3 -m unittest discover -s uat/

对应的自定义Action配置:

name: 'Continuous Integration Test'
description: 'Docker Container used for integration test'
runs:
  using: 'docker'
  image: 'Dockerfile'

Dockerfile代码:

FROM jboss/wildfly:latest
RUN wildfly/bin/add-user.sh -u admin -p admin --silent
ENTRYPOINT ["/opt/jboss/wildfly/bin/standalone.sh", "-c", "standalone.xml", "-Djboss.http.port=8080", "-Djboss.management.http.port=9998", "-b", "0.0.0.0", "-bmanagement", "0.0.0.0"]

问题原因

使用docker类型的自定义Action时,容器会以ENTRYPOINT指定的命令启动,而WildFly的启动命令是长期运行的进程,会导致该步骤一直处于阻塞状态,永远不会结束,后续的Python脚本步骤自然无法执行。同时,这种方式启动的容器和后续步骤不在同一个环境上下文,即使步骤能结束,后续步骤也无法直接访问容器。

解决方案

方案一:直接在工作流中用Docker命令后台启动容器

放弃自定义Docker Action,直接在工作流步骤中通过docker命令后台启动容器,完成测试后再清理容器,具体配置如下:

on: [push]

jobs:
  ci_test_job:
    runs-on: ubuntu-latest
    name: CI Test
    steps:
    - name: 拉取代码
      uses: actions/checkout@v4
    - name: 构建WildFly测试镜像
      run: docker build -t wildfly-test .
    - name: 后台启动WildFly容器
      run: docker run -d -p 8080:8080 -p 9998:9998 --name wildfly-test-container wildfly-test
    - name: 等待WildFly服务就绪
      run: |
        until curl -s http://localhost:8080 > /dev/null; do
          echo "等待WildFly启动..."
          sleep 5
        done
    - name: 执行Python测试脚本
      run: python3 -m unittest discover -s uat/
    - name: 停止并清理容器
      run: docker stop wildfly-test-container && docker rm wildfly-test-container

关键说明:

  • 使用docker run -d参数让容器在后台运行,避免阻塞步骤
  • 添加等待步骤,确保WildFly服务完全启动后再执行测试(避免因服务未就绪导致测试失败)
  • 测试完成后显式停止并删除容器,清理环境

方案二:修改自定义Action为复合Action(可选)

如果想保留自定义Action的结构,可以将其改为复合Action,在Action内部后台启动容器,然后让步骤结束,后续步骤复用容器:

自定义Action的action.yml修改为:

name: 'Continuous Integration Test'
description: 'Docker Container used for integration test'
runs:
  using: 'composite'
  steps:
    - name: Build WildFly image
      run: docker build -t wildfly-test .
      shell: bash
    - name: Start WildFly container
      run: docker run -d -p 8080:8080 -p 9998:9998 --name wildfly-test-container wildfly-test
      shell: bash
    - name: Wait for WildFly ready
      run: |
        until curl -s http://localhost:8080 > /dev/null; do
          echo "Waiting for WildFly to start..."
          sleep 5
        done
      shell: bash

然后工作流中使用该Action:

on: [push]

jobs:
  ci_test_job:
    runs-on: ubuntu-latest
    name: CI Test
    steps:
    - name: Checkout code
      uses: actions/checkout@v4
    - name: Start Wildfly container for integration test
      uses: user/dict/ci-test@master
    - name: Run Python script
      run: python3 -m unittest discover -s uat/
    - name: Cleanup container
      run: docker stop wildfly-test-container && docker rm wildfly-test-container

这种方式将容器启动逻辑封装在复合Action中,同样通过后台启动容器避免步骤阻塞,后续步骤可以直接访问本地端口与容器通信。

内容的提问来源于stack exchange,提问作者Rui

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.12 15:41:13