我使用MongoDB
驱动程序连接到数据库。当我的表单加载时,我想设置连接并检查它是否正常。我是这样做的:
var connectionString = "mongodb://localhost";
var client = new MongoClient(connectionString);
var server = client.GetServer();
var database = server.GetDatabase("reestr");
但我不知道如何检查连接。我试图将此代码与try-catch
重叠,但无济于事。即使我创建了一个不正确的connectionString,我仍然无法收到任何错误消息。
答案 0 :(得分:31)
使用新的3.0驱动程序ping服务器:
var database = client.GetDatabase("YourDbHere");
database.RunCommandAsync((Command<BsonDocument>)"{ping:1}")
.Wait();
答案 1 :(得分:20)
有一个ping method:
var connectionString = "mongodb://localhost";
var client = new MongoClient(connectionString);
var server = client.GetServer();
server.Ping();
答案 2 :(得分:14)
2.4.3的完整示例 - 其中“client.GetServer()”不可用。 基于“保罗凯斯特”的答案。
client = new MongoClient("mongodb://localhost");
database = client.GetDatabase(mongoDbStr);
bool isMongoLive = database.RunCommandAsync((Command<BsonDocument>)"{ping:1}").Wait(1000);
if(isMongoLive)
{
// connected
}
else
{
// couldn't connect
}
答案 3 :(得分:2)
我和OP有同样的问题,并尝试了我能在互联网上找到的每一个解决方案...... 好吧,他们都没有真正令我满意,所以我选择了一项研究,以找到一种可靠且反应灵敏的方式来检查与MongoDB数据库服务器的连接是否存在。这不会阻止应用程序的同步执行太长时间......
所以这是我的先决条件:
我在默认的localhost网址上提供了一个全新的MongoDB安装(版本3.6): mongodb:// localhost:27017 。我还写了另一个URL,其中没有MongoDB数据库服务器: mongodb:// localhost:27071 。
我也使用C#驱动程序2.4.4,并且不使用旧版实现(MongoDB.Driver.Legacy程序集)。
所以我的期望是,当我检查与第一个URL的连接时,当我检查与现有MongoDB服务器的连接时,它应该给我一个好的连接到现有的MongoDB服务器。第二个URL应该给我一个不存在的MongoDB服务器的失败...
使用IMongoDatabase.RunCommand方法查询服务器并导致服务器响应超时,因此不符合先决条件。此外,在超时之后,它会因TimeoutException而中断,这需要额外的异常处理。
这个实际的SO问题以及this SO问题已经提供了我解决方案所需的大部分启动信息......所以,伙计们,非常感谢!
现在我的解决方案:
private static bool ProbeForMongoDbConnection(string connectionString, string dbName)
{
var probeTask =
Task.Run(() =>
{
var isAlive = false;
var client = new MongoDB.Driver.MongoClient(connectionString);
for (var k = 0; k < 6; k++)
{
client.GetDatabase(dbName);
var server = client.Cluster.Description.Servers.FirstOrDefault();
isAlive = (server != null &&
server.HeartbeatException == null &&
server.State == MongoDB.Driver.Core.Servers.ServerState.Connected);
if (isAlive)
{
break;
}
System.Threading.Thread.Sleep(300);
}
return isAlive;
});
probeTask.Wait();
return probeTask.Result;
}
这背后的想法是MongoDB服务器在真正尝试访问服务器上的某些资源(例如数据库)之前不会做出反应(并且似乎不存在)。但仅仅检索一些资源是不够的,因为服务器的服务器群集描述中的状态仍然没有更新。当再次检索资源时,首先进行此更新。从这个时间点开始,服务器内部有有效的集群描述和有效数据......
通常在我看来,MongoDB服务器不会主动将其群集描述传播到所有连接的客户端。而是,当向服务器发出请求时,每个客户端都会收到描述。如果你们中的一些人有关于此的更多信息,请确认或否认我对该主题的理解......
现在,当我们定位一个无效的MongoDB服务器URL时,群集描述仍然无效,我们可以捕获并传递此案例的可用信号......
以下语句(对于有效的URL)
// The admin database should exist on each MongoDB 3.6 Installation, if not explicitly deleted!
var isAlive = ProbeForMongoDbConnection("mongodb://localhost:27017", "admin");
Console.WriteLine("Connection to mongodb://localhost:27017 was " + (isAlive ? "successful!" : "NOT successful!"));
将打印出来
与mongodb:// localhost:27017的连接成功!
和语句(针对无效网址)
// The admin database should exist on each MongoDB 3.6 Installation, if not explicitly deleted!
isAlive = ProbeForMongoDbConnection("mongodb://localhost:27071", "admin");
Console.WriteLine("Connection to mongodb://localhost:27071 was " + (isAlive ? "successful!" : "NOT successful!"));
将打印出来
与mongodb:// localhost:27071的连接未成功!
答案 4 :(得分:1)
这是对mongodb服务器执行ping操作的简单扩展方法
public static class MongoDbExt
{
public static bool Ping(this IMongoDatabase db, int secondToWait = 1)
{
if (secondToWait <= 0)
throw new ArgumentOutOfRangeException("secondToWait", secondToWait, "Must be at least 1 second");
return db.RunCommandAsync((Command<MongoDB.Bson.BsonDocument>)"{ping:1}").Wait(secondToWait * 1000);
}
}
您可以像这样使用它:
var client = new MongoClient("yourConnectionString");
var database = client.GetDatabase("yourDatabase");
if (!database.Ping())
throw new Exception("Could not connect to MongoDb");
答案 5 :(得分:0)
这是使用try-catch方法的解决方案,
var database = client.GetDatabase("YourDbHere");
bool isMongoConnected;
try
{
await database.RunCommandAsync((Command<BsonDocument>)"{ping:1}");
isMongoConnected = true;
}
catch(Exception)
{
isMongoConnected = false;
}
因此,当它无法连接到数据库时,它将引发异常,我们可以在那里处理bool标志。
答案 6 :(得分:-1)
如果您想在程序中处理连接问题,可以使用ICluster.Description
事件。
创建MongoClient
后,它将继续在后台尝试连接,直到成功为止。
using MongoDB.Driver;
using MongoDB.Driver.Core.Clusters;
var mongoClient = new MongoClient("localhost")
mongoClient.Cluster.DescriptionChanged += Cluster_DescriptionChanged;
public void Cluster_DescriptionChanged(object sender, ClusterDescriptionChangedEventArgs e)
{
switch (e.NewClusterDescription.State)
{
case ClusterState.Disconnected:
break;
case ClusterState.Connected:
break;
}
}