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

如何在Node.js中等待Docker Compose容器就绪后执行测试?

Node.js中等待Docker Compose容器就绪的优雅方案

不用硬编码休眠时间,有几种更可靠的方式实现脚本等待容器就绪后再执行测试:

1. 利用Docker健康检查+轮询容器状态

首先在你的docker-compose.yml中为目标服务配置健康检查,让Docker自动检测服务是否就绪:

services:
  your-test-service:
    image: your-service-image
    healthcheck:
      # 示例:检查HTTP服务的健康接口
      test: ["CMD", "curl", "-f", "http://localhost:8080/health"]
      interval: 3s  # 每隔3秒检查一次
      timeout: 3s   # 超时时间
      retries: 5    # 重试5次后标记为不健康

然后在Node.js脚本中轮询容器的健康状态,直到目标服务进入healthy状态:

import { execSync } from "node:child_process";
import { setTimeout } from "node:timers/promises";

async function waitForHealthyService(serviceName) {
  while (true) {
    try {
      // 获取健康状态的服务名称
      const healthyServices = execSync(
        `docker compose ps --filter health=healthy --format "{{.Name}}"`
      ).toString().trim().split("\n");
      if (healthyServices.includes(serviceName)) {
        break;
      }
    } catch (err) {
      // 忽略执行错误,继续轮询
    }
    await setTimeout(1000);
  }
}

// 使用流程
execSync("docker compose up -d");
await waitForHealthyService("your-test-service");
// 这里开始执行集成测试

2. 直接检测服务的端口或接口

如果不想配置Docker健康检查,可以直接在Node.js中尝试连接服务端口或者调用健康接口,直到成功:

检测端口是否可连接

import { execSync } from "node:child_process";
import { createConnection } from "node:net";
import { setTimeout } from "node:timers/promises";

async function waitForPort(host, port) {
  while (true) {
    try {
      await new Promise((resolve, reject) => {
        const socket = createConnection({ host, port }, () => {
          socket.end();
          resolve();
        });
        socket.on("error", reject);
      });
      break;
    } catch (err) {
      await setTimeout(1000);
    }
  }
}

// 使用流程
execSync("docker compose up -d");
await waitForPort("localhost", 8080);
// 启动测试

检测HTTP健康接口

async function waitForHealthEndpoint(url) {
  while (true) {
    try {
      const res = await fetch(url);
      if (res.ok) break;
    } catch (err) {
      // 忽略连接错误,继续重试
    }
    await setTimeout(1000);
  }
}

// 使用流程
await waitForHealthEndpoint("http://localhost:8080/health");

3. 使用Docker Compose的--wait参数(推荐,需版本2.10+)

如果你的Docker Compose版本在2.10及以上,可以直接使用--wait参数,这个命令会自动阻塞直到所有服务进入健康状态,无需额外编写轮询逻辑:

import { execSync } from "node:child_process";

// 执行后会一直阻塞,直到所有服务就绪
execSync("docker compose up -d --wait");
// 直接开始测试

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.23 10:05:19