Skip to content

Commit

Permalink
Another pass of nullable refactoring.
Browse files Browse the repository at this point in the history
  • Loading branch information
bitbound committed Jul 26, 2023
1 parent 0f9ea49 commit ac6487c
Show file tree
Hide file tree
Showing 89 changed files with 665 additions and 458 deletions.
32 changes: 17 additions & 15 deletions Agent.Installer.Win/Services/InstallerService.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using IWshRuntimeLibrary;
#nullable enable
using IWshRuntimeLibrary;
using Microsoft.VisualBasic.FileIO;
using Microsoft.Win32;
using Remotely.Agent.Installer.Win.Utilities;
Expand Down Expand Up @@ -26,14 +27,14 @@ public class InstallerService
private readonly string _platform = Environment.Is64BitOperatingSystem ? "x64" : "x86";
private readonly JavaScriptSerializer _serializer = new JavaScriptSerializer();

public event EventHandler<string> ProgressMessageChanged;
public event EventHandler<int> ProgressValueChanged;
public event EventHandler<string>? ProgressMessageChanged;
public event EventHandler<int>? ProgressValueChanged;

public async Task<bool> Install(string serverUrl,
string organizationId,
string deviceGroup,
string deviceAlias,
string deviceUuid,
string? deviceGroup,
string? deviceAlias,
string? deviceUuid,
bool createSupportShortcut)
{
try
Expand Down Expand Up @@ -174,8 +175,8 @@ private void ClearInstallDirectory()

private async Task CreateDeviceOnServer(string deviceUuid,
string serverUrl,
string deviceGroup,
string deviceAlias,
string? deviceGroup,
string? deviceAlias,
string organizationId)
{
try
Expand All @@ -199,9 +200,10 @@ private async Task CreateDeviceOnServer(string deviceUuid,
{
await sw.WriteAsync(_serializer.Serialize(setupOptions));
}
using (var response = await wr.GetResponseAsync() as HttpWebResponse)
{
Logger.Write($"Create device response: {response.StatusCode}");
using var response = await wr.GetResponseAsync();
if (response is HttpWebResponse httpResponse)
{
Logger.Write($"Create device response: {httpResponse.StatusCode}");
}
}
}
Expand Down Expand Up @@ -261,7 +263,7 @@ private async Task DownloadRemotelyAgent(string serverUrl)
}
else
{
ProgressMessageChanged.Invoke(this, "Downloading Remotely agent.");
ProgressMessageChanged?.Invoke(this, "Downloading Remotely agent.");
using (var client = new WebClient())
{
client.DownloadProgressChanged += (sender, args) =>
Expand All @@ -273,7 +275,7 @@ private async Task DownloadRemotelyAgent(string serverUrl)
}
}

ProgressMessageChanged.Invoke(this, "Extracting Remotely files.");
ProgressMessageChanged?.Invoke(this, "Extracting Remotely files.");
ProgressValueChanged?.Invoke(this, 0);

var tempDir = Path.Combine(Path.GetTempPath(), "RemotelyUpdate");
Expand Down Expand Up @@ -321,7 +323,7 @@ private async Task DownloadRemotelyAgent(string serverUrl)
ProgressValueChanged?.Invoke(this, 0);
}

