J'utilise des pilotes MongoDB
pour me connecter à la base de données. Lorsque mon formulaire se charge, je souhaite configurer la connexion et vérifier si elle est correcte ou non. Je le fais comme ça:
var connectionString = "mongodb://localhost";
var client = new MongoClient(connectionString);
var server = client.GetServer();
var database = server.GetDatabase("reestr");
Mais je ne sais pas comment vérifier la connexion. J'ai essayé de chevaucher ce code avec try-catch
, mais en vain. Même si je fais une chaîne de connexion incorrecte, je ne peux toujours pas obtenir de message d'erreur.
Il y a méthode ping pour cela:
var connectionString = "mongodb://localhost";
var client = new MongoClient(connectionString);
var server = client.GetServer();
server.Ping();
Pour envoyer une requête ping au serveur avec le nouveau pilote 3.0, procédez comme suit:
var database = client.GetDatabase("YourDbHere");
database.RunCommandAsync((Command<BsonDocument>)"{ping:1}")
.Wait();
exemple complet pour 2.4.3 - où "client.GetServer ()" n'est pas disponible. basé sur la réponse "Paul Keister".
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
}
J'ai eu la même question que l'OP, et essayé toutes les solutions que j'ai pu trouver sur Internet ... Eh bien, aucune n'a fonctionné à ma vraie satisfaction, j'ai donc opté pour une recherche pour trouver une solution fiable et une manière réactive de vérifier si la connexion à un serveur de base de données MongoDB est active. Et cela sans bloquer l'exécution synchrone de l'application pendant trop longtemps ...
Voici donc mes prérequis:
J'ai fourni une nouvelle installation de MongoDB (version 3.6) sur l'URL localhost par défaut: mongodb: // localhost: 27017 . J'ai également noté une autre URL, où il n'y avait pas de serveur de base de données MongoDB: mongodb: // localhost: 27071 .
J'utilise également le pilote C # 2.4.4 et n'utilise pas l'implémentation héritée (MongoDB.Driver.Legacy Assembly).
Donc, mes attentes sont, lorsque je vérifie la connexion à la première URL, cela devrait me donner le Ok pour une connexion vivante à un serveur MongoDB existant, lorsque je vérifie la connexion à la deuxième URL, il devrait me donner l'échec pour un serveur MongoDB inexistant ...
À l'aide de la méthode IMongoDatabase.RunCommand, interroge le serveur et entraîne l'expiration du délai de réponse du serveur, ne répondant ainsi pas aux conditions préalables. De plus, après le délai d'expiration, il rompt avec une TimeoutException, ce qui nécessite une gestion supplémentaire des exceptions.
Cette réelle SO question et aussi this SO question ont fourni la plupart des informations de démarrage dont j'avais besoin pour ma solution ... Alors les gars, merci beaucoup pour ça!
Maintenant ma solution:
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;
}
L'idée derrière cela est que le serveur MongoDB ne réagit pas (et semble être inexistant) jusqu'à ce qu'une tentative réelle soit faite pour accéder à une ressource sur le serveur (par exemple une base de données). Mais récupérer une ressource seule ne suffit pas, car le serveur n'a toujours pas de mise à jour de son état dans la description de cluster du serveur. Cette mise à jour vient en premier, lorsque la ressource est récupérée à nouveau. À partir de ce moment, le serveur a une description de cluster valide et des données valides à l'intérieur ...
En général, il me semble que le serveur MongoDB ne propage pas proactivement sa description de cluster à tous les clients connectés. Au lieu de cela, chaque client reçoit la description, lorsqu'une demande au serveur a été faite. Si certains d'entre vous ont plus d'informations à ce sujet, veuillez confirmer ou nier mes compréhensions sur le sujet ...
Maintenant, lorsque nous ciblons une URL de serveur MongoDB non valide, la description du cluster reste invalide et nous pouvons intercepter et fournir un signal utilisable pour ce cas ...
Ainsi, les instructions suivantes (pour l'URL valide)
// 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!"));
imprimera
La connexion à mongodb: // localhost: 27017 a réussi!
et les instructions (pour l'URL invalide)
// 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!"));
imprimera
La connexion à mongodb: // localhost: 27071 n'a pas réussi!
Voici une méthode d'extension simple pour envoyer un ping au serveur mongodb
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);
}
}
Vous pouvez l'utiliser comme ceci:
var client = new MongoClient("yourConnectionString");
var database = client.GetDatabase("yourDatabase");
if (!database.Ping())
throw new Exception("Could not connect to MongoDb");