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

Testcontainers中Mongo初始化脚本执行失败问题排查

Testcontainers MongoDB集成测试:解决初始化脚本"not primary"问题

问题根源

你遇到的问题确实是初始化脚本执行时机早于副本集就绪。Testcontainers启动的MongoDB默认以副本集模式运行,而/docker-entrypoint-initdb.d/下的脚本会在MongoDB进程启动后立即执行,此时副本集还没完成节点选举,当前节点还不是primary,执行创建用户、写入数据等操作就会触发"not primary"异常。

正确的初始化脚本内容

核心是在脚本开头加入等待副本集primary节点就绪的逻辑,确保后续操作在主节点可用时执行:

// 等待副本集primary节点就绪
function waitForPrimary() {
    while (true) {
        const status = rs.status();
        // status.ok=1表示副本集状态正常,myState=1表示当前节点是primary
        if (status.ok === 1 && status.myState === 1) {
            break;
        }
        print("等待副本集primary节点就绪...");
        sleep(1000); // 每秒检查一次
    }
}

// 先等待就绪,再执行初始化操作
waitForPrimary();

// 创建管理员用户(示例)
db.getSiblingDB("admin").createUser({
    user: "admin",
    pwd: "admin@123",
    roles: [{ role: "root", db: "admin" }]
});

// 预填充业务数据(示例)
const myDb = db.getSiblingDB("my_test_db");
myDb.users.insertOne({
    username: "test_user",
    email: "test@example.com"
});

额外注意事项

  • Testcontainers的MongoDB容器会自动完成副本集的初始化配置,不需要在脚本中手动执行rs.initiate()
  • 如果你的测试代码中自定义了副本集名称,脚本中的rs.status()会自动识别,无需额外修改
  • 脚本中的sleep()是MongoDB shell内置函数,无需额外依赖

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.26 00:52:10