feat(batch18): implement group-b server core helpers
This commit is contained in:
@@ -638,6 +638,14 @@ public sealed partial class NatsServer
|
||||
return (claims, claimJwt, null);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Fetches an account from the resolver, registers it, and returns it.
|
||||
/// Mirrors Go <c>Server.fetchAccount</c>.
|
||||
/// Lock must NOT be held on entry.
|
||||
/// </summary>
|
||||
public (Account? Account, Exception? Error) FetchAccount(string name) =>
|
||||
FetchAccountFromResolver(name);
|
||||
|
||||
/// <summary>
|
||||
/// Fetches an account from the resolver, registers it, and returns it.
|
||||
/// Mirrors Go <c>Server.fetchAccount</c>.
|
||||
|
||||
@@ -331,10 +331,12 @@ public sealed partial class NatsServer
|
||||
public int NumRemotes()
|
||||
{
|
||||
_mu.EnterReadLock();
|
||||
try { return _routes.Count; }
|
||||
try { return NumRemotesInternal(); }
|
||||
finally { _mu.ExitReadLock(); }
|
||||
}
|
||||
|
||||
private int NumRemotesInternal() => _routes.Count;
|
||||
|
||||
/// <summary>Returns the number of leaf-node connections. Mirrors Go <c>Server.NumLeafNodes()</c>.</summary>
|
||||
public int NumLeafNodes()
|
||||
{
|
||||
@@ -475,27 +477,56 @@ public sealed partial class NatsServer
|
||||
/// Mirrors Go <c>Server.readyForConnections()</c>.
|
||||
/// </summary>
|
||||
public Exception? ReadyForConnectionsError(TimeSpan d)
|
||||
=> ReadyForConnectionsInternal(d);
|
||||
|
||||
/// <summary>
|
||||
/// Polls until all expected listeners are up or the deadline expires.
|
||||
/// Returns an error description if not ready within <paramref name="d"/>.
|
||||
/// Mirrors Go <c>Server.readyForConnections()</c>.
|
||||
/// </summary>
|
||||
internal Exception? ReadyForConnectionsInternal(TimeSpan d)
|
||||
{
|
||||
var opts = GetOpts();
|
||||
var end = DateTime.UtcNow.Add(d);
|
||||
|
||||
var checks = new Dictionary<string, (bool ok, Exception? err)>(StringComparer.Ordinal);
|
||||
while (DateTime.UtcNow < end)
|
||||
{
|
||||
bool serverOk, routeOk, gatewayOk, leafOk, wsOk;
|
||||
bool serverOk, routeOk, gatewayOk, leafOk, wsOk, mqttOk;
|
||||
Exception? serverErr, routeErr, gatewayErr, leafErr;
|
||||
_mu.EnterReadLock();
|
||||
serverOk = _listener != null || opts.DontListen;
|
||||
serverErr = _listenerErr;
|
||||
routeOk = opts.Cluster.Port == 0 || _routeListener != null;
|
||||
routeErr = _routeListenerErr;
|
||||
gatewayOk = string.IsNullOrEmpty(opts.Gateway.Name) || _gatewayListener != null;
|
||||
gatewayErr = _gatewayListenerErr;
|
||||
leafOk = opts.LeafNode.Port == 0 || _leafNodeListener != null;
|
||||
wsOk = opts.Websocket.Port == 0; // stub — websocket listener not tracked until session 23
|
||||
leafErr = _leafNodeListenerErr;
|
||||
wsOk = opts.Websocket.Port == 0;
|
||||
mqttOk = opts.Mqtt.Port == 0;
|
||||
_mu.ExitReadLock();
|
||||
|
||||
if (serverOk && routeOk && gatewayOk && leafOk && wsOk)
|
||||
checks["server"] = (serverOk, serverErr);
|
||||
checks["route"] = (routeOk, routeErr);
|
||||
checks["gateway"] = (gatewayOk, gatewayErr);
|
||||
checks["leafnode"] = (leafOk, leafErr);
|
||||
checks["websocket"] = (wsOk, null);
|
||||
checks["mqtt"] = (mqttOk, null);
|
||||
|
||||
var numOk = checks.Values.Count(v => v.ok);
|
||||
if (numOk == checks.Count)
|
||||
{
|
||||
if (opts.DontListen)
|
||||
{
|
||||
try { _startupComplete.Task.Wait((int)d.TotalMilliseconds); }
|
||||
catch { /* timeout */ }
|
||||
catch { }
|
||||
|
||||
if (!_startupComplete.Task.IsCompleted)
|
||||
{
|
||||
return new InvalidOperationException(
|
||||
$"failed to be ready for connections after {d}: startup did not complete");
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
@@ -504,8 +535,19 @@ public sealed partial class NatsServer
|
||||
Thread.Sleep(25);
|
||||
}
|
||||
|
||||
var failed = new List<string>(checks.Count);
|
||||
foreach (var (name, info) in checks)
|
||||
{
|
||||
if (info.ok && info.err != null)
|
||||
failed.Add($"{name}(ok, but {info.err.Message})");
|
||||
else if (!info.ok && info.err == null)
|
||||
failed.Add(name);
|
||||
else if (!info.ok)
|
||||
failed.Add($"{name}({info.err!.Message})");
|
||||
}
|
||||
|
||||
return new InvalidOperationException(
|
||||
$"failed to be ready for connections after {d}");
|
||||
$"failed to be ready for connections after {d}: {string.Join(", ", failed)}");
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -528,7 +570,10 @@ public sealed partial class NatsServer
|
||||
public string Name() => _info.Name;
|
||||
|
||||
/// <summary>Returns the server name as a string. Mirrors Go <c>Server.String()</c>.</summary>
|
||||
public override string ToString() => _info.Name;
|
||||
public string String() => _info.Name;
|
||||
|
||||
/// <summary>Returns the server name as a string. Mirrors Go <c>Server.String()</c>.</summary>
|
||||
public override string ToString() => String();
|
||||
|
||||
/// <summary>Returns the number of currently-stored closed connections. Mirrors Go <c>Server.numClosedConns()</c>.</summary>
|
||||
internal int NumClosedConns()
|
||||
|
||||
Reference in New Issue
Block a user