private ConnectionInfo GetConnectionInfo(string organizationId, string serverUrl, string deviceUuid)
private ConnectionInfo GetConnectionInfo(string organizationId, string serverUrl, string? deviceUuid)
{
ConnectionInfo connectionInfo;
var connectionInfoPath = Path.Combine(_installPath, "ConnectionInfo.json");
Expand All @@ -345,7 +347,7 @@ private ConnectionInfo GetConnectionInfo(string organizationId, string serverUrl
{
connectionInfo.ServerVerificationToken = null;
}
connectionInfo.DeviceID = deviceUuid;
connectionInfo.DeviceID = deviceUuid!;
}
connectionInfo.OrganizationID = organizationId;
connectionInfo.Host = serverUrl;
Expand Down
8 changes: 7 additions & 1 deletion Agent.Installer.Win/ViewModels/MainWindowViewModel.cs
Original file line number Diff line number Diff line change
Expand Up @@ -465,7 +465,13 @@ private async Task Install()

HeaderMessage = "Installing Remotely...";

if (await _installer.Install(ServerUrl, OrganizationID, DeviceGroup, DeviceAlias, DeviceUuid, CreateSupportShortcut))
if (await _installer.Install(
ServerUrl,
OrganizationID!,
DeviceGroup,
DeviceAlias,
DeviceUuid,
CreateSupportShortcut))
{
IsServiceInstalled = true;
Progress = 0;
Expand Down
2 changes: 1 addition & 1 deletion Agent/Models/ChatSession.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,5 +5,5 @@ namespace Remotely.Agent.Models;
public class ChatSession
{
public int ProcessID { get; set; }
public NamedPipeClientStream PipeStream { get; set; }
public NamedPipeClientStream? PipeStream { get; set; }
}
108 changes: 89 additions & 19 deletions Agent/Services/AgentHubConnection.cs
Original file line number Diff line number Diff line change
Expand Up @@ -10,12 +10,15 @@
using Remotely.Shared.Services;
using System;
using System.Collections.Generic;
using System.Diagnostics.CodeAnalysis;
using System.IO;
using System.Linq;
using System.Net.Http;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
using System.Timers;
using Timer = System.Timers.Timer;

namespace Remotely.Agent.Services;

Expand All @@ -36,15 +39,16 @@ public class AgentHubConnection : IAgentHubConnection, IDisposable
private readonly IHttpClientFactory _httpFactory;
private readonly IWakeOnLanService _wakeOnLanService;
private readonly ILogger<AgentHubConnection> _logger;
private readonly ILogger _fileLogger;
private readonly IEnumerable<ILoggerProvider> _loggerProviders;
private readonly IScriptExecutor _scriptExecutor;
private readonly IUninstaller _uninstaller;
private readonly IUpdater _updater;

private ConnectionInfo _connectionInfo;
private HubConnection _hubConnection;
private Timer _heartbeatTimer;
private ConnectionInfo? _connectionInfo;
private HubConnection? _hubConnection;
private Timer? _heartbeatTimer;
private bool _isServerVerified;
private FileLogger? _fileLogger;

public AgentHubConnection(
IConfigService configService,
Expand All @@ -69,24 +73,41 @@ public AgentHubConnection(
_httpFactory = httpFactory;
_wakeOnLanService = wakeOnLanService;
_logger = logger;
_fileLogger = loggerProviders
.OfType<FileLoggerProvider>()
.FirstOrDefault()
?.CreateLogger(nameof(AgentHubConnection));
_loggerProviders = loggerProviders;
}

public bool IsConnected => _hubConnection?.State == HubConnectionState.Connected;

public async Task Connect()
{
using var throttle = new SemaphoreSlim(1, 1);
var count = 1;

while (true)
{
try
{
var waitSeconds = Math.Min(60, Math.Pow(count, 2));
// This will allow the first attempt to go through immediately, but
// subsequent attempts will have an exponential delay.
_ = await throttle.WaitAsync(TimeSpan.FromSeconds(waitSeconds));

_logger.LogInformation("Attempting to connect to server.");

_connectionInfo = _configService.GetConnectionInfo();

if (string.IsNullOrWhiteSpace(_connectionInfo.OrganizationID))
{
_logger.LogError("Organization ID is not set. Please set it in the config file.");
continue;
}

if (string.IsNullOrWhiteSpace(_connectionInfo.Host))
{
_logger.LogError("Host (server URL) is not set. Please set it in the config file.");
continue;
}

if (_hubConnection is not null)
{
await _hubConnection.DisposeAsync();
Expand Down Expand Up @@ -116,13 +137,11 @@ public async Task Connect()
// The above can be caused by temporary issues on the server. So we'll do
// nothing here and wait for it to get resolved.
_logger.LogError("There was an issue registering with the server. The server might be undergoing maintenance, or the supplied organization ID might be incorrect.");
await Task.Delay(TimeSpan.FromMinutes(1));
continue;
}

if (!await VerifyServer())
{
await Task.Delay(TimeSpan.FromMinutes(1));
continue;
}

Expand All @@ -144,10 +163,7 @@ public async Task Connect()
catch (Exception ex)
{
_logger.LogError(ex, "Error while connecting to server.");
await Task.Delay(5_000);
}


}
}

Expand All @@ -161,6 +177,17 @@ public async Task SendHeartbeat()
{
try
{
if (_connectionInfo is null || _hubConnection is null)
{
return;
}

if (string.IsNullOrWhiteSpace(_connectionInfo.OrganizationID))
{
_logger.LogError("Organization ID is not set. Please set it in the config file.");
return;
}

var currentInfo = await _deviceInfoService.CreateDevice(_connectionInfo.DeviceID, _connectionInfo.OrganizationID);
await _hubConnection.SendAsync("DeviceHeartbeat", currentInfo);
}
Expand All @@ -172,6 +199,11 @@ public async Task SendHeartbeat()

private async Task<bool> CheckForServerMigration()
{
if (_connectionInfo is null || _hubConnection is null)
{
return false;
}

var serverUrl = await _hubConnection.InvokeAsync<string>("GetServerUrl");

if (Uri.TryCreate(serverUrl, UriKind.Absolute, out var serverUri) &&
Expand All @@ -187,17 +219,22 @@ private async Task<bool> CheckForServerMigration()
return false;
}

private async void HeartbeatTimer_Elapsed(object sender, ElapsedEventArgs e)
private async void HeartbeatTimer_Elapsed(object? sender, ElapsedEventArgs e)
{
await SendHeartbeat();
}

private async Task HubConnection_Reconnected(string arg)
private async Task HubConnection_Reconnected(string? arg)
{
if (_connectionInfo is null || _hubConnection is null)
{
return;
}

_logger.LogInformation("Reconnected to server.");
await _updater.CheckForUpdates();

var device = await _deviceInfoService.CreateDevice(_connectionInfo.DeviceID, _connectionInfo.OrganizationID);
var device = await _deviceInfoService.CreateDevice(_connectionInfo.DeviceID, $"{_connectionInfo.OrganizationID}");

if (!await _hubConnection.InvokeAsync<bool>("DeviceCameOnline", device))
{
Expand All @@ -214,6 +251,10 @@ private async Task HubConnection_Reconnected(string arg)

private void RegisterMessageHandlers()
{
if (_hubConnection is null)
{
throw new InvalidOperationException("Hub connection is null.");
}

_hubConnection.On("ChangeWindowsSession", async (string viewerConnectionId, string sessionId, string accessKey, string userConnectionId, string requesterName, string orgName, string orgId, int targetSessionID) =>
{
Expand Down Expand Up @@ -263,6 +304,10 @@ private void RegisterMessageHandlers()

_hubConnection.On("DeleteLogs", () =>
{
if (TryGetFileLogger(out var fileLogger))
{
fileLogger.DeleteLogs();
}
if (_fileLogger is FileLogger logger)
{
logger.DeleteLogs();
Expand Down Expand Up @@ -466,13 +511,14 @@ private void RegisterMessageHandlers()
foreach (var fileID in fileIDs)
{
var url = $"{_connectionInfo.Host}/API/FileSharing/{fileID}";
var url = $"{_connectionInfo?.Host}/API/FileSharing/{fileID}";
using var client = _httpFactory.CreateClient();
client.DefaultRequestHeaders.Add(AppConstants.ExpiringTokenHeaderName, expiringToken);
using var response = await client.GetAsync(url);
var filename = response.Content.Headers.ContentDisposition.FileName;
var legalChars = filename.ToCharArray().Where(x => !Path.GetInvalidFileNameChars().Any(y => x == y));
var filename = response.Content.Headers.ContentDisposition?.FileName ?? Path.GetRandomFileName();
var invalidChars = Path.GetInvalidFileNameChars().ToHashSet();
var legalChars = filename.ToCharArray().Where(x => !invalidChars.Contains(x));
filename = new string(legalChars.ToArray());
Expand All @@ -499,8 +545,32 @@ private void RegisterMessageHandlers()
});
}

private bool TryGetFileLogger([NotNullWhen(true)] out FileLogger? fileLogger)
{
if (_fileLogger is null)
{
var logger = _loggerProviders
.OfType<FileLoggerProvider>()
.FirstOrDefault()
?.CreateLogger(nameof(AgentHubConnection));

if (logger is FileLogger loggerImpl)
{
_fileLogger = loggerImpl;
}
}

fileLogger = _fileLogger;
return fileLogger is not null;
}

private async Task<bool> VerifyServer()
{
if (_connectionInfo is null || _hubConnection is null)
{
return false;
}

if (string.IsNullOrWhiteSpace(_connectionInfo.ServerVerificationToken))
{
_isServerVerified = true;
Expand Down
6 changes: 3 additions & 3 deletions Agent/Services/ChatClientService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ public class ChatClientService : IChatClientService
{
return;
}
chatSession.PipeStream.Dispose();
chatSession.PipeStream?.Dispose();
var chatProcess = Process.GetProcessById(chatSession.ProcessID);
if (chatProcess?.HasExited == false)
{
Expand Down Expand Up @@ -111,7 +111,7 @@ public async Task SendMessage(

chatSession = (ChatSession)_chatClients.Get(senderConnectionID);

if (!chatSession.PipeStream.IsConnected)
if (chatSession.PipeStream?.IsConnected != true)
{
_chatClients.Remove(senderConnectionID);
await hubConnection.SendAsync("DisplayMessage", "Chat disconnected. Please try again.", "Chat disconnected.", "bg-warning", senderConnectionID);
Expand Down Expand Up @@ -142,7 +142,7 @@ private async Task ReadFromStream(NamedPipeClientStream clientPipe, string sende
if (!string.IsNullOrWhiteSpace(messageJson))
{
var chatMessage = JsonSerializer.Deserialize<ChatMessage>(messageJson);
await hubConnection.SendAsync("Chat", chatMessage.Message, false, senderConnectionID);
await hubConnection.SendAsync("Chat", $"{chatMessage?.Message}", false, senderConnectionID);
}
}
await hubConnection.SendAsync("Chat", string.Empty, true, senderConnectionID);
Expand Down
Loading

0 comments on commit ac6487c

Please sign in to comment.