Fixed more threading issues in PowerShell cmdlets to ensure WriteObject and WriteError are only called from the main thread

This commit is contained in:
GraceSolutions
2025-04-15 12:53:47 -04:00
parent 68fcec516e
commit 29b83fbf16
6 changed files with 216 additions and 156 deletions
@@ -33,28 +33,35 @@ namespace PSOPNSenseAPI.Cmdlets
/// <summary>
/// Processes the cmdlet
/// </summary>
protected override void ProcessRecord()
protected override void ProcessRecordInternal()
{
try
{
var dnsService = new DNSService(ApiClient, Logger);
var dnsService = new DNSService(ApiClient, Logger);
if (ParameterSetName == "ByUuid")
{
var task = Task.Run(async () => await dnsService.GetDNSForwardingHostAsync(Uuid));
var result = task.GetAwaiter().GetResult();
WriteObject(result.Host);
}
else
{
var task = Task.Run(async () => await dnsService.GetDNSForwardingHostsAsync());
var result = task.GetAwaiter().GetResult();
WriteObject(result.Rows, true);
}
}
catch (Exception ex)
if (ParameterSetName == "ByUuid")
{
HandleException(ex);
// Use our safe execution method
var result = ExecuteAsyncTask(() => dnsService.GetDNSForwardingHostAsync(Uuid));
// Only continue if no exception occurred
if (ProcessingException != null || result == null)
{
return;
}
WriteObject(result.Host);
}
else
{
// Use our safe execution method
var result = ExecuteAsyncTask(() => dnsService.GetDNSForwardingHostsAsync());
// Only continue if no exception occurred
if (ProcessingException != null || result == null)
{
return;
}
WriteObject(result.Rows, true);
}
}
}
@@ -33,28 +33,35 @@ namespace PSOPNSenseAPI.Cmdlets
/// <summary>
/// Processes the cmdlet
/// </summary>
protected override void ProcessRecord()
protected override void ProcessRecordInternal()
{
try
{
var dnsService = new DNSService(ApiClient, Logger);
var dnsService = new DNSService(ApiClient, Logger);
if (ParameterSetName == "ByUuid")
{
var task = Task.Run(async () => await dnsService.GetDNSOverrideAsync(Uuid));
var result = task.GetAwaiter().GetResult();
WriteObject(result.Host);
}
else
{
var task = Task.Run(async () => await dnsService.GetDNSOverridesAsync());
var result = task.GetAwaiter().GetResult();
WriteObject(result.Rows, true);
}
}
catch (Exception ex)
if (ParameterSetName == "ByUuid")
{
HandleException(ex);
// Use our safe execution method
var result = ExecuteAsyncTask(() => dnsService.GetDNSOverrideAsync(Uuid));
// Only continue if no exception occurred
if (ProcessingException != null || result == null)
{
return;
}
WriteObject(result.Host);
}
else
{
// Use our safe execution method
var result = ExecuteAsyncTask(() => dnsService.GetDNSOverridesAsync());
// Only continue if no exception occurred
if (ProcessingException != null || result == null)
{
return;
}
WriteObject(result.Rows, true);
}
}
}
@@ -55,57 +55,84 @@ namespace PSOPNSenseAPI.Cmdlets
/// <summary>
/// Processes the cmdlet
/// </summary>
protected override void ProcessRecord()
protected override void ProcessRecordInternal()
{
try
var firmwareService = new FirmwareService(ApiClient, Logger);
switch (ParameterSetName)
{
var firmwareService = new FirmwareService(ApiClient, Logger);
case "Changelog":
// Use our safe execution method
var changelogResult = ExecuteAsyncTask(() => firmwareService.GetChangelogAsync());
switch (ParameterSetName)
{
case "Changelog":
var changelogTask = Task.Run(async () => await firmwareService.GetChangelogAsync());
var changelogResult = changelogTask.GetAwaiter().GetResult();
WriteObject(changelogResult.Changelog);
break;
// Only continue if no exception occurred
if (ProcessingException != null || changelogResult == null)
{
return;
}
case "Audit":
var auditTask = Task.Run(async () => await firmwareService.GetAuditAsync());
var auditResult = auditTask.GetAwaiter().GetResult();
WriteObject(auditResult.Audit, true);
break;
WriteObject(changelogResult.Changelog);
break;
case "Health":
var healthTask = Task.Run(async () => await firmwareService.GetHealthAsync());
var healthResult = healthTask.GetAwaiter().GetResult();
WriteObject(healthResult.Health);
break;
case "Audit":
// Use our safe execution method
var auditResult = ExecuteAsyncTask(() => firmwareService.GetAuditAsync());
case "Check":
var checkTask = Task.Run(async () => await firmwareService.CheckForUpdatesAsync());
var checkResult = checkTask.GetAwaiter().GetResult();
WriteObject($"Check for updates: {checkResult.Status}");
break;
// Only continue if no exception occurred
if (ProcessingException != null || auditResult == null)
{
return;
}
default:
var statusTask = Task.Run(async () => await firmwareService.GetStatusAsync());
var statusResult = statusTask.GetAwaiter().GetResult();
WriteObject(auditResult.Audit, true);
break;
var firmware = new PSObject();
firmware.Properties.Add(new PSNoteProperty("Status", statusResult.Status));
firmware.Properties.Add(new PSNoteProperty("Connection", statusResult.Connection));
firmware.Properties.Add(new PSNoteProperty("DownloadSize", statusResult.DownloadSize));
firmware.Properties.Add(new PSNoteProperty("LastCheck", statusResult.LastCheck));
firmware.Properties.Add(new PSNoteProperty("UpgradeMessage", statusResult.UpgradeMessage));
firmware.Properties.Add(new PSNoteProperty("Updates", statusResult.Updates));
WriteObject(firmware);
break;
}
}
catch (Exception ex)
{
HandleException(ex);
case "Health":
// Use our safe execution method
var healthResult = ExecuteAsyncTask(() => firmwareService.GetHealthAsync());
// Only continue if no exception occurred
if (ProcessingException != null || healthResult == null)
{
return;
}
WriteObject(healthResult.Health);
break;
case "Check":
// Use our safe execution method
var checkResult = ExecuteAsyncTask(() => firmwareService.CheckForUpdatesAsync());
// Only continue if no exception occurred
if (ProcessingException != null || checkResult == null)
{
return;
}
WriteObject($"Check for updates: {checkResult.Status}");
break;
default:
// Use our safe execution method
var statusResult = ExecuteAsyncTask(() => firmwareService.GetStatusAsync());
// Only continue if no exception occurred
if (ProcessingException != null || statusResult == null)
{
return;
}
var firmware = new PSObject();
firmware.Properties.Add(new PSNoteProperty("Status", statusResult.Status));
firmware.Properties.Add(new PSNoteProperty("Connection", statusResult.Connection));
firmware.Properties.Add(new PSNoteProperty("DownloadSize", statusResult.DownloadSize));
firmware.Properties.Add(new PSNoteProperty("LastCheck", statusResult.LastCheck));
firmware.Properties.Add(new PSNoteProperty("UpgradeMessage", statusResult.UpgradeMessage));
firmware.Properties.Add(new PSNoteProperty("Updates", statusResult.Updates));
WriteObject(firmware);
break;
}
}
}
@@ -39,69 +39,81 @@ namespace PSOPNSenseAPI.Cmdlets
/// <summary>
/// Processes the cmdlet
/// </summary>
protected override void ProcessRecord()
protected override void ProcessRecordInternal()
{
try
{
var gatewayService = new GatewayService(ApiClient, Logger);
var gatewayService = new GatewayService(ApiClient, Logger);
if (ParameterSetName == "ByUuid")
if (ParameterSetName == "ByUuid")
{
// Use our safe execution method
var result = ExecuteAsyncTask(() => gatewayService.GetGatewayAsync(Uuid));
// Only continue if no exception occurred
if (ProcessingException != null || result == null)
{
var task = Task.Run(async () => await gatewayService.GetGatewayAsync(Uuid));
var result = task.GetAwaiter().GetResult();
WriteObject(result.Gateway);
return;
}
WriteObject(result.Gateway);
}
else
{
// Use our safe execution method
var result = ExecuteAsyncTask(() => gatewayService.GetGatewaysAsync());
// Only continue if no exception occurred
if (ProcessingException != null || result == null)
{
return;
}
if (IncludeStatus.IsPresent)
{
// Use our safe execution method
var statusResult = ExecuteAsyncTask(() => gatewayService.GetGatewayStatusAsync());
// Only continue if no exception occurred
if (ProcessingException != null || statusResult == null)
{
return;
}
foreach (var gateway in result.Rows)
{
var gatewayWithStatus = new PSObject();
gatewayWithStatus.Properties.Add(new PSNoteProperty("Uuid", gateway.Uuid));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Name", gateway.Name));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Interface", gateway.Interface));
gatewayWithStatus.Properties.Add(new PSNoteProperty("IpAddress", gateway.IpAddress));
gatewayWithStatus.Properties.Add(new PSNoteProperty("MonitorIp", gateway.MonitorIp));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Description", gateway.Description));
gatewayWithStatus.Properties.Add(new PSNoteProperty("IsDefault", gateway.IsDefault == "1"));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Disabled", gateway.Disabled == "1"));
if (statusResult.Items.ContainsKey(gateway.Name))
{
var status = statusResult.Items[gateway.Name];
gatewayWithStatus.Properties.Add(new PSNoteProperty("Status", status.Status));
gatewayWithStatus.Properties.Add(new PSNoteProperty("RTT", status.RTT));
gatewayWithStatus.Properties.Add(new PSNoteProperty("StdDev", status.StdDev));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Loss", status.Loss));
}
else
{
gatewayWithStatus.Properties.Add(new PSNoteProperty("Status", "Unknown"));
gatewayWithStatus.Properties.Add(new PSNoteProperty("RTT", "N/A"));
gatewayWithStatus.Properties.Add(new PSNoteProperty("StdDev", "N/A"));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Loss", "N/A"));
}
WriteObject(gatewayWithStatus);
}
}
else
{
var task = Task.Run(async () => await gatewayService.GetGatewaysAsync());
var result = task.GetAwaiter().GetResult();
if (IncludeStatus.IsPresent)
{
var statusTask = Task.Run(async () => await gatewayService.GetGatewayStatusAsync());
var statusResult = statusTask.GetAwaiter().GetResult();
foreach (var gateway in result.Rows)
{
var gatewayWithStatus = new PSObject();
gatewayWithStatus.Properties.Add(new PSNoteProperty("Uuid", gateway.Uuid));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Name", gateway.Name));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Interface", gateway.Interface));
gatewayWithStatus.Properties.Add(new PSNoteProperty("IpAddress", gateway.IpAddress));
gatewayWithStatus.Properties.Add(new PSNoteProperty("MonitorIp", gateway.MonitorIp));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Description", gateway.Description));
gatewayWithStatus.Properties.Add(new PSNoteProperty("IsDefault", gateway.IsDefault == "1"));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Disabled", gateway.Disabled == "1"));
if (statusResult.Items.ContainsKey(gateway.Name))
{
var status = statusResult.Items[gateway.Name];
gatewayWithStatus.Properties.Add(new PSNoteProperty("Status", status.Status));
gatewayWithStatus.Properties.Add(new PSNoteProperty("RTT", status.RTT));
gatewayWithStatus.Properties.Add(new PSNoteProperty("StdDev", status.StdDev));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Loss", status.Loss));
}
else
{
gatewayWithStatus.Properties.Add(new PSNoteProperty("Status", "Unknown"));
gatewayWithStatus.Properties.Add(new PSNoteProperty("RTT", "N/A"));
gatewayWithStatus.Properties.Add(new PSNoteProperty("StdDev", "N/A"));
gatewayWithStatus.Properties.Add(new PSNoteProperty("Loss", "N/A"));
}
WriteObject(gatewayWithStatus);
}
}
else
{
WriteObject(result.Rows, true);
}
WriteObject(result.Rows, true);
}
}
catch (Exception ex)
{
HandleException(ex);
}
}
}
}
@@ -33,28 +33,35 @@ namespace PSOPNSenseAPI.Cmdlets
/// <summary>
/// Processes the cmdlet
/// </summary>
protected override void ProcessRecord()
protected override void ProcessRecordInternal()
{
try
{
var routeService = new RouteService(ApiClient, Logger);
var routeService = new RouteService(ApiClient, Logger);
if (ParameterSetName == "ByUuid")
{
var task = Task.Run(async () => await routeService.GetRouteAsync(Uuid));
var result = task.GetAwaiter().GetResult();
WriteObject(result.Route);
}
else
{
var task = Task.Run(async () => await routeService.GetRoutesAsync());
var result = task.GetAwaiter().GetResult();
WriteObject(result.Rows, true);
}
}
catch (Exception ex)
if (ParameterSetName == "ByUuid")
{
HandleException(ex);
// Use our safe execution method
var result = ExecuteAsyncTask(() => routeService.GetRouteAsync(Uuid));
// Only continue if no exception occurred
if (ProcessingException != null || result == null)
{
return;
}
WriteObject(result.Route);
}
else
{
// Use our safe execution method
var result = ExecuteAsyncTask(() => routeService.GetRoutesAsync());
// Only continue if no exception occurred
if (ProcessingException != null || result == null)
{
return;
}
WriteObject(result.Rows, true);
}
}
}
+1 -1
View File
@@ -3,7 +3,7 @@
RootModule = 'lib\PSOPNSenseAPI.dll'
# Version number of this module.
ModuleVersion = '2025.04.15.1249'
ModuleVersion = '2025.04.15.1253'
# Supported PSEditions
CompatiblePSEditions = @('Desktop', 'Core')