Skip to content

Commit dc021c6

Browse files
fix: client side disconnect incorrect client count on host-server side [MTTB-135] (#2941)
* fix This resolves the issue with the client count not being correct on the host or server side when a client disconnects itself from a session. This also resolves the issue with the host trying to send itself a message that it has connected when first starting up. Fixing issue with NetworkSceneManager finishing synchronization prior to the server connection timing out. * test Adding validation for the connected clients count on the server side when the client-side disconnects.
1 parent 1644801 commit dc021c6

File tree

4 files changed

+39
-19
lines changed

4 files changed

+39
-19
lines changed

com.unity.netcode.gameobjects/CHANGELOG.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,8 @@ Additional documentation and release notes are available at [Multiplayer Documen
1515

1616
### Fixed
1717

18+
- Fixed issue with the client count not being correct on the host or server side when a client disconnects itself from a session. (#2941)
19+
- Fixed issue with the host trying to send itself a message that it has connected when first starting up. (#2941)
1820
- Fixed issue where in-scene placed NetworkObjects could be destroyed if a client disconnects early and/or before approval. (#2923)
1921
- Fixed issue where `NetworkDeltaPosition` would "jitter" periodically if both unreliable delta state updates and half-floats were used together. (#2922)
2022
- Fixed issue where `NetworkRigidbody2D` would not properly change body type based on the instance's authority when spawned. (#2916)

com.unity.netcode.gameobjects/Runtime/Connection/NetworkConnectionManager.cs

Lines changed: 33 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -104,9 +104,11 @@ internal void InvokeOnClientConnectedCallback(ulong clientId)
104104
{
105105
continue;
106106
}
107-
108-
peerClientIds[idx] = peerId;
109-
++idx;
107+
if (peerClientIds.Length > idx)
108+
{
109+
peerClientIds[idx] = peerId;
110+
++idx;
111+
}
110112
}
111113

112114
try
@@ -491,24 +493,32 @@ internal void DisconnectEventHandler(ulong transportClientId)
491493
// Process the incoming message queue so that we get everything from the server disconnecting us or, if we are the server, so we got everything from that client.
492494
MessageManager.ProcessIncomingMessageQueue();
493495

494-
InvokeOnClientDisconnectCallback(clientId);
495-
496-
if (LocalClient.IsHost)
497-
{
498-
InvokeOnPeerDisconnectedCallback(clientId);
499-
}
500-
501496
if (LocalClient.IsServer)
502497
{
498+
// We need to process the disconnection before notifying
503499
OnClientDisconnectFromServer(clientId);
500+
501+
// Now notify the client has disconnected
502+
InvokeOnClientDisconnectCallback(clientId);
503+
504+
if (LocalClient.IsHost)
505+
{
506+
InvokeOnPeerDisconnectedCallback(clientId);
507+
}
504508
}
505-
else // As long as we are not in the middle of a shutdown
506-
if (!NetworkManager.ShutdownInProgress)
509+
else
507510
{
508-
// We must pass true here and not process any sends messages as we are no longer connected.
509-
// Otherwise, attempting to process messages here can cause an exception within UnityTransport
510-
// as the client ID is no longer valid.
511-
NetworkManager.Shutdown(true);
511+
// Notify local client of disconnection
512+
InvokeOnClientDisconnectCallback(clientId);
513+
514+
// As long as we are not in the middle of a shutdown
515+
if (!NetworkManager.ShutdownInProgress)
516+
{
517+
// We must pass true here and not process any sends messages as we are no longer connected.
518+
// Otherwise, attempting to process messages here can cause an exception within UnityTransport
519+
// as the client ID is no longer valid.
520+
NetworkManager.Shutdown(true);
521+
}
512522
}
513523

514524
if (NetworkManager.IsServer)
@@ -900,9 +910,14 @@ internal NetworkClient AddClient(ulong clientId)
900910

901911
ConnectedClients.Add(clientId, networkClient);
902912
ConnectedClientsList.Add(networkClient);
903-
var message = new ClientConnectedMessage { ClientId = clientId };
904-
NetworkManager.MessageManager.SendMessage(ref message, NetworkDelivery.ReliableFragmentedSequenced, ConnectedClientIds);
905913
ConnectedClientIds.Add(clientId);
914+
// Host should not send this message to itself
915+
if (clientId != NetworkManager.ServerClientId)
916+
{
917+
var message = new ClientConnectedMessage { ClientId = clientId };
918+
NetworkManager.MessageManager.SendMessage(ref message, NetworkDelivery.ReliableFragmentedSequenced, ConnectedClientIds);
919+
}
920+
906921
return networkClient;
907922
}
908923

com.unity.netcode.gameobjects/Tests/Runtime/ConnectionApprovalTimeoutTests.cs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -81,7 +81,7 @@ protected override IEnumerator OnStartedServerAndClients()
8181
public IEnumerator ValidateApprovalTimeout()
8282
{
8383
// Delay for half of the wait period
84-
yield return new WaitForSeconds(k_TestTimeoutPeriod * 0.5f);
84+
yield return new WaitForSeconds(k_TestTimeoutPeriod * 0.25f);
8585

8686
// Verify we haven't received the time out message yet
8787
NetcodeLogAssert.LogWasNotReceived(LogType.Log, m_ExpectedLogMessage);

com.unity.netcode.gameobjects/Tests/Runtime/DisconnectTests.cs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -182,6 +182,9 @@ public IEnumerator ClientPlayerDisconnected([Values] ClientDisconnectType client
182182
Assert.IsTrue(m_DisconnectedEvent[m_ServerNetworkManager].ClientId == m_ClientId, $"Expected ClientID {m_ClientId} but found ClientID {m_DisconnectedEvent[m_ServerNetworkManager].ClientId} for the server {nameof(NetworkManager)} disconnect event entry!");
183183
Assert.IsTrue(m_DisconnectedEvent.ContainsKey(clientManager), $"Could not find the client {nameof(NetworkManager)} disconnect event entry!");
184184
Assert.IsTrue(m_DisconnectedEvent[clientManager].ClientId == m_ClientId, $"Expected ClientID {m_ClientId} but found ClientID {m_DisconnectedEvent[m_ServerNetworkManager].ClientId} for the client {nameof(NetworkManager)} disconnect event entry!");
185+
Assert.IsTrue(m_ServerNetworkManager.ConnectedClientsIds.Count == 1, $"Expected connected client identifiers count to be 1 but it was {m_ServerNetworkManager.ConnectedClientsIds.Count}!");
186+
Assert.IsTrue(m_ServerNetworkManager.ConnectedClients.Count == 1, $"Expected connected client identifiers count to be 1 but it was {m_ServerNetworkManager.ConnectedClients.Count}!");
187+
Assert.IsTrue(m_ServerNetworkManager.ConnectedClientsList.Count == 1, $"Expected connected client identifiers count to be 1 but it was {m_ServerNetworkManager.ConnectedClientsList.Count}!");
185188
}
186189

187190
if (m_OwnerPersistence == OwnerPersistence.DestroyWithOwner)

0 commit comments

Comments
 (0)