From 7bb422cfb4d261ec0333905fa93e64d26b88ef75 Mon Sep 17 00:00:00 2001 From: teascade Date: Wed, 12 Aug 2020 22:53:46 +0300 Subject: [PATCH] Add brand new traffic analytics --- Assets/Scripts/Interface/NetDebugScreen.cs | 25 ++++-- .../Scripts/TeaNet/Peers/ConnectionManager.cs | 77 +++++++++++++++---- Assets/Scripts/TeaNet/Peers/ListenerThread.cs | 7 +- Assets/Scripts/TeaNet/Peers/Peer.cs | 60 +++++++++++---- 4 files changed, 130 insertions(+), 39 deletions(-) diff --git a/Assets/Scripts/Interface/NetDebugScreen.cs b/Assets/Scripts/Interface/NetDebugScreen.cs index c7b1fd6..8fb81cb 100644 --- a/Assets/Scripts/Interface/NetDebugScreen.cs +++ b/Assets/Scripts/Interface/NetDebugScreen.cs @@ -2,6 +2,7 @@ using UnityEngine.InputSystem; using TMPro; using NeonTea.Quakeball.Networking; +using NeonTea.Quakeball.TeaNet.Peers; using System; public class NetDebugScreen : MonoBehaviour { @@ -33,15 +34,27 @@ public class NetDebugScreen : MonoBehaviour { var Peer = Net.Singleton.Instance.Peer; if (Time.time - LastUpdate > UpdateInterval) { LastUpdate = Time.time; + TrafficData data = Peer.TrafficData; + float ToSeconds = 1f / (Peer.TrafficDataInterval / 1000f); - string received = $"Total Bytes Receivd: {Peer.TrafficReceived * ToSeconds} B/s\nReceived by packet:"; - foreach (Type t in Peer.TrafficReceivedByPacket.Keys) { - received += $"\n{t.Name} - {Peer.TrafficReceivedByPacket[t] * ToSeconds} B/s"; + string received = $"Total incoming traffic: {data.Received * ToSeconds} B/s"; + received += $"\n{data.TotalMessagesReceived * ToSeconds} total messages"; + received += $"\n{data.ReliableReceived * ToSeconds} reliable Packets/s"; + received += $"\n{data.UnreliableReceived * ToSeconds} unreliable Packets/s"; + received += "\nPer packet received traffic:"; + foreach (Type t in data.ReceivedByPacket.Keys) { + PerPacketData packetData = data.ReceivedByPacket[t]; + received += $"\n{t.Name} {packetData.Packets * ToSeconds} P/s - {packetData.Bytes * ToSeconds} B/s"; } ReceivedText.text = received; - string sent = $"Total Bytes Sent: {Net.Singleton.Instance.Peer.TrafficSent * ToSeconds} B/s\nSent by packet:"; - foreach (Type t in Peer.TrafficSentByPacket.Keys) { - sent += $"\n{t.Name} - {Peer.TrafficSentByPacket[t] * ToSeconds} B/s"; + string sent = $"Total outgoing traffic: {data.Sent * ToSeconds} B/s"; + sent += $"\n{data.TotalMessagesSent * ToSeconds} total messages"; + sent += $"\n{data.ReliableSent * ToSeconds} reliable Packets/s"; + sent += $"\n{data.UnreliableSent * ToSeconds} unreliable Packets/s"; + sent += "\nPer packet sent traffic:"; + foreach (Type t in data.SentByPacket.Keys) { + PerPacketData packetData = data.SentByPacket[t]; + sent += $"\n{t.Name} {packetData.Packets * ToSeconds} P/s - {data.SentByPacket[t].Bytes * ToSeconds} B/s"; } SentText.text = sent; } diff --git a/Assets/Scripts/TeaNet/Peers/ConnectionManager.cs b/Assets/Scripts/TeaNet/Peers/ConnectionManager.cs index 32d9787..dc980dd 100644 --- a/Assets/Scripts/TeaNet/Peers/ConnectionManager.cs +++ b/Assets/Scripts/TeaNet/Peers/ConnectionManager.cs @@ -23,10 +23,7 @@ namespace NeonTea.Quakeball.TeaNet.Peers { public long Timeout = 8000; public long Interval = 100; - /// The amount of bytes sent since the last clear interval from Peer - public int BytesSent; - public ConcurrentDictionary SentByPacket = new ConcurrentDictionary(); - public ConcurrentDictionary ReceivedByPacket = new ConcurrentDictionary(); + public ConnectionManagerTrafficData TrafficData = new ConnectionManagerTrafficData(); public ConnectionManager(Peer peer) { Peer = peer; @@ -103,9 +100,12 @@ namespace NeonTea.Quakeball.TeaNet.Peers { buffer.WritePacket(protocol, p); // Do the analytics dance! - int OldSentByPacket; - SentByPacket.TryGetValue(p.GetType(), out OldSentByPacket); - SentByPacket[p.GetType()] = OldSentByPacket + p.Size; + PerPacketData OldSentByPacket; + TrafficData.SentByPacket.TryGetValue(p.GetType(), out OldSentByPacket); + OldSentByPacket.Bytes += p.Size; + OldSentByPacket.Packets += 1; + TrafficData.SentByPacket[p.GetType()] = OldSentByPacket; + TrafficData.ReliablePacketsSent++; } Send(conn, buffer); } @@ -126,11 +126,14 @@ namespace NeonTea.Quakeball.TeaNet.Peers { buffer.Write(1); buffer.WritePacket(protocol, p); Send(conn, buffer); + TrafficData.UnreliablePacketsSent++; // Do the analytics dance! - int OldSentByPacket; - SentByPacket.TryGetValue(p.GetType(), out OldSentByPacket); - SentByPacket[p.GetType()] = OldSentByPacket + p.Size; + PerPacketData OldSentByPacket; + TrafficData.SentByPacket.TryGetValue(p.GetType(), out OldSentByPacket); + OldSentByPacket.Bytes += p.Size; + OldSentByPacket.Packets += 1; + TrafficData.SentByPacket[p.GetType()] = OldSentByPacket; } } @@ -183,7 +186,8 @@ namespace NeonTea.Quakeball.TeaNet.Peers { if (conn.Status == ConnectionStatus.Lost) { return; } - BytesSent += buffer.Size; + TrafficData.BytesSent += buffer.Size; + TrafficData.TotalMessagesSent++; byte[] bytes = buffer.Pack(); Peer.ListenerThread.LastSentConnection = conn; Peer.UdpClient.Send(bytes, bytes.Length, conn.Endpoint); @@ -258,7 +262,15 @@ namespace NeonTea.Quakeball.TeaNet.Peers { } PacketQueue[conn.uid] = queue; + int PacketAmount = buffer.ReadInt(); + + if (Reliable) { + TrafficData.ReliablePacketsReceived += PacketAmount; + } else { + TrafficData.UnreliablePacketsreceived += PacketAmount; + } + for (int i = 0; i < PacketAmount; i++) { Packet p = buffer.ReadPacket(protocol); p.PacketId = FirstPacketId + i; @@ -274,9 +286,11 @@ namespace NeonTea.Quakeball.TeaNet.Peers { } // Do some analytics! - int OldReceivedByPacket; - ReceivedByPacket.TryGetValue(p.GetType(), out OldReceivedByPacket); - ReceivedByPacket[p.GetType()] = OldReceivedByPacket + p.Size; + PerPacketData OldReceivedByPacket; + TrafficData.ReceivedByPacket.TryGetValue(p.GetType(), out OldReceivedByPacket); + OldReceivedByPacket.Bytes += p.Size; + OldReceivedByPacket.Packets += 1; + TrafficData.ReceivedByPacket[p.GetType()] = OldReceivedByPacket; } break; } @@ -353,4 +367,37 @@ namespace NeonTea.Quakeball.TeaNet.Peers { Connection = connection; } } -} \ No newline at end of file + + public class ConnectionManagerTrafficData { + /// The amount of bytes sent since the last clear interval from Peer + public int BytesSent; + /// The amount of total IP messages sent since the last clear interval from Peer + public int TotalMessagesSent; + /// The amount of reliable packets sent since the last clear interval from Peer + public int ReliablePacketsSent; + /// The amount of unreliable packets sent since the last clear interval from Peer + public int UnreliablePacketsSent; + /// The amount of reliable packets received since the last clear interval from Peer + public int ReliablePacketsReceived; + /// The amount of unreliable packets received since the last clear interval from Peer + public int UnreliablePacketsreceived; + /// Data relating to outward packet specific traffic + public ConcurrentDictionary SentByPacket = new ConcurrentDictionary(); + /// Data relating to inward packet specific traffic + public ConcurrentDictionary ReceivedByPacket = new ConcurrentDictionary(); + + public void Clear() { + BytesSent = 0; + TotalMessagesSent = 0; + ReliablePacketsSent = 0; + UnreliablePacketsSent = 0; + ReliablePacketsReceived = 0; + UnreliablePacketsreceived = 0; + } + } + + public struct PerPacketData { + public int Bytes; + public int Packets; + } +} diff --git a/Assets/Scripts/TeaNet/Peers/ListenerThread.cs b/Assets/Scripts/TeaNet/Peers/ListenerThread.cs index b81ed3f..2860522 100644 --- a/Assets/Scripts/TeaNet/Peers/ListenerThread.cs +++ b/Assets/Scripts/TeaNet/Peers/ListenerThread.cs @@ -18,7 +18,9 @@ namespace NeonTea.Quakeball.TeaNet.Peers { private static int[] CONN_LOST_CODES = new int[] { 10054, 10051 }; /// The amount of bytes received since the last clear interval from Peer - public int ReceivedBytes; + public int BytesReceived; + /// The amount of bytes received since the last clear interval from Peer + public int MessagesReceived; public ListenerThread(Peer peer, IPEndPoint endpoint) { EndPoint = endpoint; @@ -64,7 +66,8 @@ namespace NeonTea.Quakeball.TeaNet.Peers { } if (Buffer.ReadFingerprint(Peer.Fingerprint)) { Peer.ConnectionManager.Handle(Listened, Buffer); - ReceivedBytes += Buffer.Size; + BytesReceived += Buffer.Size; + MessagesReceived++; } } } diff --git a/Assets/Scripts/TeaNet/Peers/Peer.cs b/Assets/Scripts/TeaNet/Peers/Peer.cs index 850da79..619992f 100644 --- a/Assets/Scripts/TeaNet/Peers/Peer.cs +++ b/Assets/Scripts/TeaNet/Peers/Peer.cs @@ -33,14 +33,8 @@ namespace NeonTea.Quakeball.TeaNet.Peers { } /// The interval of traffic analyzed before updating. By default 5000 (5 seconds) public long TrafficDataInterval = 5000; - /// The amount of bytes received in the last TrafficDataIntervel - public int TrafficReceived { get; private set; } - /// The amount of bytes sent in the last TrafficDataIntervel - public int TrafficSent { get; private set; } - /// The amount of bytes sent in the last TrafficDataIntervel by Packet - public ConcurrentDictionary TrafficSentByPacket => ConnectionManager.SentByPacket; - /// The amount of bytes received in the last TrafficDataIntervel by Packet - public ConcurrentDictionary TrafficReceivedByPacket => ConnectionManager.ReceivedByPacket; + /// Traffic Data for this Peer + public TrafficData TrafficData { get; private set; } = new TrafficData(); /// Whether the Peer is currently doing anything or not.null public bool Running { get; private set; } @@ -168,19 +162,30 @@ namespace NeonTea.Quakeball.TeaNet.Peers { if (now - LastTrafficData > TrafficDataInterval) { LastTrafficData = now; if (ListenerThread != null) { - TrafficReceived = ListenerThread.ReceivedBytes; - ListenerThread.ReceivedBytes = 0; + TrafficData.Received = ListenerThread.BytesReceived; + TrafficData.TotalMessagesReceived = ListenerThread.MessagesReceived; + ListenerThread.BytesReceived = 0; + ListenerThread.MessagesReceived = 0; } if (ConnectionManager != null) { - TrafficSent = ConnectionManager.BytesSent; - ConnectionManager.BytesSent = 0; + TrafficData.Sent = ConnectionManager.TrafficData.BytesSent; + TrafficData.TotalMessagesSent = ConnectionManager.TrafficData.TotalMessagesSent; + TrafficData.UnreliableReceived = ConnectionManager.TrafficData.UnreliablePacketsreceived; + TrafficData.ReliableReceived = ConnectionManager.TrafficData.ReliablePacketsReceived; + TrafficData.UnreliableSent = ConnectionManager.TrafficData.UnreliablePacketsSent; + TrafficData.ReliableSent = ConnectionManager.TrafficData.ReliablePacketsSent; - foreach (Type t in ConnectionManager.ReceivedByPacket.Keys) { - ConnectionManager.ReceivedByPacket[t] = 0; + PerPacketData empty = new PerPacketData(); + foreach (Type t in ConnectionManager.TrafficData.ReceivedByPacket.Keys) { + TrafficData.ReceivedByPacket[t] = ConnectionManager.TrafficData.ReceivedByPacket[t]; + ConnectionManager.TrafficData.ReceivedByPacket[t] = empty; } - foreach (Type t in ConnectionManager.SentByPacket.Keys) { - ConnectionManager.SentByPacket[t] = 0; + foreach (Type t in ConnectionManager.TrafficData.SentByPacket.Keys) { + TrafficData.SentByPacket[t] = ConnectionManager.TrafficData.SentByPacket[t]; + ConnectionManager.TrafficData.SentByPacket[t] = empty; } + + ConnectionManager.TrafficData.Clear(); } } } @@ -204,4 +209,27 @@ namespace NeonTea.Quakeball.TeaNet.Peers { void Message(string msg); void Err(string msg); } + + public class TrafficData { + /// The amount of bytes received in the last TrafficDataIntervel + public int Received; + /// The amount of bytes sent in the last TrafficDataIntervel + public int Sent; + /// The amount of total messages received in the last TrafficDataIntervel + public int TotalMessagesReceived; + /// The amount of total messages sent in the last TrafficDataIntervel + public int TotalMessagesSent; + /// The amount of reliable messages received in the last TrafficDataIntervel + public int ReliableReceived; + /// The amount of reliable messages sent in the last TrafficDataIntervel + public int ReliableSent; + /// The amount of unreliable messages received in the last TrafficDataIntervel + public int UnreliableReceived; + /// The amount of unreliable messages sent in the last TrafficDataIntervel + public int UnreliableSent; + /// The amount of bytes sent in the last TrafficDataIntervel by Packet + public Dictionary SentByPacket = new Dictionary(); + /// The amount of bytes received in the last TrafficDataIntervel by Packet + public Dictionary ReceivedByPacket = new Dictionary(); + } }