如何使用FluentDocker连接MongoDB并解决连接超时问题
问题原因及解决方案
核心错误点
- 端口映射配置错误:MongoDB容器内部默认监听
27017端口,你当前代码中ExposePort(27018)仅声明暴露容器的27018端口,既没有和容器内实际服务端口绑定,也没有映射到宿主机端口。FluentDocker的ExposePort方法需要传入两个参数,格式为ExposePort(宿主机端口, 容器内部服务端口) - 端口等待逻辑错误:
WaitForPort("27018/tcp", 30000)等待的是容器内部的27018端口,但MongoDB根本没有监听该端口,所以即使等待逻辑执行完成,实际服务也没有被正确检测。 - 可选优化:MongoDB初始化的root用户默认属于
admin认证库,连接字符串建议补充authSource=admin参数,避免权限认证失败。
修正后代码
[Fact] public async Task TestMongoDbConnection3() { const string root = "root"; const string secret = "secret"; // 定义宿主机端口和容器内部端口,避免硬编码出错 const int hostPort = 27018; const int containerPort = 27017; using ( var container = new Builder().UseContainer() .UseImage("mongo") .WithEnvironment($"MONGO_INITDB_ROOT_USERNAME:{root}") .WithEnvironment($"MONGO_INITDB_ROOT_PASSWORD:{secret}") // 修正:将宿主机27018端口映射到容器内部27017端口 .ExposePort(hostPort, containerPort) // 修正:等待容器内部的MongoDB服务端口27017 .WaitForPort($"{containerPort}/tcp", 30000 /*30s*/) .Build() .Start()) { var config = container.GetConfiguration(true); Assert.Equal(ServiceRunningState.Running, config.State.ToServiceState()); // 修正:补充authSource=admin指定认证库 var connectionString = $"mongodb://{root}:{secret}@localhost:{hostPort}/?authSource=admin"; // insert data const string collectionName = "Users"; var mongoClient = new MongoClient(connectionString); var database = mongoClient.GetDatabase ("Users"); var collection = database.GetCollection<User>(collectionName); const int id = 1; var data = new Fixture().Build<User>() .With(x => x.Id, id) .Create(); await collection.DeleteOneAsync(x => x.Id == data.Id); ... } }
额外说明
如果你的运行环境是WSL2、虚拟机或者远程Docker服务,需要确认宿主机27018端口没有被其他服务占用,同时Docker daemon的端口暴露规则允许本地访问。不需要使用容器内部IP地址访问,该IP仅能在Docker内部网络下被访问,本地测试直接使用localhost:映射的宿主机端口即可。
内容的提问来源于stack exchange,提问作者J. Viégas
相关产品推荐
相关产品推荐

