diff --git a/RelayClient/MainPage.xaml.cs b/RelayClient/MainPage.xaml.cs index 5dd799e..6973b9b 100644 --- a/RelayClient/MainPage.xaml.cs +++ b/RelayClient/MainPage.xaml.cs @@ -3,6 +3,7 @@ using WebSocketSharp; using System.Text.Json; using System.Text.Json.Serialization; using RelayShared.Rtc; +using RelayShared.Services; namespace RelayClient; diff --git a/RelayClient/MauiProgram.cs b/RelayClient/MauiProgram.cs index c6d626a..fe2e144 100644 --- a/RelayClient/MauiProgram.cs +++ b/RelayClient/MauiProgram.cs @@ -5,11 +5,8 @@ namespace RelayClient; public static class MauiProgram { - // public static event Action? MessageSent; public static MauiApp CreateMauiApp() { - //wsc.OnMessage += (sender, e) => OnWebSocketRecieved(sender, e); - //wsc.Connect(); var builder = MauiApp.CreateBuilder(); builder.UseMauiApp().ConfigureFonts(fonts => { @@ -18,8 +15,6 @@ public static class MauiProgram fonts.AddFont("AnonymousPro-Italic.ttf", "AnonymousProItalic"); fonts.AddFont("AnonymousPro-Regular.ttf", "AnonymousProRegular"); }); - - #if DEBUG builder.Services.AddHybridWebViewDeveloperTools(); @@ -28,19 +23,4 @@ public static class MauiProgram return builder.Build(); } - - //public static void OnWebSocketRecieved(object? sender, MessageEventArgs e) - //{ - // Console.WriteLine(sender.ToString()); - // - // ChatSimulator.Send(e.Data.Split(":")[0], e.Data.Split(":")[1]); - // // var message = new ChatMessage - // // { - // // SenderUsername = e.Data.Split(":")[0], - // // Text = e.Data.Split(":")[1], - // // Timestamp = DateTime.Now - // // }; - // // - // // MessageSent?.Invoke(message); - //} } \ No newline at end of file diff --git a/RelayServer/Endpoints/RtcEndpoints.cs b/RelayServer/Endpoints/RtcEndpoints.cs index cebccac..5d0058c 100644 --- a/RelayServer/Endpoints/RtcEndpoints.cs +++ b/RelayServer/Endpoints/RtcEndpoints.cs @@ -1,6 +1,7 @@ using System.Text.Json; using RelayShared.Rtc; using RelayServer.Services.Rtc; +using RelayShared.Services; namespace RelayServer.Endpoints; diff --git a/RelayServer/RelayServer.csproj b/RelayServer/RelayServer.csproj index 0943ae8..88a35cc 100644 --- a/RelayServer/RelayServer.csproj +++ b/RelayServer/RelayServer.csproj @@ -17,8 +17,4 @@ - - - - diff --git a/RelayServer/Services/Rtc/RtcCallService.cs b/RelayServer/Services/Rtc/RtcCallService.cs index ec3775f..8bb3cde 100644 --- a/RelayServer/Services/Rtc/RtcCallService.cs +++ b/RelayServer/Services/Rtc/RtcCallService.cs @@ -1,5 +1,6 @@ using RelayShared.Rtc; using SurrealDb.Net; +using RelayShared.Rtc; namespace RelayServer.Services.Rtc; diff --git a/RelayShared/Rtc/RTCDatabase.cs b/RelayShared/Rtc/RTCDatabase.cs new file mode 100644 index 0000000..707a63c --- /dev/null +++ b/RelayShared/Rtc/RTCDatabase.cs @@ -0,0 +1,40 @@ +using SurrealDb.Net.Models; + +namespace RelayShared.Rtc; + +public sealed class DBActiveCall : Record +{ + public string ChannelId { get; set; } = string.Empty; + public string? OfferUser { get; set; } + public RtcSessionDescription? Offer { get; set; } + public RtcSessionDescription? Answer { get; set; } + public DateTime CreatedAt { get; set; } + public DateTime UpdatedAt { get; set; } + public bool IsActive { get; set; } + public string[] IceCandidates { get; set; } = []; //TODO: Should be array of DBIceCandidates IDs +} + +public sealed class DBOffer : Record +{ + public string ChannelId { get; set; } = string.Empty; + public string Username { get; set; } = string.Empty; + public string Type { get; set; } = string.Empty; + public string Sdp { get; set; } = string.Empty; +} +public sealed class DBAnswer : Record +{ + public string ChannelId { get; set; } = string.Empty; + public string Username { get; set; } = string.Empty; + public string Type { get; set; } = string.Empty; + public string Sdp { get; set; } = string.Empty; +} + +public class DBIceCandidate : Record +{ + public required string ChannelId { get; set; } + public required string Username { get; set; } + public required string Candidate { get; set; } + public string? SdpMid { get; set; } + public int? SdpMLineIndex { get; set; } + public DateTime CreatedAt { get; set; } +} \ No newline at end of file diff --git a/RelayShared/Rtc/RTCTransmissions.cs b/RelayShared/Rtc/RTCTransmissions.cs new file mode 100644 index 0000000..d9bc83d --- /dev/null +++ b/RelayShared/Rtc/RTCTransmissions.cs @@ -0,0 +1,93 @@ +using System.Text.Json.Serialization; +using RelayShared.Services; + +namespace RelayShared.Rtc; + +public sealed class RtcSessionDescription +{ + public string Type { get; set; } = string.Empty; + public string Sdp { get; set; } = string.Empty; +} + +public sealed class RtcOffer +{ + public string ChannelId { get; set; } = string.Empty; + public string Username { get; set; } = string.Empty; + public RtcSessionDescription SessionDescription { get; set; } = new(); +} + +public sealed class RtcAnswer +{ + public string ChannelId { get; set; } = string.Empty; + public string Username { get; set; } = string.Empty; + public RtcSessionDescription SessionDescription { get; set; } = new(); +} +public class RtcIceCandidate +{ + public required string ChannelId { get; set; } + public required string Username { get; set; } + public required IceCandidate Candidate { get; set; } +} + +public class IceCandidate +{ + public required string candidate { get; set; } + public required string sdpMid { get; set; } + public required int sdpMLineIndex { get; set; } + public required string usernameFragment { get; set; } + +} + +public sealed class RtcJoinRequest +{ + public string ChannelId { get; set; } = string.Empty; + public string Username { get; set; } = string.Empty; +} + +public sealed class RtcJoinResponse +{ + public string ChannelId { get; set; } = string.Empty; + public string[] Participants { get; set; } = []; +} + +public sealed class RtcLeaveRequest +{ + public string ChannelId { get; set; } = string.Empty; + public string Username { get; set; } = string.Empty; +} +public sealed class RtcNotificationMessage //TODO: Review for removal +{ + public SignalType? Type { get; set; } + public string? ChannelId { get; set; } + public string? Username { get; set; } + public string? Direction { get; set; } +} +public sealed class RtcSignalMessage //TODO: Review for removal. +{ + [JsonPropertyName("type")] + public string Type { get; set; } = string.Empty; + + [JsonPropertyName("from")] + public string From { get; set; } = string.Empty; + + [JsonPropertyName("to")] + public string To { get; set; } = string.Empty; + + [JsonPropertyName("channelId")] + public string ChannelId { get; set; } = string.Empty; + + [JsonPropertyName("sdp")] + public string? Sdp { get; set; } + + [JsonPropertyName("candidate")] + public string? Candidate { get; set; } + + [JsonPropertyName("sdpMid")] + public string? SdpMid { get; set; } + + [JsonPropertyName("sdpMLineIndex")] + public int? SdpMLineIndex { get; set; } + + [JsonPropertyName("isInitiator")] + public bool IsInitiator { get; set; } +} \ No newline at end of file diff --git a/RelayShared/Rtc/RtcModels.cs b/RelayShared/Rtc/RtcModels.cs deleted file mode 100644 index e167c08..0000000 --- a/RelayShared/Rtc/RtcModels.cs +++ /dev/null @@ -1,198 +0,0 @@ -using System.Text.Json.Serialization; -using RelayShared.Rtc; -using SurrealDb.Net.Models; - -#region Resharper Stuff -// ReSharper disable ClassNeverInstantiated.Global -// ReSharper disable PropertyCanBeMadeInitOnly.Global -// ReSharper disable InconsistentNaming -#endregion - -namespace RelayShared.Rtc; - -public enum SignalType -{ - Offer, - Answer, - Candidate, - OfferUpdated, - AnswerUpdated, - CandidateAdded, - CallLeft, - ChannelList, - ServerPublicKey, - EncryptedSignal, - EncryptedChat, - ClientEncryptedChat -} - -public enum ChannelType -{ - Text, //Default channel type, handles text, links, files*, all in a linear live chat format - Voice, //Used for general voice and video calls, utilizes WebRTC in its intended use - File, //File browser for connected text channels, used for browsing files rather than scrolling through text channel - Forum, //Specific forum posts, meant to keep conversations grouped and on topic while keeping all in an easy to find place - Stage //Used for announcements and presentations, voice/video call utilizing a modified WebRTC protocol through server -} -public sealed class RtcSignalMessage -{ - [JsonPropertyName("type")] - public string Type { get; set; } = string.Empty; - - [JsonPropertyName("from")] - public string From { get; set; } = string.Empty; - - [JsonPropertyName("to")] - public string To { get; set; } = string.Empty; - - [JsonPropertyName("channelId")] - public string ChannelId { get; set; } = string.Empty; - - [JsonPropertyName("sdp")] - public string? Sdp { get; set; } - - [JsonPropertyName("candidate")] - public string? Candidate { get; set; } - - [JsonPropertyName("sdpMid")] - public string? SdpMid { get; set; } - - [JsonPropertyName("sdpMLineIndex")] - public int? SdpMLineIndex { get; set; } - - [JsonPropertyName("isInitiator")] - public bool IsInitiator { get; set; } -} - -public sealed class RtcNotificationMessage -{ - public SignalType? Type { get; set; } - public string? ChannelId { get; set; } - public string? Username { get; set; } - public string? Direction { get; set; } -} - -public sealed class ServerPublicKeyMessage -{ - public SignalType Type { get; set; } = SignalType.ServerPublicKey; - public string PublicKey { get; set; } = string.Empty; -} - -public sealed class SocketRtcSignalMessage -{ - public SignalType Type { get; set; } - public string SenderUsername { get; set; } = string.Empty; - public string ChannelId { get; set; } = string.Empty; - public string CipherText { get; set; } = string.Empty; - public string Nonce { get; set; } = string.Empty; - public string Tag { get; set; } = string.Empty; - public string EncryptedKey { get; set; } = string.Empty; -} - -public sealed class SocketEncryptedMessage -{ - public SignalType Type { get; set; } = SignalType.EncryptedChat; - public string SenderUsername { get; set; } = string.Empty; - public string RecipientUsername { get; set; } = string.Empty; - public string ChannelId { get; set; } = string.Empty; - public string CipherText { get; set; } = string.Empty; - public string Nonce { get; set; } = string.Empty; - public string Tag { get; set; } = string.Empty; - public string EncryptedKey { get; set; } = string.Empty; -} - -public sealed class ChannelItem -{ - public string ChannelId { get; set; } = string.Empty; - public string Name { get; set; } = string.Empty; - - public ChannelType Type { get; set; } - - public string Group { get; set; } = string.Empty; - public DateTime CreatedAt { get; set; } -} - -public sealed class SocketChannelList -{ - public SignalType Type { get; set; } = SignalType.ChannelList; - public List Channels { get; set; } = []; -} - -public sealed class RtcJoinRequest -{ - public string ChannelId { get; set; } = string.Empty; - public string Username { get; set; } = string.Empty; -} - -public sealed class RtcJoinResponse -{ - public string ChannelId { get; set; } = string.Empty; - public bool HasActiveCall { get; set; } - public bool IsOfferer { get; set; } - public string? OfferUser { get; set; } - public RtcSessionDescription? OfferSdp { get; set; } -} - -public sealed class RtcLeaveRequest -{ - public string ChannelId { get; set; } = string.Empty; - public string Username { get; set; } = string.Empty; -} - -public sealed class RtcSessionDescription -{ - public string Type { get; set; } = string.Empty; - public string Sdp { get; set; } = string.Empty; -} - -public sealed class RtcOffer -{ - public string ChannelId { get; set; } = string.Empty; - public string Username { get; set; } = string.Empty; - public RtcSessionDescription SessionDescription { get; set; } = new(); -} - -public sealed class RtcAnswer -{ - public string ChannelId { get; set; } = string.Empty; - public string Username { get; set; } = string.Empty; - public RtcSessionDescription SessionDescription { get; set; } = new(); -} - -public class DBIceCandidate : Record -{ - public required string ChannelId { get; set; } - public required string Username { get; set; } - public required string Candidate { get; set; } - public string? SdpMid { get; set; } - public int? SdpMLineIndex { get; set; } - // public required string Direction { get; set; } // "offer" or "answer" - public DateTime CreatedAt { get; set; } -} - -public class RtcIceCandidate -{ - public required string ChannelId { get; set; } - public required string Username { get; set; } - public required IceCandidate Candidate { get; set; } -} - -public class IceCandidate -{ - public required string candidate { get; set; } - public required string sdpMid { get; set; } - public required int sdpMLineIndex { get; set; } - public required string usernameFragment { get; set; } - -} - -public sealed class DBActiveCall : Record -{ - public string ChannelId { get; set; } = string.Empty; - public string? OfferUser { get; set; } - public RtcSessionDescription? Offer { get; set; } - public RtcSessionDescription? Answer { get; set; } - public DateTime CreatedAt { get; set; } - public DateTime UpdatedAt { get; set; } - public bool IsActive { get; set; } -} \ No newline at end of file diff --git a/RelayShared/Services/ChannelEnums.cs b/RelayShared/Services/ChannelEnums.cs new file mode 100644 index 0000000..73e1d00 --- /dev/null +++ b/RelayShared/Services/ChannelEnums.cs @@ -0,0 +1,10 @@ +namespace RelayShared.Services; + +public enum ChannelType +{ + Text, //Default channel type, handles text, links, files*, all in a linear live chat format + Voice, //Used for general voice and video calls, utilizes WebRTC in its intended use + File, //File browser for connected text channels, used for browsing files rather than scrolling through text channel + Forum, //Specific forum posts, meant to keep conversations grouped and on topic while keeping all in an easy to find place + Stage //Used for announcements and presentations, voice/video call utilizing a modified WebRTC protocol through server +} \ No newline at end of file diff --git a/RelayShared/Services/ChannelTransmissions.cs b/RelayShared/Services/ChannelTransmissions.cs new file mode 100644 index 0000000..99da406 --- /dev/null +++ b/RelayShared/Services/ChannelTransmissions.cs @@ -0,0 +1,18 @@ +namespace RelayShared.Services; + +public sealed class ChannelItem +{ + public string ChannelId { get; set; } = string.Empty; + public string Name { get; set; } = string.Empty; + + public ChannelType Type { get; set; } + + public string Group { get; set; } = string.Empty; + public DateTime CreatedAt { get; set; } +} + +public sealed class SocketChannelList +{ + public SignalType Type { get; set; } = SignalType.ChannelList; + public List Channels { get; set; } = []; +} \ No newline at end of file diff --git a/RelayShared/Services/SocketTransmissions.cs b/RelayShared/Services/SocketTransmissions.cs new file mode 100644 index 0000000..ccf82df --- /dev/null +++ b/RelayShared/Services/SocketTransmissions.cs @@ -0,0 +1,48 @@ +namespace RelayShared.Services; + +//TODO: review name of file, potentially rename for Encryption services rather than sockets + +public sealed class SocketRtcSignalMessage +{ + public SignalType Type { get; set; } + public string SenderUsername { get; set; } = string.Empty; + public string ChannelId { get; set; } = string.Empty; + public string CipherText { get; set; } = string.Empty; + public string Nonce { get; set; } = string.Empty; + public string Tag { get; set; } = string.Empty; + public string EncryptedKey { get; set; } = string.Empty; +} + +public sealed class SocketEncryptedMessage +{ + public SignalType Type { get; set; } = SignalType.EncryptedChat; + public string SenderUsername { get; set; } = string.Empty; + public string RecipientUsername { get; set; } = string.Empty; + public string ChannelId { get; set; } = string.Empty; + public string CipherText { get; set; } = string.Empty; + public string Nonce { get; set; } = string.Empty; + public string Tag { get; set; } = string.Empty; + public string EncryptedKey { get; set; } = string.Empty; +} + +public sealed class ServerPublicKeyMessage +{ + public SignalType Type { get; set; } = SignalType.ServerPublicKey; + public string PublicKey { get; set; } = string.Empty; +} + +public enum SignalType +{ + Offer, + Answer, + Candidate, + OfferUpdated, + AnswerUpdated, + CandidateAdded, + CallLeft, + ChannelList, + ServerPublicKey, + EncryptedSignal, + EncryptedChat, + ClientEncryptedChat +} \ No newline at end of file