/// <summary> /// Initializes a new instance of the <see cref="MultipleInstanceMongoServerProxy"/> class. /// </summary> /// <param name="settings">The settings.</param> /// <param name="instances">The instances.</param> /// <param name="connectionQueue">The state change queue.</param> /// <param name="connectionAttempt">The connection attempt.</param> /// <remarks>This constructor is used when the instances have already been instructed to connect.</remarks> protected MultipleInstanceMongoServerProxy(MongoServerSettings settings, IEnumerable <MongoServerInstance> instances, BlockingQueue <MongoServerInstance> connectionQueue, int connectionAttempt) { _state = MongoServerState.Connecting; _settings = settings; _connectedInstances = new ConnectedInstanceCollection(); _connectionAttempt = connectionAttempt; _outstandingInstanceConnections = connectionQueue.Count; ThreadPool.QueueUserWorkItem(_ => { while (connectionQueue.Count > 0) { connectionQueue.Dequeue(); Interlocked.Decrement(ref _outstandingInstanceConnections); } }); // It's important to have our own copy of this list because it might get modified during iteration. _instances = instances.ToList(); foreach (var instance in instances) { instance.StateChanged += InstanceStateChanged; ProcessInstanceStateChange(instance); } }
private void Discover(TimeSpan timeout) { var connectionQueue = new BlockingQueue <MongoServerInstance>(); for (int i = 0; i < _instances.Count; i++) { var local = _instances[i]; connectionQueue.EnqueuWorkItem(() => { try { local.Connect(); } catch { // instance is keeping it's last ConnectionException } return(local); }); } MongoServerInstance instance = null; var timeRemaining = timeout; var timeoutAt = DateTime.UtcNow + timeout; while ((instance = connectionQueue.Dequeue(timeRemaining)) != null) { if (instance.ConnectException == null) { CreateActualProxy(instance, connectionQueue); return; } timeRemaining = timeoutAt - DateTime.UtcNow; } throw new MongoConnectionException(string.Format("Unable to connect in the specified timeframe of '{0}'.", timeout)); }