Skip to content

Commit cbb8321

Browse files
committed
Fix initial randomization of nodes (#4112)
This commit fixes the initial randomization of nodes in a StaticConnectionPool. Instead of calling the protected ctor, the initialization logic has been pulled out into a separate method that is now called from the ctor that accepts a randomize parameter. Fixes #4055 (cherry picked from commit 02dfd4b)
1 parent b0747d3 commit cbb8321

File tree

2 files changed

+49
-11
lines changed

2 files changed

+49
-11
lines changed

src/Elasticsearch.Net/ConnectionPool/StaticConnectionPool.cs

Lines changed: 25 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -14,24 +14,38 @@ public StaticConnectionPool(IEnumerable<Uri> uris, bool randomize = true, IDateT
1414
: this(uris.Select(uri => new Node(uri)), randomize, dateTimeProvider) { }
1515

1616
public StaticConnectionPool(IEnumerable<Node> nodes, bool randomize = true, IDateTimeProvider dateTimeProvider = null)
17-
: this(nodes, null, dateTimeProvider) => Randomize = randomize;
17+
{
18+
nodes.ThrowIfEmpty(nameof(nodes));
19+
Randomize = randomize;
20+
Initialize(nodes, dateTimeProvider);
21+
}
1822

1923
//this constructor is protected because nodeScorer only makes sense on subclasses that support reseeding
2024
//otherwise just manually sort `nodes` before instantiating.
2125
protected StaticConnectionPool(IEnumerable<Node> nodes, Func<Node, float> nodeScorer, IDateTimeProvider dateTimeProvider = null)
2226
{
2327
nodes.ThrowIfEmpty(nameof(nodes));
24-
DateTimeProvider = dateTimeProvider ?? Net.DateTimeProvider.Default;
28+
_nodeScorer = nodeScorer;
29+
Initialize(nodes, dateTimeProvider);
30+
}
2531

26-
var nn = nodes.ToList();
27-
var uris = nn.Select(n => n.Uri).ToList();
28-
if (uris.Select(u => u.Scheme).Distinct().Count() > 1)
29-
throw new ArgumentException("Trying to instantiate a connection pool with mixed URI Schemes");
32+
private void Initialize(IEnumerable<Node> nodes, IDateTimeProvider dateTimeProvider)
33+
{
34+
DateTimeProvider = dateTimeProvider ?? Net.DateTimeProvider.Default;
3035

31-
UsingSsl = uris.Any(uri => uri.Scheme == "https");
36+
string scheme = null;
37+
foreach (var node in nodes)
38+
{
39+
if (scheme == null)
40+
{
41+
scheme = node.Uri.Scheme;
42+
UsingSsl = scheme == "https";
43+
}
44+
else if (scheme != node.Uri.Scheme)
45+
throw new ArgumentException("Trying to instantiate a connection pool with mixed URI Schemes");
46+
}
3247

33-
_nodeScorer = nodeScorer;
34-
InternalNodes = SortNodes(nn)
48+
InternalNodes = SortNodes(nodes)
3549
.DistinctBy(n => n.Uri)
3650
.ToList();
3751
LastUpdate = DateTimeProvider.Now();
@@ -56,7 +70,7 @@ protected StaticConnectionPool(IEnumerable<Node> nodes, Func<Node, float> nodeSc
5670
public virtual bool SupportsReseeding => false;
5771

5872
/// <inheritdoc />
59-
public bool UsingSsl { get; }
73+
public bool UsingSsl { get; private set; }
6074

6175
protected List<Node> AliveNodes
6276
{
@@ -69,7 +83,7 @@ protected List<Node> AliveNodes
6983
}
7084
}
7185

72-
protected IDateTimeProvider DateTimeProvider { get; }
86+
protected IDateTimeProvider DateTimeProvider { get; private set; }
7387

7488
protected List<Node> InternalNodes { get; set; }
7589
protected Random Random { get; } = new Random();

src/Tests/Tests/ClientConcepts/ConnectionPooling/BuildingBlocks/ConnectionPooling.doc.cs

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -212,6 +212,30 @@ [U] public void Static()
212212
}
213213
}
214214

215+
// hide
216+
[U] public void RandomizedInitialNodes()
217+
{
218+
StaticConnectionPool CreatStaticConnectionPool()
219+
{
220+
var uris = new[]
221+
{
222+
new Uri("https://10.0.0.1:9200/"),
223+
new Uri("https://10.0.0.2:9200/"),
224+
new Uri("https://10.0.0.3:9200/")
225+
};
226+
227+
var staticConnectionPool = new StaticConnectionPool(uris);
228+
return staticConnectionPool;
229+
}
230+
231+
// assertion works on the probability of seeing a Uri other than https://10.0.0.1:9200/
232+
// as the first value over 50 runs, when randomized.
233+
Enumerable.Repeat(CreatStaticConnectionPool().CreateView().First().Uri.ToString(), 50)
234+
.All(uri => uri == "https://10.0.0.1:9200/")
235+
.Should()
236+
.BeFalse();
237+
}
238+
215239
/**[[sniffing-connection-pool]]
216240
* ==== SniffingConnectionPool
217241
*

0 commit comments

Comments
 (0)