From 9736ed31c3d4c85668d86bcdf286ffb40bbc0235 Mon Sep 17 00:00:00 2001 From: Jared Goodwin Date: Tue, 14 Jan 2020 17:48:43 -0800 Subject: [PATCH] Added Server Logs page. Added outgoing buffer throttling in screen caster. Refactoring. --- Agent/Services/Logger.cs | 27 ++++++---- ScreenCast.Core/Capture/ScreenCasterBase.cs | 12 ++++- ScreenCast.Core/Models/Viewer.cs | 1 + ScreenCast.Core/Services/Logger.cs | 10 +--- ScreenCast.Core/Sockets/CasterSocket.cs | 3 +- Server/API/ClientDownloadsController.cs | 2 +- Server/API/CommandsController.cs | 11 ++-- Server/API/DevicesController.cs | 2 +- ...ileSharing.cs => FileSharingController.cs} | 8 +-- Server/API/LoginController.cs | 18 +++++-- Server/API/RemoteControlController.cs | 11 ++-- Server/API/ServerLogsController.cs | 37 +++++++++++++ .../Pages/Account/Manage/ManageNavPages.cs | 3 ++ .../Pages/Account/Manage/Options.cshtml.cs | 2 +- .../Account/Manage/Organization.cshtml.cs | 6 +-- .../Pages/Account/Manage/ServerLogs.cshtml | 53 +++++++++++++++++++ .../Pages/Account/Manage/ServerLogs.cshtml.cs | 16 ++++++ .../Pages/Account/Manage/_ManageNav.cshtml | 25 ++++----- .../Pages/Account/Manage/_ViewImports.cshtml | 2 +- .../Identity/Pages/Account/Register.cshtml | 2 +- Server/Pages/EditDevice.cshtml.cs | 2 +- Server/Pages/Error.cshtml.cs | 4 +- Server/Pages/Index.cshtml.cs | 2 +- Server/Pages/Invite.cshtml.cs | 2 +- Server/Pages/_IndexNotLoggedIn.cshtml | 2 +- Server/Pages/_ViewImports.cshtml | 2 +- Server/Services/BrowserSocketHub.cs | 2 +- Server/{Data => Services}/DataService.cs | 40 +++++++++++--- Server/Services/DeviceSocketHub.cs | 2 +- .../{PascalCase.cs => PascalCasePolicy.cs} | 2 +- Server/Services/RCBrowserSocketHub.cs | 27 +++++++--- Server/Startup.cs | 4 +- .../scripts/RemoteControl/RCBrowserSockets.js | 6 +-- .../RemoteControl/RCBrowserSockets.js.map | 2 +- .../scripts/RemoteControl/RCBrowserSockets.ts | 6 +-- Shared/Models/EventLog.cs | 7 +-- 36 files changed, 264 insertions(+), 99 deletions(-) rename Server/API/{FileSharing.cs => FileSharingController.cs} (89%) create mode 100644 Server/API/ServerLogsController.cs create mode 100644 Server/Areas/Identity/Pages/Account/Manage/ServerLogs.cshtml create mode 100644 Server/Areas/Identity/Pages/Account/Manage/ServerLogs.cshtml.cs rename Server/{Data => Services}/DataService.cs (93%) rename Server/Services/{PascalCase.cs => PascalCasePolicy.cs} (90%) diff --git a/Agent/Services/Logger.cs b/Agent/Services/Logger.cs index c36557f5..2647903a 100644 --- a/Agent/Services/Logger.cs +++ b/Agent/Services/Logger.cs @@ -15,9 +15,9 @@ namespace Remotely.Agent.Services public static object WriteLock { get; } = new object(); public static void Write(string message) { - lock (WriteLock) + try { - try + lock (WriteLock) { var path = Path.Combine(Path.GetTempPath(), "Remotely_Logs.txt"); if (!File.Exists(path)) @@ -28,12 +28,6 @@ namespace Remotely.Agent.Services Process.Start("sudo", $"chmod 666 {path}").WaitForExit(); } } - var jsoninfo = new - { - Type = "Info", - Timestamp = DateTime.Now.ToString(), - Message = message - }; if (File.Exists(path)) { var fi = new FileInfo(path); @@ -44,10 +38,11 @@ namespace Remotely.Agent.Services fi = new FileInfo(path); } } - File.AppendAllText(path, JsonConvert.SerializeObject(jsoninfo) + Environment.NewLine); + File.AppendAllText(path, $"{DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff")}\t[INFO]\t{message}{Environment.NewLine}"); + Console.WriteLine(message); } - catch { } } + catch { } } public static void Write(Exception ex) @@ -59,6 +54,15 @@ namespace Remotely.Agent.Services var exception = ex; var path = Path.Combine(Path.GetTempPath(), "Remotely_Logs.txt"); + if (!File.Exists(path)) + { + File.Create(path).Close(); + if (RuntimeInformation.IsOSPlatform(OSPlatform.Linux)) + { + Process.Start("sudo", $"chmod 666 {path}").WaitForExit(); + } + } + while (exception != null) { var jsonError = new @@ -79,7 +83,8 @@ namespace Remotely.Agent.Services fi = new FileInfo(path); } } - File.AppendAllText(path, JsonConvert.SerializeObject(jsonError) + Environment.NewLine); + File.AppendAllText(path, $"{DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff")}\t[ERROR]\t{exception?.Message}\t{exception?.StackTrace}\t{exception?.Source}{Environment.NewLine}"); + Console.WriteLine(exception.Message); exception = exception.InnerException; } } diff --git a/ScreenCast.Core/Capture/ScreenCasterBase.cs b/ScreenCast.Core/Capture/ScreenCasterBase.cs index 5cfde779..fe4c53a4 100644 --- a/ScreenCast.Core/Capture/ScreenCasterBase.cs +++ b/ScreenCast.Core/Capture/ScreenCasterBase.cs @@ -98,7 +98,14 @@ namespace Remotely.ScreenCast.Core.Capture fpsQueue.Dequeue(); } fpsQueue.Enqueue(DateTime.Now); - Debug.WriteLine("Capture FPS: " + fpsQueue.Count); + Debug.WriteLine($"Capture FPS: {fpsQueue.Count}"); + } + + if (viewer.OutputBuffer > 150_000) + { + Debug.WriteLine($"Waiting for buffer to clear. Size: {viewer.OutputBuffer}"); + await Task.Delay(50); + continue; } capturer.GetNextFrame(); @@ -120,7 +127,7 @@ namespace Remotely.ScreenCast.Core.Capture if (viewer.AutoAdjustQuality && viewer.Latency > 1000) { var quality = (int)(viewer.ImageQuality * 1000 / viewer.Latency); - Logger.Write($"Auto-adjusting image quality. Latency: {viewer.Latency}. Quality: {quality}"); + Debug.WriteLine($"Auto-adjusting image quality. Latency: {viewer.Latency}. Quality: {quality}"); encodedImageBytes = ImageUtils.EncodeBitmap(newImage, new EncoderParameters() { Param = new[] @@ -138,6 +145,7 @@ namespace Remotely.ScreenCast.Core.Capture { await conductor.CasterSocket.SendScreenCapture(encodedImageBytes, viewerID, diffArea.Left, diffArea.Top, diffArea.Width, diffArea.Height, DateTime.UtcNow); viewer.Latency += 300; + viewer.OutputBuffer += encodedImageBytes.Length; } } } diff --git a/ScreenCast.Core/Models/Viewer.cs b/ScreenCast.Core/Models/Viewer.cs index 0186edba..98c21aba 100644 --- a/ScreenCast.Core/Models/Viewer.cs +++ b/ScreenCast.Core/Models/Viewer.cs @@ -53,6 +53,7 @@ namespace Remotely.ScreenCast.Core.Models public double Latency { get; set; } = 1; public string Name { get; set; } + public int OutputBuffer { get; set; } public string ViewerConnectionID { get; set; } } } diff --git a/ScreenCast.Core/Services/Logger.cs b/ScreenCast.Core/Services/Logger.cs index 0c4e2f60..a1e0853d 100644 --- a/ScreenCast.Core/Services/Logger.cs +++ b/ScreenCast.Core/Services/Logger.cs @@ -29,12 +29,6 @@ namespace Remotely.ScreenCast.Core.Services Process.Start("sudo", $"chmod 666 {path}").WaitForExit(); } } - var jsoninfo = new - { - Type = "Info", - Timestamp = DateTime.Now.ToString(), - Message = message - }; if (File.Exists(path)) { var fi = new FileInfo(path); @@ -45,7 +39,7 @@ namespace Remotely.ScreenCast.Core.Services fi = new FileInfo(path); } } - File.AppendAllText(path, JsonSerializer.Serialize(jsoninfo) + Environment.NewLine); + File.AppendAllText(path, $"{DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff")}\t[INFO]\t{message}{Environment.NewLine}"); Console.WriteLine(message); } } @@ -90,7 +84,7 @@ namespace Remotely.ScreenCast.Core.Services fi = new FileInfo(path); } } - File.AppendAllText(path, JsonSerializer.Serialize(jsonError) + Environment.NewLine); + File.AppendAllText(path, $"{DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss.fff")}\t[ERROR]\t{exception?.Message}\t{exception?.StackTrace}\t{exception?.Source}{Environment.NewLine}"); Console.WriteLine(exception.Message); exception = exception.InnerException; } diff --git a/ScreenCast.Core/Sockets/CasterSocket.cs b/ScreenCast.Core/Sockets/CasterSocket.cs index c3dabc39..0d2371ac 100644 --- a/ScreenCast.Core/Sockets/CasterSocket.cs +++ b/ScreenCast.Core/Sockets/CasterSocket.cs @@ -271,12 +271,13 @@ namespace Remotely.ScreenCast.Core.Sockets conductor.InvokeViewerRemoved(viewerID); }); - Connection.On("LatencyUpdate", (DateTime sentTime, string viewerID) => + Connection.On("LatencyUpdate", (DateTime sentTime, int bytesReceived, string viewerID) => { if (conductor.Viewers.TryGetValue(viewerID, out var viewer)) { var latency = DateTime.UtcNow - sentTime; viewer.Latency = latency.TotalMilliseconds; + viewer.OutputBuffer -= bytesReceived; } }); diff --git a/Server/API/ClientDownloadsController.cs b/Server/API/ClientDownloadsController.cs index c4334978..2d5f1331 100644 --- a/Server/API/ClientDownloadsController.cs +++ b/Server/API/ClientDownloadsController.cs @@ -3,12 +3,12 @@ using System.Collections.Generic; using System.IO; using System.Linq; using System.Threading.Tasks; -using Remotely.Server.Data; using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc; using Microsoft.Extensions.FileProviders; using Microsoft.AspNetCore.Hosting; +using Remotely.Server.Services; // For more information on enabling Web API for empty projects, visit https://go.microsoft.com/fwlink/?LinkID=397860 diff --git a/Server/API/CommandsController.cs b/Server/API/CommandsController.cs index 14a9f654..e9b7fadd 100644 --- a/Server/API/CommandsController.cs +++ b/Server/API/CommandsController.cs @@ -7,10 +7,9 @@ using System.Text; using System.Threading.Tasks; using System.Xml.Serialization; using Remotely.Shared.Models; -using Remotely.Server.Data; +using Remotely.Server.Services; using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Mvc; -using Newtonsoft.Json; // For more information on enabling Web API for empty projects, visit https://go.microsoft.com/fwlink/?LinkID=397860 @@ -41,7 +40,7 @@ namespace Remotely.Server.API switch (fileExt.ToUpper()) { case "JSON": - content = JsonConvert.SerializeObject(commandContexts); + content = System.Text.Json.JsonSerializer.Serialize(commandContexts); break; case "XML": var serializer = new DataContractSerializer(typeof(CommandContext)); @@ -67,7 +66,7 @@ namespace Remotely.Server.API switch (fileExt.ToUpper()) { case "JSON": - content = JsonConvert.SerializeObject(commandContext); + content = System.Text.Json.JsonSerializer.Serialize(commandContext); break; case "XML": var serializer = new DataContractSerializer(typeof(CommandContext)); @@ -108,7 +107,7 @@ namespace Remotely.Server.API { case "PSCore": { - var result = JsonConvert.DeserializeObject(content); + var result = System.Text.Json.JsonSerializer.Deserialize(content); var commandContext = DataService.GetCommandContext(result.CommandContextID); commandContext.PSCoreResults.Add(result); DataService.AddOrUpdateCommandContext(commandContext); @@ -118,7 +117,7 @@ namespace Remotely.Server.API case "CMD": case "Bash": { - var result = JsonConvert.DeserializeObject(content); + var result = System.Text.Json.JsonSerializer.Deserialize(content); var commandContext = DataService.GetCommandContext(result.CommandContextID); commandContext.CommandResults.Add(result); DataService.AddOrUpdateCommandContext(commandContext); diff --git a/Server/API/DevicesController.cs b/Server/API/DevicesController.cs index 0e068923..fba0362b 100644 --- a/Server/API/DevicesController.cs +++ b/Server/API/DevicesController.cs @@ -3,7 +3,7 @@ using System.Collections.Generic; using System.Linq; using System.Threading.Tasks; using Remotely.Shared.Models; -using Remotely.Server.Data; +using Remotely.Server.Services; using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Identity; using Microsoft.AspNetCore.Mvc; diff --git a/Server/API/FileSharing.cs b/Server/API/FileSharingController.cs similarity index 89% rename from Server/API/FileSharing.cs rename to Server/API/FileSharingController.cs index 0d328fd5..54ed5f33 100644 --- a/Server/API/FileSharing.cs +++ b/Server/API/FileSharingController.cs @@ -3,7 +3,7 @@ using System.Collections.Generic; using System.IO; using System.Linq; using System.Threading.Tasks; -using Remotely.Server.Data; +using Remotely.Server.Services; using Microsoft.AspNetCore.Hosting; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Mvc; @@ -14,14 +14,14 @@ using Microsoft.Net.Http.Headers; namespace Remotely.Server.API { [Route("api/[controller]")] - public class FileSharing : Controller + public class FileSharingController : Controller { - public FileSharing(DataService dataService) + public FileSharingController(DataService dataService) { DataService = dataService; } public DataService DataService { get; set; } - // GET api//5 + [HttpGet("{id}")] public ActionResult Get(string id) { diff --git a/Server/API/LoginController.cs b/Server/API/LoginController.cs index 5ba3d85d..e9ad0302 100644 --- a/Server/API/LoginController.cs +++ b/Server/API/LoginController.cs @@ -36,30 +36,40 @@ namespace Remotely.Server.API { return NotFound(); } + + var orgId = DataService.GetUserByName(login.Email)?.OrganizationID; + var result = await SignInManager.PasswordSignInAsync(login.Email, login.Password, false, true); if (result.Succeeded) { - DataService.WriteEvent($"API login successful for {login.Email}."); + DataService.WriteEvent($"API login successful for {login.Email}.", orgId); return Ok(); } else if (result.IsLockedOut) { - DataService.WriteEvent($"API login unsuccessful due to lockout for {login.Email}."); + DataService.WriteEvent($"API login unsuccessful due to lockout for {login.Email}.", orgId); return Unauthorized("Account is locked."); } else if (result.RequiresTwoFactor) { - DataService.WriteEvent($"API login unsuccessful due to 2FA for {login.Email}."); + DataService.WriteEvent($"API login unsuccessful due to 2FA for {login.Email}.", orgId); return Unauthorized("Account requires two-factor authentication."); } - DataService.WriteEvent($"API login unsuccessful due to bad attempt for {login.Email}."); + DataService.WriteEvent($"API login unsuccessful due to bad attempt for {login.Email}.", orgId); return BadRequest(); } [HttpGet("Logout")] public async Task Logout() { + string orgId = null; + + if (HttpContext?.User?.Identity?.IsAuthenticated == true) + { + orgId = DataService.GetUserByName(HttpContext.User.Identity.Name)?.OrganizationID; + } await SignInManager.SignOutAsync(); + DataService.WriteEvent($"API logout successful for {HttpContext?.User?.Identity?.Name}.", orgId); return Ok(); } } diff --git a/Server/API/RemoteControlController.cs b/Server/API/RemoteControlController.cs index d71ab22c..9aa4c498 100644 --- a/Server/API/RemoteControlController.cs +++ b/Server/API/RemoteControlController.cs @@ -47,23 +47,26 @@ namespace Remotely.Server.API { return NotFound(); } + + var orgId = DataService.GetUserByName(rcRequest.Email)?.OrganizationID; + var result = await SignInManager.PasswordSignInAsync(rcRequest.Email, rcRequest.Password, false, true); if (result.Succeeded) { - DataService.WriteEvent($"API login successful for {rcRequest.Email}."); + DataService.WriteEvent($"API login successful for {rcRequest.Email}.", orgId); return await InitiateRemoteControl(rcRequest.DeviceID, rcRequest.Email); } else if (result.IsLockedOut) { - DataService.WriteEvent($"API login unsuccessful due to lockout for {rcRequest.Email}."); + DataService.WriteEvent($"API login unsuccessful due to lockout for {rcRequest.Email}.", orgId); return Unauthorized("Account is locked."); } else if (result.RequiresTwoFactor) { - DataService.WriteEvent($"API login unsuccessful due to 2FA for {rcRequest.Email}."); + DataService.WriteEvent($"API login unsuccessful due to 2FA for {rcRequest.Email}.", orgId); return Unauthorized("Account requires two-factor authentication."); } - DataService.WriteEvent($"API login unsuccessful due to bad attempt for {rcRequest.Email}."); + DataService.WriteEvent($"API login unsuccessful due to bad attempt for {rcRequest.Email}.", orgId); return BadRequest(); } diff --git a/Server/API/ServerLogsController.cs b/Server/API/ServerLogsController.cs new file mode 100644 index 00000000..fdd4da3d --- /dev/null +++ b/Server/API/ServerLogsController.cs @@ -0,0 +1,37 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Net.Mime; +using System.Text; +using System.Text.Json; +using System.Threading.Tasks; +using Microsoft.AspNetCore.Authorization; +using Microsoft.AspNetCore.Http; +using Microsoft.AspNetCore.Mvc; +using Remotely.Server.Services; +using Remotely.Shared.Models; + +namespace Remotely.Server.API +{ + [Route("api/[controller]")] + [ApiController] + [Authorize] + public class ServerLogsController : ControllerBase + { + + public ServerLogsController(DataService dataService) + { + DataService = dataService; + } + public DataService DataService { get; set; } + + // GET: api/ServerLogs + [HttpGet("Download")] + public ActionResult Download() + { + var logs = DataService.GetAllEventLogs(HttpContext.User.Identity.Name); + var fileBytes = Encoding.UTF8.GetBytes(JsonSerializer.Serialize(logs)); + return File(fileBytes, "application/octet-stream", "ServerLogs.json"); + } + } +} diff --git a/Server/Areas/Identity/Pages/Account/Manage/ManageNavPages.cs b/Server/Areas/Identity/Pages/Account/Manage/ManageNavPages.cs index b40cd990..a5e8bb48 100644 --- a/Server/Areas/Identity/Pages/Account/Manage/ManageNavPages.cs +++ b/Server/Areas/Identity/Pages/Account/Manage/ManageNavPages.cs @@ -24,6 +24,8 @@ namespace Remotely.Server.Areas.Identity.Pages.Account.Manage public static string Options => "Options"; public static string Organization => "Organization"; + public static string ServerLogs => "ServerLogs"; + public static string IndexNavClass(ViewContext viewContext) => PageNavClass(viewContext, Index); public static string ChangePasswordNavClass(ViewContext viewContext) => PageNavClass(viewContext, ChangePassword); @@ -39,6 +41,7 @@ namespace Remotely.Server.Areas.Identity.Pages.Account.Manage public static string TwoFactorAuthenticationNavClass(ViewContext viewContext) => PageNavClass(viewContext, TwoFactorAuthentication); public static string OptionsNavClass(ViewContext viewContext) => PageNavClass(viewContext, Options); public static string OrganizationNavClass(ViewContext viewContext) => PageNavClass(viewContext, Organization); + public static string ServerLogsNavClass(ViewContext viewContext) => PageNavClass(viewContext, ServerLogs); public static string PageNavClass(ViewContext viewContext, string page) { diff --git a/Server/Areas/Identity/Pages/Account/Manage/Options.cshtml.cs b/Server/Areas/Identity/Pages/Account/Manage/Options.cshtml.cs index 610828ee..521d7689 100644 --- a/Server/Areas/Identity/Pages/Account/Manage/Options.cshtml.cs +++ b/Server/Areas/Identity/Pages/Account/Manage/Options.cshtml.cs @@ -3,7 +3,7 @@ using System.Collections.Generic; using System.Linq; using System.Threading.Tasks; using Remotely.Shared.Models; -using Remotely.Server.Data; +using Remotely.Server.Services; using Microsoft.AspNetCore.Identity; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.RazorPages; diff --git a/Server/Areas/Identity/Pages/Account/Manage/Organization.cshtml.cs b/Server/Areas/Identity/Pages/Account/Manage/Organization.cshtml.cs index b2f50fc6..d4492f87 100644 --- a/Server/Areas/Identity/Pages/Account/Manage/Organization.cshtml.cs +++ b/Server/Areas/Identity/Pages/Account/Manage/Organization.cshtml.cs @@ -1,6 +1,6 @@ using Remotely.Shared.Models; using Remotely.Shared.ViewModels; -using Remotely.Server.Data; +using Remotely.Server.Services; using Microsoft.AspNetCore.Identity; using Microsoft.AspNetCore.Mvc.RazorPages; using System.Collections.Generic; @@ -13,10 +13,9 @@ namespace Remotely.Server.Areas.Identity.Pages.Account.Manage { public class OrganizationModel : PageModel { - public OrganizationModel(DataService dataService, UserManager userManager) + public OrganizationModel(DataService dataService) { DataService = dataService; - UserManager = userManager; } public List DeviceGroups { get; } = new List(); @@ -31,7 +30,6 @@ namespace Remotely.Server.Areas.Identity.Pages.Account.Manage public List Users { get; set; } private DataService DataService { get; } - private UserManager UserManager { get; } public void OnGet() { OrganizationName = DataService.GetOrganizationName(User.Identity.Name); diff --git a/Server/Areas/Identity/Pages/Account/Manage/ServerLogs.cshtml b/Server/Areas/Identity/Pages/Account/Manage/ServerLogs.cshtml new file mode 100644 index 00000000..bc8e5942 --- /dev/null +++ b/Server/Areas/Identity/Pages/Account/Manage/ServerLogs.cshtml @@ -0,0 +1,53 @@ +@page +@model Remotely.Server.Areas.Identity.Pages.Account.Manage.ServerLogsModel +@inject DataService DataService +@{ + ViewData["Title"] = "Server Logs"; + var currentUser = DataService.GetUserByName(User.Identity.Name); + var isAdmin = currentUser.IsAdministrator; + var eventLogs = DataService.GetAllEventLogs(User.Identity.Name); +} +

@ViewData["Title"]

+ +@if (isAdmin) +{ +
+
+ + +
+
+ + + + + + + + + + + + @foreach (var eventLog in eventLogs) + { + + + + + + + + } + +
TypeTimestampMessageSourceStack Trace
@eventLog.EventType@eventLog.TimeStamp@eventLog.Message@eventLog.Source@eventLog.StackTrace
+} +else +{ +
Only organization administrators can view this page.
+} \ No newline at end of file diff --git a/Server/Areas/Identity/Pages/Account/Manage/ServerLogs.cshtml.cs b/Server/Areas/Identity/Pages/Account/Manage/ServerLogs.cshtml.cs new file mode 100644 index 00000000..560d5021 --- /dev/null +++ b/Server/Areas/Identity/Pages/Account/Manage/ServerLogs.cshtml.cs @@ -0,0 +1,16 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Threading.Tasks; +using Microsoft.AspNetCore.Mvc; +using Microsoft.AspNetCore.Mvc.RazorPages; + +namespace Remotely.Server.Areas.Identity.Pages.Account.Manage +{ + public class ServerLogsModel : PageModel + { + public void OnGet() + { + } + } +} diff --git a/Server/Areas/Identity/Pages/Account/Manage/_ManageNav.cshtml b/Server/Areas/Identity/Pages/Account/Manage/_ManageNav.cshtml index 09a9e4f7..ddb0d472 100644 --- a/Server/Areas/Identity/Pages/Account/Manage/_ManageNav.cshtml +++ b/Server/Areas/Identity/Pages/Account/Manage/_ManageNav.cshtml @@ -3,15 +3,16 @@ var hasExternalLogins = (await SignInManager.GetExternalAuthenticationSchemesAsync()).Any(); } - + diff --git a/Server/Areas/Identity/Pages/Account/Manage/_ViewImports.cshtml b/Server/Areas/Identity/Pages/Account/Manage/_ViewImports.cshtml index 106be22c..377d4811 100644 --- a/Server/Areas/Identity/Pages/Account/Manage/_ViewImports.cshtml +++ b/Server/Areas/Identity/Pages/Account/Manage/_ViewImports.cshtml @@ -1,3 +1,3 @@ @using Remotely.Server.Areas.Identity.Pages.Account.Manage -@using Remotely.Server.Data; +@using Remotely.Server.Services @using Remotely.Shared.Models diff --git a/Server/Areas/Identity/Pages/Account/Register.cshtml b/Server/Areas/Identity/Pages/Account/Register.cshtml index 390528b8..fb896f0e 100644 --- a/Server/Areas/Identity/Pages/Account/Register.cshtml +++ b/Server/Areas/Identity/Pages/Account/Register.cshtml @@ -1,6 +1,6 @@ @page @inject Remotely.Server.Services.ApplicationConfig AppConfig -@inject Remotely.Server.Data.DataService DataService +@inject Remotely.Server.Services.DataService DataService @model RegisterModel @{ ViewData["Title"] = "Register"; diff --git a/Server/Pages/EditDevice.cshtml.cs b/Server/Pages/EditDevice.cshtml.cs index 21e501ec..128395b5 100644 --- a/Server/Pages/EditDevice.cshtml.cs +++ b/Server/Pages/EditDevice.cshtml.cs @@ -7,7 +7,7 @@ using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.RazorPages; using Microsoft.AspNetCore.Mvc.Rendering; -using Remotely.Server.Data; +using Remotely.Server.Services; namespace Remotely.Server.Pages { diff --git a/Server/Pages/Error.cshtml.cs b/Server/Pages/Error.cshtml.cs index 407583ad..1da1e343 100644 --- a/Server/Pages/Error.cshtml.cs +++ b/Server/Pages/Error.cshtml.cs @@ -3,7 +3,7 @@ using System.Collections.Generic; using System.Diagnostics; using System.Linq; using System.Threading.Tasks; -using Remotely.Server.Data; +using Remotely.Server.Services; using Microsoft.AspNetCore.Diagnostics; using Microsoft.AspNetCore.Hosting; using Microsoft.AspNetCore.Mvc; @@ -38,7 +38,7 @@ namespace Remotely.Server.Pages { var logEntry = new Remotely.Shared.Models.EventLog() { - EventType = Remotely.Shared.Models.EventTypes.Error, + EventType = Remotely.Shared.Models.EventType.Error, Message = error.Message, Source = error.Source, StackTrace = error.StackTrace, diff --git a/Server/Pages/Index.cshtml.cs b/Server/Pages/Index.cshtml.cs index 86e54b11..12ab5769 100644 --- a/Server/Pages/Index.cshtml.cs +++ b/Server/Pages/Index.cshtml.cs @@ -2,12 +2,12 @@ using System.Collections.Generic; using System.Linq; using System.Threading.Tasks; -using Remotely.Server.Data; using Microsoft.AspNetCore.Identity; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.RazorPages; using Remotely.Shared.Models; using Microsoft.AspNetCore.Mvc.Rendering; +using Remotely.Server.Services; namespace Remotely.Server.Pages { diff --git a/Server/Pages/Invite.cshtml.cs b/Server/Pages/Invite.cshtml.cs index 4f40183d..badb7ced 100644 --- a/Server/Pages/Invite.cshtml.cs +++ b/Server/Pages/Invite.cshtml.cs @@ -2,7 +2,7 @@ using System.Collections.Generic; using System.Linq; using System.Threading.Tasks; -using Remotely.Server.Data; +using Remotely.Server.Services; using Microsoft.AspNetCore.Authorization; using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc.RazorPages; diff --git a/Server/Pages/_IndexNotLoggedIn.cshtml b/Server/Pages/_IndexNotLoggedIn.cshtml index 3920aa7e..35dc8f23 100644 --- a/Server/Pages/_IndexNotLoggedIn.cshtml +++ b/Server/Pages/_IndexNotLoggedIn.cshtml @@ -1,5 +1,5 @@ @inject Remotely.Server.Services.ApplicationConfig AppConfig -@inject Remotely.Server.Data.DataService DataService +@inject Remotely.Server.Services.DataService DataService @model IndexModel @{ var organizationCount = DataService.GetOrganizationCount(); diff --git a/Server/Pages/_ViewImports.cshtml b/Server/Pages/_ViewImports.cshtml index e872f413..22df3c22 100644 --- a/Server/Pages/_ViewImports.cshtml +++ b/Server/Pages/_ViewImports.cshtml @@ -1,5 +1,5 @@ @using Microsoft.AspNetCore.Identity @using Remotely.Server -@using Remotely.Server.Data +@using Remotely.Server.Services @namespace Remotely.Server.Pages @addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers diff --git a/Server/Services/BrowserSocketHub.cs b/Server/Services/BrowserSocketHub.cs index 18eb615c..00e2992e 100644 --- a/Server/Services/BrowserSocketHub.cs +++ b/Server/Services/BrowserSocketHub.cs @@ -140,7 +140,7 @@ namespace Remotely.Server.Services { DataService.WriteEvent(new EventLog() { - EventType = EventTypes.Info, + EventType = EventType.Info, Message = $"File transfer started by {RemotelyUser.UserName}. File transfer IDs: {string.Join(", ", fileIDs)}.", TimeStamp = DateTime.Now, OrganizationID = RemotelyUser.OrganizationID diff --git a/Server/Data/DataService.cs b/Server/Services/DataService.cs similarity index 93% rename from Server/Data/DataService.cs rename to Server/Services/DataService.cs index 8627ed67..9c0dfce6 100644 --- a/Server/Data/DataService.cs +++ b/Server/Services/DataService.cs @@ -1,6 +1,5 @@ using Remotely.Shared.Models; using Remotely.Shared.ViewModels; -using Remotely.Server.Services; using Microsoft.AspNetCore.Http; using Microsoft.AspNetCore.Identity; using Microsoft.EntityFrameworkCore; @@ -9,8 +8,9 @@ using System.Collections.Generic; using System.IO; using System.Linq; using Remotely.Shared.ViewModels.Organization; +using Remotely.Server.Data; -namespace Remotely.Server.Data +namespace Remotely.Server.Services { public class DataService { @@ -119,7 +119,7 @@ namespace Remotely.Server.Data { WriteEvent(new EventLog() { - EventType = EventTypes.Info, + EventType = EventType.Info, Message = $"Unable to add device {device.DeviceName} because organization {device.OrganizationID} does not exist.", Source = "DataService.AddOrUpdateDevice" }); @@ -269,9 +269,20 @@ namespace Remotely.Server.Data public IEnumerable GetAllCommandContexts(string userName) { - var orgID = GetUserByName(userName).OrganizationID; + var orgID = RemotelyContext.Users + .FirstOrDefault(x => x.UserName == userName) + ?.OrganizationID; + return RemotelyContext.CommandContexts.Where(x => x.OrganizationID == orgID); } + public IEnumerable GetAllEventLogs(string userName) + { + var orgID = RemotelyContext.Users + .FirstOrDefault(x => x.UserName == userName) + ?.OrganizationID; + + return RemotelyContext.EventLogs.Where(x => x.OrganizationID == orgID); + } public IEnumerable GetAllDevicesForUser(string userID) { @@ -513,7 +524,7 @@ namespace Remotely.Server.Data { RemotelyContext.EventLogs.Add(new EventLog() { - EventType = EventTypes.Error, + EventType = EventType.Error, Message = ex.Message, Source = ex.Source, StackTrace = ex.StackTrace, @@ -522,13 +533,26 @@ namespace Remotely.Server.Data RemotelyContext.SaveChanges(); } - public void WriteEvent(string message) + public void WriteEvent(string message, string organizationId) { RemotelyContext.EventLogs.Add(new EventLog() { - EventType = EventTypes.Info, + EventType = EventType.Info, Message = message, - TimeStamp = DateTime.Now + TimeStamp = DateTime.Now, + OrganizationID = organizationId + }); + RemotelyContext.SaveChanges(); + } + + public void WriteEvent(string message, EventType eventType, string organizationId) + { + RemotelyContext.EventLogs.Add(new EventLog() + { + EventType = eventType, + Message = message, + TimeStamp = DateTime.Now, + OrganizationID = organizationId }); RemotelyContext.SaveChanges(); } diff --git a/Server/Services/DeviceSocketHub.cs b/Server/Services/DeviceSocketHub.cs index 0a692ae5..7786bc8d 100644 --- a/Server/Services/DeviceSocketHub.cs +++ b/Server/Services/DeviceSocketHub.cs @@ -68,7 +68,7 @@ namespace Remotely.Server.Services { DataService.WriteEvent(new EventLog() { - EventType = EventTypes.Info, + EventType = EventType.Info, OrganizationID = device.OrganizationID, Message = $"Device connection for {device?.DeviceName} was denied because it is already connected." }); diff --git a/Server/Services/PascalCase.cs b/Server/Services/PascalCasePolicy.cs similarity index 90% rename from Server/Services/PascalCase.cs rename to Server/Services/PascalCasePolicy.cs index 0decdfcb..1393849b 100644 --- a/Server/Services/PascalCase.cs +++ b/Server/Services/PascalCasePolicy.cs @@ -6,7 +6,7 @@ using System.Threading.Tasks; namespace Remotely.Server.Services { - public class PascalCase : JsonNamingPolicy + public class PascalCasePolicy : JsonNamingPolicy { public override string ConvertName(string name) { diff --git a/Server/Services/RCBrowserSocketHub.cs b/Server/Services/RCBrowserSocketHub.cs index 5bbe42da..46c43702 100644 --- a/Server/Services/RCBrowserSocketHub.cs +++ b/Server/Services/RCBrowserSocketHub.cs @@ -150,9 +150,9 @@ namespace Remotely.Server.Services await RCDeviceHub.Clients.Client(ScreenCasterID).SendAsync("ClipboardTransfer", transferText, typeText, Context.ConnectionId); } - public async Task SendLatencyUpdate(DateTime sentTime) + public async Task SendLatencyUpdate(DateTime sentTime, int bytesRecieved) { - await RCDeviceHub.Clients.Client(ScreenCasterID).SendAsync("LatencyUpdate", sentTime, Context.ConnectionId); + await RCDeviceHub.Clients.Client(ScreenCasterID).SendAsync("LatencyUpdate", sentTime, bytesRecieved, Context.ConnectionId); } public async Task SendQualityChange(int qualityLevel) @@ -177,24 +177,35 @@ namespace Remotely.Server.Services screenCasterID = RCDeviceSocketHub.SessionInfoList.First(x => x.Value.AttendedSessionID == screenCasterID).Value.RCSocketID; } - + + string orgId = null; + + if (Context?.User?.Identity?.IsAuthenticated == true) + { + orgId = DataService.GetUserByID(Context.UserIdentifier).OrganizationID; + } + + RCDeviceSocketHub.SessionInfoList.TryGetValue(screenCasterID, out var sessionInfo); + DataService.WriteEvent(new EventLog() { - EventType = EventTypes.Info, + EventType = EventType.Info, TimeStamp = DateTime.Now, Message = $"Remote control session requested. " + + $"Login ID (if logged in): {Context?.User?.Identity?.Name}. " + + $"Machine Name: {sessionInfo.MachineName}. " + + $"Requester Name (if specified): {requesterName}. " + $"Connection ID: {Context.ConnectionId}. User ID: {Context.UserIdentifier}. " + $"Screen Caster ID: {screenCasterID}. " + $"Mode: {((RemoteControlMode)remoteControlMode).ToString()}. " + - $"Login ID (if logged in): {Context?.User?.Identity?.Name}. " + - $"Rquester Name (if specified): {requesterName}. " + - $"Requester IP Address: " + Context?.GetHttpContext()?.Connection?.RemoteIpAddress?.ToString() + $"Requester IP Address: " + Context?.GetHttpContext()?.Connection?.RemoteIpAddress?.ToString(), + OrganizationID = orgId }); ScreenCasterID = screenCasterID; Mode = (RemoteControlMode)remoteControlMode; RequesterName = requesterName; - var sessionInfo = RCDeviceSocketHub.SessionInfoList.FirstOrDefault(x => x.Value.RCSocketID == screenCasterID).Value; + if (Mode == RemoteControlMode.Unattended) { sessionInfo.Mode = RemoteControlMode.Unattended; diff --git a/Server/Startup.cs b/Server/Startup.cs index 4d405abb..e8b8c01e 100644 --- a/Server/Startup.cs +++ b/Server/Startup.cs @@ -132,7 +132,7 @@ namespace Remotely.Server services.AddMvc() .SetCompatibilityVersion(CompatibilityVersion.Version_3_0).AddJsonOptions(options => { - options.JsonSerializerOptions.PropertyNamingPolicy = new PascalCase(); + options.JsonSerializerOptions.PropertyNamingPolicy = new PascalCasePolicy(); }); services.AddSignalR(options => @@ -142,7 +142,7 @@ namespace Remotely.Server }) .AddJsonProtocol(options => { - options.PayloadSerializerOptions.PropertyNamingPolicy = new PascalCase(); + options.PayloadSerializerOptions.PropertyNamingPolicy = new PascalCasePolicy(); }) .AddMessagePackProtocol(); diff --git a/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.js b/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.js index 6d3f6261..35c0f03e 100644 --- a/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.js +++ b/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.js @@ -36,8 +36,8 @@ export class RCBrowserSockets { SendScreenCastRequestToDevice() { this.Connection.invoke("SendScreenCastRequestToDevice", RemoteControl.ClientID, RemoteControl.RequesterName, RemoteControl.Mode); } - SendLatencyUpdate(sentTime) { - this.Connection.invoke("SendLatencyUpdate", sentTime); + SendLatencyUpdate(sentTime, bytesReceived) { + this.Connection.invoke("SendLatencyUpdate", sentTime, bytesReceived); } SendSelectScreen(index) { this.Connection.invoke("SelectScreen", index); @@ -128,7 +128,7 @@ export class RCBrowserSockets { UI.Screen2DContext.clearRect(0, 0, width, height); }); hubConnection.on("ScreenCapture", (buffer, left, top, width, height, captureTime) => { - this.SendLatencyUpdate(captureTime); + this.SendLatencyUpdate(captureTime, buffer.byteLength); var url = window.URL.createObjectURL(new Blob([buffer])); var img = document.createElement("img"); img.onload = () => { diff --git a/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.js.map b/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.js.map index 6e5e517f..3c8401ad 100644 --- a/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.js.map +++ b/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.js.map @@ -1 +1 @@ -{"version":3,"file":"RCBrowserSockets.js","sourceRoot":"","sources":["RCBrowserSockets.ts"],"names":[],"mappings":"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"} \ No newline at end of file +{"version":3,"file":"RCBrowserSockets.js","sourceRoot":"","sources":["RCBrowserSockets.ts"],"names":[],"mappings":"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"} \ No newline at end of file diff --git a/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.ts b/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.ts index 406a911f..f97e6d68 100644 --- a/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.ts +++ b/Server/wwwroot/scripts/RemoteControl/RCBrowserSockets.ts @@ -49,8 +49,8 @@ export class RCBrowserSockets { SendScreenCastRequestToDevice() { this.Connection.invoke("SendScreenCastRequestToDevice", RemoteControl.ClientID, RemoteControl.RequesterName, RemoteControl.Mode); } - SendLatencyUpdate(sentTime: Date) { - this.Connection.invoke("SendLatencyUpdate", sentTime); + SendLatencyUpdate(sentTime: Date, bytesReceived: number) { + this.Connection.invoke("SendLatencyUpdate", sentTime, bytesReceived); } SendSelectScreen(index: number) { this.Connection.invoke("SelectScreen", index); @@ -142,7 +142,7 @@ export class RCBrowserSockets { }); hubConnection.on("ScreenCapture", (buffer: Uint8Array, left:number, top:number, width:number, height:number, captureTime: Date) => { - this.SendLatencyUpdate(captureTime); + this.SendLatencyUpdate(captureTime, buffer.byteLength); var url = window.URL.createObjectURL(new Blob([buffer])); var img = document.createElement("img"); diff --git a/Shared/Models/EventLog.cs b/Shared/Models/EventLog.cs index 87566060..56e69874 100644 --- a/Shared/Models/EventLog.cs +++ b/Shared/Models/EventLog.cs @@ -10,7 +10,7 @@ namespace Remotely.Shared.Models { [Key] public string ID { get; set; } = Guid.NewGuid().ToString(); - public EventTypes EventType { get; set; } + public EventType EventType { get; set; } public string Message { get; set; } public string Source { get; set; } public string StackTrace { get; set; } @@ -19,10 +19,11 @@ namespace Remotely.Shared.Models [JsonIgnore] public virtual Organization Organization { get; set; } } - public enum EventTypes + public enum EventType { Info = 0, Error = 1, - Debug = 2 + Debug = 2, + Warning = 3 } }