net8, language features, bugfixes
This commit is contained in:
parent
1591618c2c
commit
ce99053a10
353 changed files with 3245 additions and 3944 deletions
|
|
@ -39,6 +39,8 @@ Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Insight.Remote.Shared", "sr
|
|||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Insight.Remote.Windows", "src\Remote\Insight.Remote.Windows\Insight.Remote.Windows.csproj", "{AF313B47-3079-407F-91D1-9989C1E1AF2A}"
|
||||
EndProject
|
||||
Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Insight.Infrastructure.Web", "src\Core\Insight.Infrastructure.Web\Insight.Infrastructure.Web.csproj", "{39B81A0D-A88C-44D3-9624-1A19C78A4310}"
|
||||
EndProject
|
||||
Global
|
||||
GlobalSection(SolutionConfigurationPlatforms) = preSolution
|
||||
Debug|Any CPU = Debug|Any CPU
|
||||
|
|
@ -85,6 +87,10 @@ Global
|
|||
{AF313B47-3079-407F-91D1-9989C1E1AF2A}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{AF313B47-3079-407F-91D1-9989C1E1AF2A}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{AF313B47-3079-407F-91D1-9989C1E1AF2A}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
{39B81A0D-A88C-44D3-9624-1A19C78A4310}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
|
||||
{39B81A0D-A88C-44D3-9624-1A19C78A4310}.Debug|Any CPU.Build.0 = Debug|Any CPU
|
||||
{39B81A0D-A88C-44D3-9624-1A19C78A4310}.Release|Any CPU.ActiveCfg = Release|Any CPU
|
||||
{39B81A0D-A88C-44D3-9624-1A19C78A4310}.Release|Any CPU.Build.0 = Release|Any CPU
|
||||
EndGlobalSection
|
||||
GlobalSection(SolutionProperties) = preSolution
|
||||
HideSolutionNode = FALSE
|
||||
|
|
@ -100,6 +106,7 @@ Global
|
|||
{2A391CA2-F96B-4DB7-80AA-0668A5141640} = {140F73DD-29D3-4C44-809B-5B470880AA0D}
|
||||
{5C4697BD-BC97-484F-9DB1-CA87E2BEAA4B} = {D4D7BF4A-B2E3-470A-A14C-FC658FF7461D}
|
||||
{AF313B47-3079-407F-91D1-9989C1E1AF2A} = {D4D7BF4A-B2E3-470A-A14C-FC658FF7461D}
|
||||
{39B81A0D-A88C-44D3-9624-1A19C78A4310} = {88B03853-2215-4E52-8986-0E76602E5F21}
|
||||
EndGlobalSection
|
||||
GlobalSection(ExtensibilityGlobals) = postSolution
|
||||
SolutionGuid = {F376A326-7590-4E7E-AB9B-76CED8527AB0}
|
||||
|
|
|
|||
|
|
@ -2,17 +2,24 @@
|
|||
|
||||
<PropertyGroup>
|
||||
<OutputType>Exe</OutputType>
|
||||
<TargetFramework>net7.0</TargetFramework>
|
||||
<TargetFramework>net8.0</TargetFramework>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<RootNamespace>Insight.Agent</RootNamespace>
|
||||
<Product>Insight</Product>
|
||||
<AssemblyName>agent</AssemblyName>
|
||||
<AssemblyVersion>2023.12.14.0</AssemblyVersion>
|
||||
<Nullable>enable</Nullable>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<SatelliteResourceLanguages>none</SatelliteResourceLanguages>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<!--WMI / System.Management-->
|
||||
<RuntimeHostConfigurationOption Include="System.Runtime.Loader.UseRidGraph" Value="true" />
|
||||
</ItemGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
|
||||
<DebugType>none</DebugType>
|
||||
<DebugType>none</DebugType>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|AnyCPU'">
|
||||
|
|
@ -20,14 +27,14 @@
|
|||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="7.0.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.Systemd" Version="7.0.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="7.0.1" />
|
||||
<PackageReference Include="Microsoft.Extensions.Configuration.Json" Version="8.0.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.Systemd" Version="8.0.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="8.0.0" />
|
||||
<PackageReference Include="Microsoft.PowerShell.SDK" Version="7.3.10" />
|
||||
<PackageReference Include="Serilog.Extensions.Logging.File" Version="3.0.0" />
|
||||
<PackageReference Include="System.Management" Version="7.0.2" />
|
||||
<PackageReference Include="System.ServiceProcess.ServiceController" Version="7.0.1" />
|
||||
<PackageReference Include="Vaitr.Snmp" Version="2023.3.3" />
|
||||
<PackageReference Include="System.Management" Version="8.0.0" />
|
||||
<PackageReference Include="System.ServiceProcess.ServiceController" Version="8.0.0" />
|
||||
<PackageReference Include="Vaitr.Snmp" Version="2023.12.15.1" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
|
|
|
|||
|
|
@ -5,14 +5,10 @@ using Vaitr.Network;
|
|||
|
||||
namespace Insight.Agent.Network;
|
||||
|
||||
public class AgentSession : TcpSession<IMessage>
|
||||
public class AgentSession(IEnumerable<IMessageHandler<AgentSession>> handlers, ISerializer<IMessage> serializer, ILogger<AgentSession> logger)
|
||||
: TcpSession<IMessage>(serializer, logger)
|
||||
{
|
||||
private readonly IEnumerable<IMessageHandler<AgentSession>> _handlers;
|
||||
|
||||
public AgentSession(IEnumerable<IMessageHandler<AgentSession>> handlers, ISerializer<IMessage> serializer, ILogger<AgentSession> logger) : base(serializer, logger)
|
||||
{
|
||||
_handlers = handlers;
|
||||
}
|
||||
private readonly IEnumerable<IMessageHandler<AgentSession>> _handlers = handlers;
|
||||
|
||||
protected override ValueTask OnConnectedAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -2,20 +2,12 @@
|
|||
using Insight.Domain.Interfaces;
|
||||
using Insight.Domain.Network;
|
||||
using Insight.Domain.Network.Agent.Messages;
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
||||
namespace Insight.Agent.Network.Handlers;
|
||||
|
||||
public class CustomHandler : IMessageHandler<AgentSession>
|
||||
public class CustomHandler(ScriptService scriptService) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly ScriptService _scriptService;
|
||||
private readonly ILogger<CustomHandler> _logger;
|
||||
|
||||
public CustomHandler(ScriptService scriptService, ILogger<CustomHandler> logger)
|
||||
{
|
||||
_scriptService = scriptService;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly ScriptService _scriptService = scriptService;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -29,6 +21,7 @@ public class CustomHandler : IMessageHandler<AgentSession>
|
|||
|
||||
private async ValueTask OnRequestAsync(AgentSession sender, Request request, CancellationToken cancellationToken)
|
||||
{
|
||||
if (request.RequestData is null) return;
|
||||
var result = await _scriptService.QueryAsync(request.RequestData);
|
||||
|
||||
await sender.SendAsync(new Response(request)
|
||||
|
|
|
|||
|
|
@ -59,7 +59,7 @@ public class DriveHandler : IMessageHandler<AgentSession>
|
|||
drive.InterfaceType = @object.GetValue<string>(properties, "interfacetype")?.Trim();
|
||||
drive.FirmwareRevision = @object.GetValue<string>(properties, "firmwarerevision")?.Trim();
|
||||
drive.PNPDeviceID = @object.GetValue<string>(properties, "pnpdeviceid")?.Trim();
|
||||
drive.Volumes = new List<Volume>();
|
||||
drive.Volumes = [];
|
||||
|
||||
var diskpartition = @object.GetRelated("win32_diskpartition");
|
||||
using (diskpartition)
|
||||
|
|
@ -155,7 +155,7 @@ public class DriveHandler : IMessageHandler<AgentSession>
|
|||
{
|
||||
using (collection2)
|
||||
{
|
||||
foreach (ManagementObject @object2 in collection2)
|
||||
foreach (ManagementObject @object2 in collection2.Cast<ManagementObject>())
|
||||
{
|
||||
var properties2 = @object2.GetPropertyHashes();
|
||||
|
||||
|
|
|
|||
|
|
@ -19,7 +19,7 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
case InventoryRequest:
|
||||
{
|
||||
var result = new Collection<Interface>();
|
||||
result.AddRange(GetInterfaces());
|
||||
if (GetInterfaces() is List<Interface> interfaces) result.AddRange(interfaces);
|
||||
|
||||
await sender.SendAsync(result, cancellationToken);
|
||||
break;
|
||||
|
|
@ -27,10 +27,10 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
}
|
||||
}
|
||||
|
||||
private static List<Interface> GetInterfaces()
|
||||
private static List<Interface>? GetInterfaces()
|
||||
{
|
||||
if (NetworkInterface.GetIsNetworkAvailable() is false) return null;
|
||||
if (NetworkInterface.GetAllNetworkInterfaces().Any() is false) return null;
|
||||
if (NetworkInterface.GetAllNetworkInterfaces().Length == 0) return null;
|
||||
|
||||
var interfaces = new List<Interface>();
|
||||
|
||||
|
|
@ -99,7 +99,7 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
|
||||
using (collection)
|
||||
{
|
||||
foreach (ManagementObject @object in collection)
|
||||
foreach (ManagementObject @object in collection.Cast<ManagementObject>())
|
||||
{
|
||||
var properties = @object.GetPropertyHashes();
|
||||
|
||||
|
|
@ -185,7 +185,7 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
{
|
||||
var addresses = new List<Unicast>();
|
||||
|
||||
if (unicastCollection.Any() is false) return addresses;
|
||||
if (unicastCollection.Count == 0) return addresses;
|
||||
|
||||
foreach (var unicast in unicastCollection)
|
||||
{
|
||||
|
|
@ -210,7 +210,7 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
{
|
||||
var addresses = new List<IPAddress2>();
|
||||
|
||||
if (addressCollection.Any() is false) return addresses;
|
||||
if (addressCollection.Count == 0) return addresses;
|
||||
|
||||
foreach (var address in addressCollection)
|
||||
{
|
||||
|
|
@ -224,7 +224,7 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
{
|
||||
var addresses = new List<IPAddress2>();
|
||||
|
||||
if (addressCollection.Any() is false) return addresses;
|
||||
if (addressCollection.Count == 0) return addresses;
|
||||
|
||||
foreach (var address in addressCollection)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -14,12 +14,12 @@ public class MainboardHandler : IMessageHandler<AgentSession>
|
|||
switch (message)
|
||||
{
|
||||
case InventoryRequest:
|
||||
await sender.SendAsync(GetMainboard(), cancellationToken);
|
||||
if (GetMainboard() is Mainboard mainboard) await sender.SendAsync(mainboard, cancellationToken);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
private static Mainboard GetMainboard()
|
||||
private static Mainboard? GetMainboard()
|
||||
{
|
||||
using var searcher = new ManagementObjectSearcher
|
||||
{
|
||||
|
|
|
|||
|
|
@ -41,7 +41,7 @@ public class OperationSystemHandler : IMessageHandler<AgentSession>
|
|||
|
||||
using (collection)
|
||||
{
|
||||
foreach (ManagementObject @object in collection)
|
||||
foreach (ManagementObject @object in collection.Cast<ManagementObject>())
|
||||
{
|
||||
var properties = @object.GetPropertyHashes();
|
||||
|
||||
|
|
@ -51,7 +51,8 @@ public class OperationSystemHandler : IMessageHandler<AgentSession>
|
|||
|
||||
if (@object.TryGetValue<string>(properties, "osarchitecture", out var architecture))
|
||||
{
|
||||
if (architecture is not null && architecture.ToLower().Contains("64")) os.Architecture = Architecture.X64;
|
||||
if (architecture is not null && architecture.Contains("64", StringComparison.CurrentCultureIgnoreCase))
|
||||
os.Architecture = Architecture.X64;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
|
|||
|
|
@ -2,20 +2,12 @@
|
|||
using Insight.Domain.Interfaces;
|
||||
using Insight.Domain.Network;
|
||||
using Insight.Domain.Network.Agent.Messages;
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
||||
namespace Insight.Agent.Network.Handlers;
|
||||
|
||||
public class ProxyHandler : IMessageHandler<AgentSession>
|
||||
public class ProxyHandler(ScriptService scriptService) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly ScriptService _scriptService;
|
||||
private readonly ILogger<ProxyHandler> _logger;
|
||||
|
||||
public ProxyHandler(ScriptService scriptService, ILogger<ProxyHandler> logger)
|
||||
{
|
||||
_scriptService = scriptService;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly ScriptService _scriptService = scriptService;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -29,6 +21,7 @@ public class ProxyHandler : IMessageHandler<AgentSession>
|
|||
|
||||
private async ValueTask OnProxyRequestAsync(AgentSession sender, Proxy<Request> proxyRequest, CancellationToken cancellationToken)
|
||||
{
|
||||
if (proxyRequest.Message?.RequestData is null) return;
|
||||
var result = await _scriptService.QueryAsync(proxyRequest.Message.RequestData);
|
||||
|
||||
await sender.SendAsync(new Proxy<Response>()
|
||||
|
|
|
|||
|
|
@ -30,7 +30,7 @@ public class ServiceHandler : IMessageHandler<AgentSession>
|
|||
var services = new List<Service>();
|
||||
|
||||
var serviceControllers = ServiceController.GetServices()?.OrderBy(s => s.DisplayName)?.ToList();
|
||||
if (serviceControllers is null || serviceControllers.Any() is false) throw new InvalidOperationException("SERVICE Collection NULL");
|
||||
if (serviceControllers is null || serviceControllers.Count == 0) throw new InvalidOperationException("SERVICE Collection NULL");
|
||||
|
||||
foreach (var sc in serviceControllers)
|
||||
{
|
||||
|
|
@ -102,7 +102,7 @@ public class ServiceHandler : IMessageHandler<AgentSession>
|
|||
}
|
||||
}
|
||||
|
||||
if (services2.Any() is false) return services;
|
||||
if (services2.Count == 0) return services;
|
||||
|
||||
foreach (var svc in services)
|
||||
{
|
||||
|
|
@ -117,6 +117,6 @@ public class ServiceHandler : IMessageHandler<AgentSession>
|
|||
svc.Delay = map.Delay;
|
||||
}
|
||||
|
||||
return services.OrderBy(x => x.Name).ToList();
|
||||
return [.. services.OrderBy(x => x.Name)];
|
||||
}
|
||||
}
|
||||
|
|
@ -48,7 +48,7 @@ public class SessionHandler : IMessageHandler<AgentSession>
|
|||
//public const int WTS_CURRENT_SESSION = -1;
|
||||
|
||||
[DllImport("wtsapi32.dll")]
|
||||
static extern int WTSEnumerateSessions(
|
||||
private static extern int WTSEnumerateSessions(
|
||||
nint pServer,
|
||||
[MarshalAs(UnmanagedType.U4)] int iReserved,
|
||||
[MarshalAs(UnmanagedType.U4)] int iVersion,
|
||||
|
|
@ -64,7 +64,7 @@ public class SessionHandler : IMessageHandler<AgentSession>
|
|||
out uint iBytesReturned);
|
||||
|
||||
[DllImport("wtsapi32.dll")]
|
||||
static extern void WTSFreeMemory(
|
||||
private static extern void WTSFreeMemory(
|
||||
nint pMemory);
|
||||
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
|
|
|
|||
|
|
@ -89,121 +89,6 @@ public class StoragePoolHandler : IMessageHandler<AgentSession>
|
|||
return pools;
|
||||
}
|
||||
|
||||
private static List<PhysicalDisk> GetPhysicalDisks()
|
||||
{
|
||||
using var searcher = new ManagementObjectSearcher
|
||||
{
|
||||
Scope = new ManagementScope(@"root\microsoft\windows\storage"),
|
||||
Query = new ObjectQuery("select objectid, uniqueid, name, friendlyname from msft_physicaldisk")
|
||||
};
|
||||
|
||||
if (searcher.TryGet(out var collection) is false)
|
||||
{
|
||||
searcher.Query = new ObjectQuery("select * from msft_physicaldisk");
|
||||
|
||||
if (searcher.TryGet(out collection) is false) throw new InvalidOperationException("WMI Collection NULL");
|
||||
}
|
||||
|
||||
var disks = new List<PhysicalDisk>();
|
||||
|
||||
using (collection)
|
||||
{
|
||||
foreach (ManagementObject @object in collection.Cast<ManagementObject>())
|
||||
{
|
||||
var disk = new PhysicalDisk();
|
||||
|
||||
var properties = @object.GetPropertyHashes();
|
||||
|
||||
disk.UniqueId = @object.GetValue<string>(properties, "uniqueid")?.Trim();
|
||||
disk.FriendlyName = @object.GetValue<string>(properties, "friendlyname")?.Trim();
|
||||
disk.Manufacturer = @object.GetValue<string>(properties, "manufacturer")?.Trim();
|
||||
disk.Model = @object.GetValue<string>(properties, "model")?.Trim();
|
||||
disk.MediaType = @object.GetValue<ushort>(properties, "mediatype");
|
||||
disk.BusType = @object.GetValue<ushort>(properties, "bustype");
|
||||
|
||||
if (@object.TryGetValue<ushort[]>(properties, "operationalstatus", out var operationals) && operationals is not null)
|
||||
{
|
||||
disk.States = operationals.Select(p => (PhysicalDisk.OperationalState)p).ToList();
|
||||
}
|
||||
|
||||
disk.Health = (PhysicalDisk.HealthState)@object.GetValue<ushort>(properties, "healthstatus");
|
||||
|
||||
if (@object.TryGetValue<ushort[]>(properties, "supportedusages", out var supportedusages) && supportedusages is not null)
|
||||
{
|
||||
disk.SupportedUsages = supportedusages.Select(p => (SupportedUsagesEnum)p).ToList();
|
||||
}
|
||||
|
||||
disk.Usage = @object.GetValue<ushort>(properties, "usage");
|
||||
disk.PhysicalLocation = @object.GetValue<string>(properties, "physicallocation")?.Trim();
|
||||
disk.SerialNumber = @object.GetValue<string>(properties, "serialnumber")?.Trim();
|
||||
disk.FirmwareVersion = @object.GetValue<string>(properties, "firmwareversion")?.Trim();
|
||||
disk.Size = @object.GetValue<ulong>(properties, "size");
|
||||
disk.AllocatedSize = @object.GetValue<ulong>(properties, "allocatedsize");
|
||||
disk.LogicalSectorSize = @object.GetValue<ulong>(properties, "logicalsectorsize");
|
||||
disk.PhysicalSectorSize = @object.GetValue<ulong>(properties, "physicalsectorsize");
|
||||
disk.VirtualDiskFootprint = @object.GetValue<ulong>(properties, "virtualdiskfootprint");
|
||||
|
||||
disks.Add(disk);
|
||||
}
|
||||
}
|
||||
|
||||
return disks;
|
||||
}
|
||||
|
||||
private static List<VirtualDisk> GetVirtualDisks()
|
||||
{
|
||||
using var searcher = new ManagementObjectSearcher
|
||||
{
|
||||
Scope = new ManagementScope(@"root\microsoft\windows\storage"),
|
||||
Query = new ObjectQuery("select objectid, uniqueid, name, friendlyname, access, provisioningtype, physicaldiskredundancy, resiliencysettingname, isdeduplicationenabled, issnapshot, operationalstatus, healthstatus, size, allocatedsize, footprintonpool, readcachesize, writecachesize from msft_virtualdisk")
|
||||
};
|
||||
|
||||
if (searcher.TryGet(out var collection) is false)
|
||||
{
|
||||
searcher.Query = new ObjectQuery("select * from msft_virtualdisk");
|
||||
|
||||
if (searcher.TryGet(out collection) is false) throw new InvalidOperationException("WMI Collection NULL");
|
||||
}
|
||||
|
||||
var disks = new List<VirtualDisk>();
|
||||
|
||||
using (collection)
|
||||
{
|
||||
foreach (ManagementObject @object in collection.Cast<ManagementObject>())
|
||||
{
|
||||
var disk = new VirtualDisk();
|
||||
|
||||
var properties = @object.GetPropertyHashes();
|
||||
|
||||
disk.UniqueId = @object.GetValue<string>(properties, "uniqueid")?.Trim();
|
||||
disk.Name = @object.GetValue<string>(properties, "name")?.Trim();
|
||||
disk.FriendlyName = @object.GetValue<string>(properties, "friendlyname")?.Trim();
|
||||
disk.AccessType = (AccessTypeEnum)@object.GetValue<ushort>(properties, "access");
|
||||
disk.ProvisioningType = (ProvisioningTypeEnum)@object.GetValue<ushort>(properties, "provisioningtype");
|
||||
disk.PhysicalDiskRedundancy = @object.GetValue<ushort>(properties, "physicaldiskredundancy");
|
||||
disk.ResiliencySettingName = @object.GetValue<string>(properties, "resiliencysettingname")?.Trim();
|
||||
disk.Deduplication = @object.GetValue<bool>(properties, "isdeduplicationenabled");
|
||||
disk.IsSnapshot = @object.GetValue<bool>(properties, "issnapshot");
|
||||
|
||||
if (@object.TryGetValue<ushort[]>(properties, "operationalstatus", out var operationals) && operationals is not null)
|
||||
{
|
||||
disk.States = operationals.Select(p => (VirtualDisk.OperationalState)p).ToList();
|
||||
}
|
||||
|
||||
disk.Health = (VirtualDisk.HealthState)@object.GetValue<ushort>(properties, "healthstatus");
|
||||
disk.Size = @object.GetValue<ulong>(properties, "size");
|
||||
disk.AllocatedSize = @object.GetValue<ulong>(properties, "allocatedsize");
|
||||
disk.FootprintOnPool = @object.GetValue<ulong>(properties, "footprintonpool");
|
||||
disk.ReadCacheSize = @object.GetValue<ulong>(properties, "readcachesize");
|
||||
disk.WriteCacheSize = @object.GetValue<ulong>(properties, "writecachesize");
|
||||
|
||||
disks.Add(disk);
|
||||
}
|
||||
}
|
||||
|
||||
return disks;
|
||||
}
|
||||
|
||||
private static List<PhysicalDisk> QueryPhysicalDisksByStoragePool(string storagePoolObjectId)
|
||||
{
|
||||
using var searcher = new ManagementObjectSearcher
|
||||
|
|
@ -218,7 +103,7 @@ public class StoragePoolHandler : IMessageHandler<AgentSession>
|
|||
|
||||
using (collection)
|
||||
{
|
||||
foreach (ManagementObject @object in collection)
|
||||
foreach (ManagementObject @object in collection.Cast<ManagementObject>())
|
||||
{
|
||||
var disk = new PhysicalDisk();
|
||||
|
||||
|
|
@ -275,7 +160,7 @@ public class StoragePoolHandler : IMessageHandler<AgentSession>
|
|||
|
||||
using (collection)
|
||||
{
|
||||
foreach (ManagementObject @object in collection)
|
||||
foreach (ManagementObject @object in collection.Cast<ManagementObject>())
|
||||
{
|
||||
var disk = new VirtualDisk();
|
||||
|
||||
|
|
|
|||
|
|
@ -87,7 +87,6 @@ public class SystemInfoHandler : IMessageHandler<AgentSession>
|
|||
|
||||
private static string GetWindowsProductKeyFromDigitalProductId(byte[] digitalProductId, DigitalProductIdVersion digitalProductIdVersion)
|
||||
{
|
||||
|
||||
var productKey = digitalProductIdVersion == DigitalProductIdVersion.Windows8AndUp
|
||||
? DecodeProductKeyWin8AndUp(digitalProductId)
|
||||
: DecodeProductKey(digitalProductId);
|
||||
|
|
@ -124,7 +123,7 @@ public class SystemInfoHandler : IMessageHandler<AgentSession>
|
|||
var digitMapIndex = 0;
|
||||
for (var j = decodeStringLength - 1; j >= 0; j--)
|
||||
{
|
||||
var byteValue = digitMapIndex << 8 | (byte)hexPid[j];
|
||||
var byteValue = digitMapIndex << 8 | (byte)hexPid[j]!;
|
||||
hexPid[j] = (byte)(byteValue / 24);
|
||||
digitMapIndex = byteValue % 24;
|
||||
decodedChars[i] = digits[digitMapIndex];
|
||||
|
|
@ -148,17 +147,17 @@ public class SystemInfoHandler : IMessageHandler<AgentSession>
|
|||
var current = 0;
|
||||
for (var j = 14; j >= 0; j--)
|
||||
{
|
||||
current = current * 256;
|
||||
current *= 256;
|
||||
current = digitalProductId[j + keyOffset] + current;
|
||||
digitalProductId[j + keyOffset] = (byte)(current / 24);
|
||||
current = current % 24;
|
||||
current %= 24;
|
||||
last = current;
|
||||
}
|
||||
key = digits[current] + key;
|
||||
}
|
||||
|
||||
var keypart1 = key.Substring(1, last);
|
||||
var keypart2 = key.Substring(last + 1, key.Length - (last + 1));
|
||||
var keypart2 = key[(last + 1)..];
|
||||
key = keypart1 + "N" + keypart2;
|
||||
|
||||
for (var i = 5; i < key.Length; i += 6)
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@ using UpdateCollection = Insight.Domain.Network.Agent.Messages.UpdateCollection;
|
|||
namespace Insight.Agent.Network.Handlers;
|
||||
|
||||
[SupportedOSPlatform("windows")]
|
||||
public class UpdateHandler : IMessageHandler<AgentSession>
|
||||
public partial class UpdateHandler : IMessageHandler<AgentSession>
|
||||
{
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -60,7 +60,7 @@ public class UpdateHandler : IMessageHandler<AgentSession>
|
|||
|
||||
try
|
||||
{
|
||||
var rx = new Regex(@"KB(\d+)");
|
||||
var rx = KnowledgeBaseRegex();
|
||||
update.Hotfix = rx.Match(wupdate.Title).Value;
|
||||
}
|
||||
catch (Exception)
|
||||
|
|
@ -125,4 +125,7 @@ public class UpdateHandler : IMessageHandler<AgentSession>
|
|||
|
||||
return updates;
|
||||
}
|
||||
|
||||
[GeneratedRegex(@"KB(\d+)")]
|
||||
private static partial Regex KnowledgeBaseRegex();
|
||||
}
|
||||
|
|
@ -32,7 +32,7 @@ public class UserHandler : IMessageHandler<AgentSession>
|
|||
|
||||
foreach (var u in users)
|
||||
{
|
||||
u.Groups = new List<Group>();
|
||||
u.Groups = [];
|
||||
|
||||
foreach (var ug in usergrouping.Where(ug => ug.UserDomain == u.Domain && ug.UserName == u.Name))
|
||||
{
|
||||
|
|
@ -67,7 +67,7 @@ public class UserHandler : IMessageHandler<AgentSession>
|
|||
|
||||
using (collection)
|
||||
{
|
||||
foreach (ManagementObject @object in collection)
|
||||
foreach (ManagementObject @object in collection.Cast<ManagementObject>())
|
||||
{
|
||||
var group = new Group();
|
||||
|
||||
|
|
@ -83,7 +83,7 @@ public class UserHandler : IMessageHandler<AgentSession>
|
|||
}
|
||||
}
|
||||
|
||||
return groups.OrderBy(x => x.Name)?.ToList();
|
||||
return [.. groups.OrderBy(x => x.Name)];
|
||||
}
|
||||
|
||||
private static List<User> QueryUsers()
|
||||
|
|
@ -105,7 +105,7 @@ public class UserHandler : IMessageHandler<AgentSession>
|
|||
|
||||
using (collection)
|
||||
{
|
||||
foreach (ManagementObject @object in collection)
|
||||
foreach (ManagementObject @object in collection.Cast<ManagementObject>())
|
||||
{
|
||||
var user = new User();
|
||||
|
||||
|
|
@ -150,7 +150,7 @@ public class UserHandler : IMessageHandler<AgentSession>
|
|||
|
||||
using (collection)
|
||||
{
|
||||
foreach (ManagementObject @object in collection)
|
||||
foreach (ManagementObject @object in collection.Cast<ManagementObject>())
|
||||
{
|
||||
var usergroup = new UserGroupMap();
|
||||
|
||||
|
|
|
|||
|
|
@ -341,7 +341,7 @@ public class VirtualMaschineHandler : IMessageHandler<AgentSession>
|
|||
{
|
||||
conf.ParentId = parentGuid.ToString();
|
||||
|
||||
parentConfig.Childs ??= new List<VirtualMaschineConfiguration>();
|
||||
parentConfig.Childs ??= [];
|
||||
parentConfig.Childs.Add(conf);
|
||||
}
|
||||
else
|
||||
|
|
|
|||
|
|
@ -9,6 +9,7 @@ using Microsoft.Extensions.Configuration;
|
|||
using Microsoft.Extensions.DependencyInjection;
|
||||
using Microsoft.Extensions.Hosting;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using System.Runtime.Versioning;
|
||||
using Vaitr.Network;
|
||||
using Vaitr.Network.Hosting;
|
||||
|
||||
|
|
@ -66,29 +67,13 @@ internal class Program
|
|||
options.UseSerializer<AgentSession, IMessage, MemPackSerializer<IMessage>>();
|
||||
});
|
||||
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, CustomHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, ProxyHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, AuthenticationHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, DriveHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, InterfaceHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, MainboardHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, MemoryHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, OperationSystemHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, PrinterHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, ProcessorHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, ServiceHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, SessionHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, SoftwareHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, StoragePoolHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, SystemInfoHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, UpdateHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, UserHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, VideocardHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, VirtualMaschineHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, ProxyHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, CustomHandler>();
|
||||
|
||||
if (OperatingSystem.IsWindows()) ServiceCollectionExtensions.InjectWindowsHandler(services);
|
||||
|
||||
// GLOBAL DEPENDENCIES
|
||||
//services.AddSingleton<Bus>();
|
||||
services.AddTransient(provider => new HttpClient(new HttpClientHandler
|
||||
{
|
||||
ClientCertificateOptions = ClientCertificateOption.Manual,
|
||||
|
|
@ -100,3 +85,29 @@ internal class Program
|
|||
await host.RunAsync().ConfigureAwait(false);
|
||||
}
|
||||
}
|
||||
|
||||
internal static class ServiceCollectionExtensions
|
||||
{
|
||||
[SupportedOSPlatform("windows")]
|
||||
internal static IServiceCollection InjectWindowsHandler(this IServiceCollection services)
|
||||
{
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, DriveHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, InterfaceHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, MainboardHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, MemoryHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, OperationSystemHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, PrinterHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, ProcessorHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, ServiceHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, SessionHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, SoftwareHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, StoragePoolHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, SystemInfoHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, UpdateHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, UserHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, VideocardHandler>();
|
||||
services.AddSingleton<IMessageHandler<AgentSession>, VirtualMaschineHandler>();
|
||||
|
||||
return services;
|
||||
}
|
||||
}
|
||||
|
|
@ -5,12 +5,7 @@ using System.Runtime.Versioning;
|
|||
namespace Insight.Agent.Services;
|
||||
|
||||
[SupportedOSPlatform("linux")]
|
||||
public partial class CollectorService
|
||||
public partial class CollectorService(ILogger<CollectorService>? logger = null)
|
||||
{
|
||||
public ILogger<CollectorService> Logger { get; }
|
||||
|
||||
public CollectorService(ILogger<CollectorService>? logger = null)
|
||||
{
|
||||
Logger = logger ?? NullLogger<CollectorService>.Instance;
|
||||
}
|
||||
public ILogger<CollectorService> Logger { get; } = logger ?? NullLogger<CollectorService>.Instance;
|
||||
}
|
||||
|
|
@ -4,12 +4,14 @@ namespace Insight.Agent.Services;
|
|||
|
||||
public static class Configurator
|
||||
{
|
||||
private static readonly JsonSerializerOptions _serializerOptions = new() { PropertyNameCaseInsensitive = true, WriteIndented = true };
|
||||
|
||||
public static async ValueTask<TConfig> ReadAsync<TConfig>(string file, CancellationToken cancellationToken = default)
|
||||
where TConfig : class
|
||||
{
|
||||
var json = await File.ReadAllTextAsync(file, cancellationToken);
|
||||
|
||||
if (JsonSerializer.Deserialize<TConfig>(json, new JsonSerializerOptions { PropertyNameCaseInsensitive = true, WriteIndented = true }) is not TConfig config)
|
||||
if (JsonSerializer.Deserialize<TConfig>(json, _serializerOptions) is not TConfig config)
|
||||
{
|
||||
throw new InvalidDataException($"Failed to deserialize ({file})");
|
||||
}
|
||||
|
|
@ -31,7 +33,7 @@ public static class Configurator
|
|||
{
|
||||
var json = await File.ReadAllTextAsync(file, cancellationToken);
|
||||
|
||||
if (JsonSerializer.Deserialize<IDictionary<string, object>>(json, new JsonSerializerOptions { PropertyNameCaseInsensitive = true, WriteIndented = true }) is not IDictionary<string, object> config)
|
||||
if (JsonSerializer.Deserialize<IDictionary<string, object>>(json, _serializerOptions) is not IDictionary<string, object> config)
|
||||
{
|
||||
throw new InvalidDataException($"Failed to deserialize ({file})");
|
||||
}
|
||||
|
|
@ -89,7 +91,7 @@ public static class Configurator
|
|||
|
||||
private static async ValueTask WriteToFileAsync<TData>(TData data, string file, CancellationToken cancellationToken)
|
||||
{
|
||||
var json = JsonSerializer.Serialize(data, new JsonSerializerOptions { WriteIndented = true });
|
||||
var json = JsonSerializer.Serialize(data, _serializerOptions);
|
||||
|
||||
await File.WriteAllTextAsync(file, json, cancellationToken);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -163,7 +163,7 @@ internal class EventService : BackgroundService
|
|||
};
|
||||
}
|
||||
|
||||
_queue.Writer.WriteAsync(@event, default);
|
||||
_ = _queue.Writer.WriteAsync(@event, default);
|
||||
}
|
||||
catch (Exception) { } // app crash
|
||||
}
|
||||
|
|
|
|||
|
|
@ -4,17 +4,14 @@ using System.Management.Automation.Runspaces;
|
|||
|
||||
namespace Insight.Agent.Services;
|
||||
|
||||
public class ScriptService
|
||||
public class ScriptService(ILogger<ScriptService> logger)
|
||||
{
|
||||
private readonly ILogger<ScriptService> _logger;
|
||||
|
||||
public ScriptService(ILogger<ScriptService> logger)
|
||||
{
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly ILogger<ScriptService> _logger = logger;
|
||||
|
||||
public async Task<QueryResult> QueryAsync(string query)
|
||||
{
|
||||
_logger.LogDebug("QueryAsync ({query})", query);
|
||||
|
||||
var result = new QueryResult();
|
||||
var errors = new List<string>();
|
||||
|
||||
|
|
|
|||
|
|
@ -12,19 +12,12 @@ using System.Text.Json;
|
|||
|
||||
namespace Insight.Agent.Services;
|
||||
|
||||
internal class UpdateService : BackgroundService
|
||||
internal class UpdateService(HttpClient httpClient, IConfiguration configuration, ILogger<UpdateService> logger) : BackgroundService
|
||||
{
|
||||
private readonly Uri _uri;
|
||||
private readonly Uri _uri = configuration.GetValue<Uri?>("api") ?? throw new Exception($"api value not set (appsettings)");
|
||||
|
||||
private readonly HttpClient _httpClient;
|
||||
private readonly ILogger<UpdateService> _logger;
|
||||
|
||||
public UpdateService(HttpClient httpClient, IConfiguration configuration, ILogger<UpdateService> logger)
|
||||
{
|
||||
_httpClient = httpClient;
|
||||
_uri = configuration.GetValue<Uri?>("api") ?? throw new Exception($"api value not set (appsettings)");
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly HttpClient _httpClient = httpClient;
|
||||
private readonly ILogger<UpdateService> _logger = logger;
|
||||
|
||||
protected override async Task ExecuteAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
|
|
@ -42,7 +35,7 @@ internal class UpdateService : BackgroundService
|
|||
_logger.LogInformation("Update Result: {result}", result?.Success);
|
||||
if (result?.UpdateErrors is not null)
|
||||
{
|
||||
_logger.LogError("Update Errors: {errors}", string.Concat(result?.UpdateErrors));
|
||||
_logger.LogError("Update Errors: {errors}", string.Concat(result.UpdateErrors));
|
||||
}
|
||||
}
|
||||
catch (OperationCanceledException) { }
|
||||
|
|
@ -198,7 +191,7 @@ internal class UpdateService : BackgroundService
|
|||
await File.WriteAllBytesAsync(updateFile.FullName, await update.Content.ReadAsByteArrayAsync(cancellationToken), cancellationToken);
|
||||
|
||||
// extract update archive from temp to app dir (overwrite)
|
||||
ZipFile.ExtractToDirectory(updateFile.FullName, bin.Directory?.FullName, true);
|
||||
ZipFile.ExtractToDirectory(updateFile.FullName, bin.Directory!.FullName, true);
|
||||
|
||||
// delete temp folder
|
||||
if (temp.Exists) temp.Delete(true);
|
||||
|
|
@ -229,7 +222,7 @@ internal class UpdateService : BackgroundService
|
|||
|
||||
var matched = System.Diagnostics.Process.GetProcessesByName(bin.FullName);
|
||||
|
||||
if (matched is null || matched.Any() is false) return false;
|
||||
if (matched is null || matched.Length == 0) return false;
|
||||
|
||||
if (matched.Any(p =>
|
||||
p.MainModule is not null &&
|
||||
|
|
@ -262,7 +255,7 @@ internal class UpdateService : BackgroundService
|
|||
|
||||
var matched = System.Diagnostics.Process.GetProcessesByName(bin.FullName);
|
||||
|
||||
if (matched is null || matched.Any() is false) return true;
|
||||
if (matched is null || matched.Length == 0) return true;
|
||||
|
||||
foreach (var procsInfo in matched.Where(p =>
|
||||
p.MainModule is not null &&
|
||||
|
|
@ -312,7 +305,7 @@ internal class UpdateService : BackgroundService
|
|||
await File.WriteAllBytesAsync(updateFile.FullName, await update.Content.ReadAsByteArrayAsync(cancellationToken), cancellationToken);
|
||||
|
||||
// extract update archive from temp to app dir (overwrite)
|
||||
ZipFile.ExtractToDirectory(updateFile.FullName, bin.Directory?.FullName, true);
|
||||
ZipFile.ExtractToDirectory(updateFile.FullName, bin.Directory!.FullName, true);
|
||||
|
||||
// delete temp folder
|
||||
if (temp.Exists) temp.Delete(true);
|
||||
|
|
@ -353,7 +346,7 @@ internal class UpdateService : BackgroundService
|
|||
public bool ApiAvailable { get; set; } = false;
|
||||
public bool UpdateAvailable { get; set; } = false;
|
||||
public bool Success { get; set; } = false;
|
||||
public List<string> ApiErrors { get; } = new();
|
||||
public List<string> UpdateErrors { get; } = new();
|
||||
public List<string> ApiErrors { get; } = [];
|
||||
public List<string> UpdateErrors { get; } = [];
|
||||
}
|
||||
}
|
||||
|
|
@ -21,10 +21,9 @@ public partial class CollectorService
|
|||
output = stream.ReadToEnd();
|
||||
|
||||
// clean output
|
||||
var clean = Regex
|
||||
.Replace(output
|
||||
var clean = CleanRegex().Replace(output
|
||||
.Trim()
|
||||
.Replace("\t", " "), @"[ ]{2,}", " ");
|
||||
.Replace("\t", " "), " ");
|
||||
|
||||
var elements = clean.Split(Array.Empty<char>(), StringSplitOptions.RemoveEmptyEntries);
|
||||
|
||||
|
|
@ -36,13 +35,12 @@ public partial class CollectorService
|
|||
|
||||
// linebreak list conversion
|
||||
var lines = new List<string>(output
|
||||
.Split(new string[] { "\n", "\r\n" }, StringSplitOptions.RemoveEmptyEntries))
|
||||
.Split(separator, StringSplitOptions.RemoveEmptyEntries))
|
||||
.Select(l =>
|
||||
{
|
||||
return Regex
|
||||
.Replace(l
|
||||
return CleanRegex().Replace(l
|
||||
.Trim()
|
||||
.Replace("\t", " "), @"[ ]{2,}", " ");
|
||||
.Replace("\t", " "), " ");
|
||||
})
|
||||
.ToList();
|
||||
|
||||
|
|
@ -62,13 +60,12 @@ public partial class CollectorService
|
|||
|
||||
// linebreak list conversion
|
||||
lines = new List<string>(output
|
||||
.Split(new string[] { "\n", "\r\n" }, StringSplitOptions.RemoveEmptyEntries))
|
||||
.Split(separator, StringSplitOptions.RemoveEmptyEntries))
|
||||
.Select(l =>
|
||||
{
|
||||
return Regex
|
||||
.Replace(l
|
||||
return CleanRegex().Replace(l
|
||||
.Trim()
|
||||
.Replace("\t", " "), @"[ ]{2,}", " ");
|
||||
.Replace("\t", " "), " ");
|
||||
})
|
||||
.ToList();
|
||||
|
||||
|
|
@ -102,4 +99,9 @@ public partial class CollectorService
|
|||
|
||||
return os;
|
||||
}
|
||||
|
||||
private static readonly string[] separator = ["\n", "\r\n"];
|
||||
|
||||
[GeneratedRegex(@"[ ]{2,}")]
|
||||
private static partial Regex CleanRegex();
|
||||
}
|
||||
|
|
@ -17,11 +17,11 @@ public partial class CollectorService
|
|||
var output = "w".Bash();
|
||||
|
||||
// linebreak list conversion
|
||||
var lines = output.Split(new string[] { "\n", "\r\n" }, StringSplitOptions.RemoveEmptyEntries).ToList();
|
||||
var lines = output.Split(separatorArray, StringSplitOptions.RemoveEmptyEntries).ToList();
|
||||
|
||||
lines = lines.Select(l =>
|
||||
{
|
||||
return Regex.Replace(l.Trim().Replace("\t", " "), @"[ ]{2,}", " ");
|
||||
return CleanOutputRegex().Replace(l.Trim().Replace("\t", " "), " ");
|
||||
}).ToList();
|
||||
|
||||
// cleaning
|
||||
|
|
@ -46,4 +46,9 @@ public partial class CollectorService
|
|||
|
||||
return sessions;
|
||||
}
|
||||
|
||||
private static readonly string[] separatorArray = ["\n", "\r\n"];
|
||||
|
||||
[GeneratedRegex(@"[ ]{2,}")]
|
||||
private static partial Regex CleanOutputRegex();
|
||||
}
|
||||
|
|
@ -1,31 +1,29 @@
|
|||
using Insight.Api.Models;
|
||||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Models;
|
||||
using Insight.Infrastructure.Services;
|
||||
using Insight.Infrastructure.Web;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using MongoDB.Driver;
|
||||
|
||||
namespace Insight.Api.Controllers;
|
||||
|
||||
[ApiController, Route("api/accounts")]
|
||||
public class AccountController : ControllerBase
|
||||
public class AccountController(IdentityService identityService, IServiceScopeFactory scopeFactory) : ControllerBase
|
||||
{
|
||||
private readonly IdentityService _identityService;
|
||||
private readonly AccountService _accountService;
|
||||
private readonly ILogger<AccountController> _logger;
|
||||
|
||||
public AccountController(IdentityService identityService, AccountService accountService, ILogger<AccountController> logger)
|
||||
{
|
||||
_identityService = identityService;
|
||||
_accountService = accountService;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly IdentityService _identityService = identityService;
|
||||
private readonly IServiceScopeFactory _scopeFactory = scopeFactory;
|
||||
|
||||
[HttpGet, Authorize]
|
||||
public async Task<IActionResult> Get([FromQuery] PagedDataRequest request, CancellationToken cancellationToken)
|
||||
{
|
||||
using var scope = _scopeFactory.CreateScope();
|
||||
var collection = scope.ServiceProvider.GetRequiredService<IMongoDatabase>().User();
|
||||
|
||||
try
|
||||
{
|
||||
var result = await _accountService.GetAsync(
|
||||
var result = await collection.GetPagedAsync(
|
||||
offset: request.Offset,
|
||||
limit: request.Limit,
|
||||
request: Request,
|
||||
|
|
|
|||
|
|
@ -1,28 +1,26 @@
|
|||
using Insight.Infrastructure.Models;
|
||||
using Insight.Infrastructure.Services;
|
||||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Models;
|
||||
using Insight.Infrastructure.Web;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using MongoDB.Driver;
|
||||
|
||||
namespace Insight.Api.Controllers;
|
||||
|
||||
[ApiController, Route("api/agents")]
|
||||
public class AgentController : ControllerBase
|
||||
public class AgentController(IServiceScopeFactory scopeFactory) : ControllerBase
|
||||
{
|
||||
private readonly AgentService _agentService;
|
||||
private readonly ILogger<AgentController> _logger;
|
||||
|
||||
public AgentController(AgentService agentService, ILogger<AgentController> logger)
|
||||
{
|
||||
_agentService = agentService;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly IServiceScopeFactory _scopeFactory = scopeFactory;
|
||||
|
||||
[HttpGet, Authorize]
|
||||
public async Task<IActionResult> Get([FromQuery] PagedDataRequest request, CancellationToken cancellationToken)
|
||||
{
|
||||
using var scope = _scopeFactory.CreateScope();
|
||||
var collection = scope.ServiceProvider.GetRequiredService<IMongoDatabase>().Agent();
|
||||
|
||||
try
|
||||
{
|
||||
var result = await _agentService.GetAsync(
|
||||
var result = await collection.GetPagedAsync(
|
||||
offset: request.Offset,
|
||||
limit: request.Limit,
|
||||
request: Request,
|
||||
|
|
|
|||
|
|
@ -1,28 +1,26 @@
|
|||
using Insight.Infrastructure.Models;
|
||||
using Insight.Infrastructure.Services;
|
||||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Models;
|
||||
using Insight.Infrastructure.Web;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using MongoDB.Driver;
|
||||
|
||||
namespace Insight.Api.Controllers;
|
||||
|
||||
[ApiController, Route("api/customers")]
|
||||
public class CustomerController : ControllerBase
|
||||
public class CustomerController(IServiceScopeFactory scopeFactory) : ControllerBase
|
||||
{
|
||||
private readonly CustomerService _customerService;
|
||||
private readonly ILogger<CustomerController> _logger;
|
||||
|
||||
public CustomerController(CustomerService customerService, ILogger<CustomerController> logger)
|
||||
{
|
||||
_customerService = customerService;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly IServiceScopeFactory _scopeFactory = scopeFactory;
|
||||
|
||||
[HttpGet, Authorize]
|
||||
public async Task<IActionResult> Get([FromQuery] PagedDataRequest request, CancellationToken cancellationToken)
|
||||
{
|
||||
using var scope = _scopeFactory.CreateScope();
|
||||
var collection = scope.ServiceProvider.GetRequiredService<IMongoDatabase>().Customer();
|
||||
|
||||
try
|
||||
{
|
||||
var result = await _customerService.GetAsync(
|
||||
var result = await collection.GetPagedAsync(
|
||||
offset: request.Offset,
|
||||
limit: request.Limit,
|
||||
request: Request,
|
||||
|
|
|
|||
|
|
@ -1,28 +1,26 @@
|
|||
using Insight.Infrastructure.Models;
|
||||
using Insight.Infrastructure.Services;
|
||||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Models;
|
||||
using Insight.Infrastructure.Web;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using MongoDB.Driver;
|
||||
|
||||
namespace Insight.Api.Controllers;
|
||||
|
||||
[ApiController, Route("api/hosts")]
|
||||
public class HostController : ControllerBase
|
||||
public class HostController(IServiceScopeFactory scopeFactory) : ControllerBase
|
||||
{
|
||||
private readonly HostService _hostService;
|
||||
private readonly ILogger<HostController> _logger;
|
||||
|
||||
public HostController(HostService hostService, ILogger<HostController> logger)
|
||||
{
|
||||
_hostService = hostService;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly IServiceScopeFactory _scopeFactory = scopeFactory;
|
||||
|
||||
[HttpGet, Authorize]
|
||||
public async Task<IActionResult> Get([FromQuery] PagedDataRequest request, CancellationToken cancellationToken)
|
||||
{
|
||||
using var scope = _scopeFactory.CreateScope();
|
||||
var collection = scope.ServiceProvider.GetRequiredService<IMongoDatabase>().Host();
|
||||
|
||||
try
|
||||
{
|
||||
var result = await _hostService.GetAsync(
|
||||
var result = await collection.GetPagedAsync(
|
||||
offset: request.Offset,
|
||||
limit: request.Limit,
|
||||
request: Request,
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Models;
|
||||
using Insight.Infrastructure.Services;
|
||||
using Insight.Infrastructure.Web;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using MongoDB.Bson;
|
||||
|
|
@ -11,20 +11,16 @@ using System.Text.RegularExpressions;
|
|||
namespace Insight.Api.Controllers;
|
||||
|
||||
[ApiController, Route("api/inventory")]
|
||||
public class InventoryController : ControllerBase
|
||||
public class InventoryController(IServiceScopeFactory scopeFactory) : ControllerBase
|
||||
{
|
||||
private readonly InventoryService _inventoryService;
|
||||
private readonly ILogger<InventoryController> _logger;
|
||||
|
||||
public InventoryController(InventoryService inventoryService, ILogger<InventoryController> logger)
|
||||
{
|
||||
_inventoryService = inventoryService;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly IServiceScopeFactory _scopeFactory = scopeFactory;
|
||||
|
||||
[HttpGet, Authorize]
|
||||
public async Task<IActionResult> Get([FromQuery] HostApplicationEntity request, [FromQuery] PagedDataRequest meta, CancellationToken cancellationToken)
|
||||
{
|
||||
using var scope = _scopeFactory.CreateScope();
|
||||
var collection = scope.ServiceProvider.GetRequiredService<IMongoDatabase>().HostApplication();
|
||||
|
||||
try
|
||||
{
|
||||
var filter = Builders<HostApplicationEntity>.Filter.Empty;
|
||||
|
|
@ -38,7 +34,7 @@ public class InventoryController : ControllerBase
|
|||
if (request.Name is not null)
|
||||
filter &= Builders<HostApplicationEntity>.Filter.Regex(p => p.Name, new BsonRegularExpression(new Regex(request.Name, RegexOptions.IgnoreCase)));
|
||||
|
||||
var result = await _inventoryService.GetAsync(
|
||||
var result = await collection.GetPagedAsync(
|
||||
filter: filter,
|
||||
offset: meta.Offset,
|
||||
limit: meta.Limit,
|
||||
|
|
|
|||
|
|
@ -3,14 +3,9 @@
|
|||
namespace Insight.Server.Controllers;
|
||||
|
||||
[ApiController, Route("api/setup")]
|
||||
public class SetupController : ControllerBase
|
||||
public class SetupController(ILogger<SetupController> logger) : ControllerBase
|
||||
{
|
||||
private readonly ILogger<SetupController> _logger;
|
||||
|
||||
public SetupController(ILogger<SetupController> logger)
|
||||
{
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly ILogger<SetupController> _logger = logger;
|
||||
|
||||
[HttpGet("windows")]
|
||||
public async Task<IActionResult> GetAsync(CancellationToken cancellationToken)
|
||||
|
|
|
|||
|
|
@ -6,14 +6,9 @@ using Microsoft.AspNetCore.Mvc;
|
|||
namespace Insight.Api.Controllers;
|
||||
|
||||
[ApiController, Route("api/token", Order = 0)]
|
||||
public class TokenController : ControllerBase
|
||||
public class TokenController(TokenService tokenService) : ControllerBase
|
||||
{
|
||||
private readonly TokenService _tokenService;
|
||||
|
||||
public TokenController(TokenService tokenService)
|
||||
{
|
||||
_tokenService = tokenService;
|
||||
}
|
||||
private readonly TokenService _tokenService = tokenService;
|
||||
|
||||
/// <remarks>
|
||||
/// Access Token Request
|
||||
|
|
@ -21,6 +16,9 @@ public class TokenController : ControllerBase
|
|||
[HttpPost, AllowAnonymous]
|
||||
public async Task<IActionResult> Authentication([FromBody] TokenRequest request)
|
||||
{
|
||||
if (request.Username is null) return BadRequest("username is null");
|
||||
if (request.Password is null) return BadRequest("password is null");
|
||||
|
||||
try
|
||||
{
|
||||
var result = await _tokenService.GetAsync(request.Username, request.Password, request.Code, HttpContext.Connection.RemoteIpAddress).ConfigureAwait(false);
|
||||
|
|
|
|||
|
|
@ -5,14 +5,9 @@ using Microsoft.AspNetCore.Mvc;
|
|||
namespace Insight.Server.Controllers;
|
||||
|
||||
[ApiController, Route("api/update")]
|
||||
public class UpdateController : ControllerBase
|
||||
public class UpdateController(ILogger<UpdateController> logger) : ControllerBase
|
||||
{
|
||||
private readonly ILogger<UpdateController> _logger;
|
||||
|
||||
public UpdateController(ILogger<UpdateController> logger)
|
||||
{
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly ILogger<UpdateController> _logger = logger;
|
||||
|
||||
[HttpGet("updater/windows")]
|
||||
public IActionResult UpdaterWindows()
|
||||
|
|
@ -35,7 +30,7 @@ public class UpdateController : ControllerBase
|
|||
|
||||
var versions = updateDir.GetFiles("*.zip", SearchOption.TopDirectoryOnly);
|
||||
|
||||
if (versions is null || versions.Any() is false) return NotFound();
|
||||
if (versions is null || versions.Length == 0) return NotFound();
|
||||
|
||||
var latest = versions.OrderBy(x => x.Name).FirstOrDefault();
|
||||
|
||||
|
|
@ -73,7 +68,7 @@ public class UpdateController : ControllerBase
|
|||
|
||||
var versions = updateDir.GetFiles("*.zip", SearchOption.TopDirectoryOnly);
|
||||
|
||||
if (versions is null || versions.Any() is false) return NotFound();
|
||||
if (versions is null || versions.Length == 0) return NotFound();
|
||||
|
||||
var latest = versions.OrderBy(x => x.Name).FirstOrDefault();
|
||||
|
||||
|
|
|
|||
|
|
@ -6,7 +6,7 @@ namespace Insight.Api.Hosting;
|
|||
|
||||
public static class ServiceExtensions
|
||||
{
|
||||
internal static IServiceCollection AddSwaggerServices(this IServiceCollection services, IConfiguration configuration)
|
||||
internal static IServiceCollection AddSwaggerServices(this IServiceCollection services)
|
||||
{
|
||||
services.AddEndpointsApiExplorer();
|
||||
services.AddSwaggerGen(options =>
|
||||
|
|
|
|||
|
|
@ -1,42 +1,35 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk.Web">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net7.0</TargetFramework>
|
||||
<Product>Insight</Product>
|
||||
<AssemblyName>api</AssemblyName>
|
||||
<AssemblyVersion>2023.12.14.0</AssemblyVersion>
|
||||
<RootNamespace>Insight.Api</RootNamespace>
|
||||
<Nullable>enable</Nullable>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<UserSecretsId>4ae1d3bf-869e-4963-8a19-35634507d3b3</UserSecretsId>
|
||||
|
||||
<PublishAot>false</PublishAot>
|
||||
<PublishTrimmed>false</PublishTrimmed>
|
||||
<!--<ServerGarbageCollection>false</ServerGarbageCollection>
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net8.0</TargetFramework>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<Product>Insight</Product>
|
||||
<AssemblyName>api</AssemblyName>
|
||||
<AssemblyVersion>2023.12.15.0</AssemblyVersion>
|
||||
<RootNamespace>Insight.Api</RootNamespace>
|
||||
<Nullable>enable</Nullable>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<UserSecretsId>4ae1d3bf-869e-4963-8a19-35634507d3b3</UserSecretsId>
|
||||
<PublishAot>false</PublishAot>
|
||||
<PublishTrimmed>false</PublishTrimmed>
|
||||
<!--<ServerGarbageCollection>false</ServerGarbageCollection>
|
||||
<ConcurrentGarbageCollection>false</ConcurrentGarbageCollection>-->
|
||||
|
||||
<GenerateDocumentationFile>True</GenerateDocumentationFile>
|
||||
<NoWarn>$(NoWarn);1591</NoWarn>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
|
||||
<DebugType>none</DebugType>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|AnyCPU'">
|
||||
<DebugType>none</DebugType>
|
||||
</PropertyGroup>
|
||||
<GenerateDocumentationFile>True</GenerateDocumentationFile>
|
||||
<NoWarn>$(NoWarn);1591</NoWarn>
|
||||
<SatelliteResourceLanguages>none</SatelliteResourceLanguages>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.Systemd" Version="7.0.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="7.0.1" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.OpenApi" Version="7.0.13" />
|
||||
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.5.0" />
|
||||
<PackageReference Include="Serilog.Extensions.Logging.File" Version="3.0.0" />
|
||||
<!--Unix Serilog stuff-->
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.Systemd" Version="8.0.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="8.0.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.OpenApi" Version="8.0.0" />
|
||||
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.5.0" />
|
||||
<PackageReference Include="Serilog.Extensions.Logging.File" Version="3.0.0" />
|
||||
<!--Unix Serilog stuff-->
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\..\Core\Insight.Infrastructure.Web\Insight.Infrastructure.Web.csproj" />
|
||||
<ProjectReference Include="..\..\Core\Insight.Infrastructure\Insight.Infrastructure.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
|
|
|
|||
|
|
@ -40,12 +40,12 @@ internal class Program
|
|||
builder.Services.AddAuthorization();
|
||||
|
||||
// WEBSERVICES
|
||||
builder.Services.AddProxyServices(builder.Configuration);
|
||||
builder.Services.AddRoutingServices(builder.Configuration);
|
||||
builder.Services.AddProxyServices();
|
||||
builder.Services.AddRoutingServices();
|
||||
builder.Services.AddControllers();
|
||||
|
||||
// SWAGGER
|
||||
builder.Services.AddSwaggerServices(builder.Configuration);
|
||||
builder.Services.AddSwaggerServices();
|
||||
|
||||
//builder.Services.AddControllers();
|
||||
//builder.Services.AddEndpointsApiExplorer();
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
using System.Net;
|
||||
using System.Diagnostics;
|
||||
using System.Net;
|
||||
using System.Reflection;
|
||||
|
||||
namespace Insight.Domain.Constants;
|
||||
|
|
@ -7,6 +8,14 @@ public static class Configuration
|
|||
{
|
||||
public static string Hostname => Dns.GetHostEntry("localhost").HostName;
|
||||
public static Version Version => Assembly.GetEntryAssembly()?.GetName().Version ?? throw new ArgumentNullException("Version");
|
||||
public static DirectoryInfo? AppDirectory => string.IsNullOrWhiteSpace(Environment.ProcessPath) ? null : new DirectoryInfo(Environment.ProcessPath).Parent;
|
||||
public static DirectoryInfo? AppDirectory => AppDirectoryHelper();
|
||||
public static string DefaultConfig => Path.Combine(AppDirectory?.FullName ?? string.Empty, "config.json");
|
||||
|
||||
private static DirectoryInfo? AppDirectoryHelper()
|
||||
{
|
||||
using var proc = Process.GetCurrentProcess();
|
||||
|
||||
if (proc?.MainModule?.FileName is null) throw new InvalidOperationException("MainModule not found");
|
||||
return new DirectoryInfo(proc.MainModule.FileName).Parent;
|
||||
}
|
||||
}
|
||||
|
|
@ -2,6 +2,7 @@
|
|||
|
||||
public enum CategoryEnum
|
||||
{
|
||||
None = 0,
|
||||
Network = 1,
|
||||
System = 2,
|
||||
Application = 3,
|
||||
|
|
|
|||
|
|
@ -1,25 +1,25 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net7.0</TargetFramework>
|
||||
<ImplicitUsings>true</ImplicitUsings>
|
||||
<TargetFramework>net8.0</TargetFramework>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<Nullable>enable</Nullable>
|
||||
<RootNamespace>Insight.Domain</RootNamespace>
|
||||
<Product>Insight</Product>
|
||||
<AssemblyVersion>2023.12.14.0</AssemblyVersion>
|
||||
<AssemblyVersion>2023.12.15.0</AssemblyVersion>
|
||||
<SatelliteResourceLanguages>none</SatelliteResourceLanguages>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
|
||||
<!--Ignore MemoryPack Warning-->
|
||||
<NoWarn>9193</NoWarn>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Vaitr.Bus" Version="2023.12.13" />
|
||||
<PackageReference Include="Vaitr.Network" Version="2023.12.14" />
|
||||
<PackageReference Include="System.Text.Json" Version="8.0.0" />
|
||||
<PackageReference Include="Vaitr.Bus" Version="2023.12.15.1" />
|
||||
<PackageReference Include="Vaitr.Network" Version="2023.12.16" />
|
||||
</ItemGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
|
||||
<DebugType>none</DebugType>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|AnyCPU'">
|
||||
<DebugType>none</DebugType>
|
||||
</PropertyGroup>
|
||||
|
||||
</Project>
|
||||
|
|
@ -1,5 +1,4 @@
|
|||
using MessagePack;
|
||||
using System.Diagnostics.CodeAnalysis;
|
||||
using System.Runtime.Serialization;
|
||||
using System.Text.Json.Serialization;
|
||||
|
||||
|
|
@ -31,17 +30,17 @@ public class Result
|
|||
}
|
||||
|
||||
[IgnoreDataMember]
|
||||
public Exception? Exception { get; init; }
|
||||
public Exception? Exception { get; set; }
|
||||
|
||||
[IgnoreDataMember]
|
||||
[MemberNotNullWhen(true, nameof(Exception))]
|
||||
//[MemberNotNullWhen(true, nameof(Exception))]
|
||||
public bool HadException => Exception is not null;
|
||||
|
||||
[DataMember]
|
||||
public bool IsSuccess { get; init; }
|
||||
public bool IsSuccess { get; set; }
|
||||
|
||||
[DataMember]
|
||||
public string Reason { get; init; } = string.Empty;
|
||||
public string Reason { get; set; } = string.Empty;
|
||||
|
||||
|
||||
public static Result Fail(string reason)
|
||||
|
|
@ -130,19 +129,19 @@ public class Result<T>
|
|||
}
|
||||
|
||||
[IgnoreDataMember]
|
||||
public Exception? Exception { get; init; }
|
||||
public Exception? Exception { get; set; }
|
||||
|
||||
[IgnoreDataMember]
|
||||
[MemberNotNullWhen(true, nameof(Exception))]
|
||||
//[MemberNotNullWhen(true, nameof(Exception))]
|
||||
public bool HadException => Exception is not null;
|
||||
|
||||
[DataMember]
|
||||
[MemberNotNullWhen(true, nameof(Value))]
|
||||
public bool IsSuccess { get; init; }
|
||||
//[MemberNotNullWhen(true, nameof(Value))]
|
||||
public bool IsSuccess { get; set; }
|
||||
|
||||
[DataMember]
|
||||
public string Reason { get; init; } = string.Empty;
|
||||
public string Reason { get; set; } = string.Empty;
|
||||
|
||||
[DataMember]
|
||||
public T? Value { get; init; }
|
||||
public T? Value { get; set; }
|
||||
}
|
||||
|
|
|
|||
|
|
@ -27,28 +27,17 @@ public class TokenResponse
|
|||
public string? RefreshToken { get; set; }
|
||||
}
|
||||
|
||||
public class TokenRevokeRequest
|
||||
public class TokenRevokeRequest(string token, string? reason)
|
||||
{
|
||||
[JsonPropertyName("token"), Required]
|
||||
public string? Token { get; set; }
|
||||
public string? Token { get; set; } = token;
|
||||
|
||||
[JsonPropertyName("reason")]
|
||||
public string? Reason { get; set; }
|
||||
|
||||
public TokenRevokeRequest(string token, string? reason)
|
||||
{
|
||||
Token = token;
|
||||
Reason = reason;
|
||||
}
|
||||
public string? Reason { get; set; } = reason;
|
||||
}
|
||||
|
||||
public class TokenRefreshRequest
|
||||
public class TokenRefreshRequest(string token)
|
||||
{
|
||||
[JsonPropertyName("token"), Required]
|
||||
public string? Token { get; set; }
|
||||
|
||||
public TokenRefreshRequest(string token)
|
||||
{
|
||||
Token = token;
|
||||
}
|
||||
public string? Token { get; set; } = token;
|
||||
}
|
||||
|
|
@ -182,6 +182,6 @@ public partial class IPAddress2 : IMessage
|
|||
IsIPv6Multicast = address.IsIPv6Multicast;
|
||||
IsIPv6SiteLocal = address.IsIPv6SiteLocal;
|
||||
IsIPv6Teredo = address.IsIPv6Teredo;
|
||||
IsIPv6UniqueLocal = address.IsIPv6UniqueLocal;
|
||||
//IsIPv6UniqueLocal = address.IsIPv6UniqueLocal;
|
||||
}
|
||||
}
|
||||
|
|
@ -6,10 +6,6 @@ namespace Insight.Domain.Network;
|
|||
[MemoryPackUnion(0, typeof(Agent.Messages.AuthenticationRequest))]
|
||||
[MemoryPackUnion(1, typeof(Agent.Messages.AuthenticationResponse))]
|
||||
[MemoryPackUnion(2, typeof(Agent.Messages.InventoryRequest))]
|
||||
//[MemoryPackUnion(3, typeof(Agent.Messages.ConsoleQueryRequest))]
|
||||
//[MemoryPackUnion(4, typeof(Agent.Messages.ConsoleQueryResponse))]
|
||||
//[MemoryPackUnion(5, typeof(Proxy<Agent.Messages.ConsoleQueryResponse>))]
|
||||
//[MemoryPackUnion(6, typeof(Proxy<Agent.Messages.ConsoleQueryRequest>))]
|
||||
[MemoryPackUnion(7, typeof(Agent.Messages.Event))]
|
||||
[MemoryPackUnion(8, typeof(Agent.Messages.Trap))]
|
||||
[MemoryPackUnion(9, typeof(Agent.Messages.Mainboard))]
|
||||
|
|
|
|||
|
|
@ -4,7 +4,7 @@ using Microsoft.AspNetCore.Http.Extensions;
|
|||
|
||||
namespace Insight.Infrastructure;
|
||||
|
||||
public static class HttpRequestExtensions
|
||||
public static partial class HttpRequestExtensions
|
||||
{
|
||||
public static void AddPagination<TData>(this HttpRequest request, PagedList<TData> pagelist)
|
||||
{
|
||||
|
|
@ -0,0 +1,18 @@
|
|||
using Insight.Infrastructure.Models;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using System.Text.Json;
|
||||
|
||||
namespace Insight.Infrastructure;
|
||||
|
||||
public static partial class HttpResponseExtensions
|
||||
{
|
||||
private static readonly JsonSerializerOptions _options = new()
|
||||
{
|
||||
PropertyNamingPolicy = JsonNamingPolicy.CamelCase
|
||||
};
|
||||
|
||||
public static void AddPagination<TData>(this HttpResponse response, PagedList<TData> pagelist)
|
||||
{
|
||||
response.Headers.Append("X-Pagination", JsonSerializer.Serialize(pagelist.Meta as PagedHeaderData, _options));
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,44 @@
|
|||
using Insight.Infrastructure.Models;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using MongoDB.Bson;
|
||||
using MongoDB.Driver;
|
||||
|
||||
namespace Insight.Infrastructure.Web;
|
||||
|
||||
public static class MongoCollectionExtensions
|
||||
{
|
||||
public static async Task<PagedList<TData>> GetPagedAsync<TData>(
|
||||
this IMongoCollection<TData> collection,
|
||||
HttpRequest request,
|
||||
HttpResponse response,
|
||||
FilterDefinition<TData>? filter = null,
|
||||
SortDefinition<TData>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default)
|
||||
{
|
||||
var result = await Infrastructure.MongoCollectionExtensions.GetPagedAsync(collection, filter, sort, offset, limit, cancellationToken).ConfigureAwait(false);
|
||||
|
||||
request?.AddPagination(result);
|
||||
response?.AddPagination(result);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
public static async Task<PagedList<TResult>> GetPagedAsync<TData, TResult>(
|
||||
this IMongoCollection<TData> collection,
|
||||
HttpRequest request,
|
||||
HttpResponse response,
|
||||
IAggregateFluent<BsonDocument> query,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default)
|
||||
{
|
||||
var result = await Infrastructure.MongoCollectionExtensions.GetPagedAsync<TData, TResult>(collection, query, offset, limit, cancellationToken).ConfigureAwait(false);
|
||||
|
||||
request?.AddPagination(result);
|
||||
response?.AddPagination(result);
|
||||
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,229 @@
|
|||
using AspNetCore.Identity.MongoDbCore.Extensions;
|
||||
using AspNetCore.Identity.MongoDbCore.Infrastructure;
|
||||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Services;
|
||||
using Microsoft.AspNetCore.Authentication.JwtBearer;
|
||||
using Microsoft.AspNetCore.Builder;
|
||||
using Microsoft.AspNetCore.HttpOverrides;
|
||||
using Microsoft.AspNetCore.Identity;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
using Microsoft.Extensions.Primitives;
|
||||
using Microsoft.IdentityModel.Tokens;
|
||||
using Microsoft.Net.Http.Headers;
|
||||
using MongoDB.Bson;
|
||||
using System.Text;
|
||||
|
||||
namespace Insight.Infrastructure;
|
||||
|
||||
public static partial class ServiceExtensions
|
||||
{
|
||||
public static IServiceCollection AddTokenServices(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
var options = new Models.TokenOptions(
|
||||
key: configuration.GetValue<string?>(Appsettings.JwtKey) ?? throw new Exception($"{Appsettings.JwtKey} value not set (appsettings)"),
|
||||
expires: configuration.GetValue<int?>(Appsettings.JwtExp) ?? throw new Exception($"{Appsettings.JwtExp} value not set (appsettings)"),
|
||||
audience: configuration.GetValue<Uri?>(Appsettings.JwtAudience) ?? throw new Exception($"{Appsettings.JwtAudience} value not set (appsettings)"),
|
||||
issuer: configuration.GetValue<Uri?>(Appsettings.JwtIssuer) ?? throw new Exception($"{Appsettings.JwtIssuer} value not set (appsettings)"));
|
||||
|
||||
services.AddSingleton(options);
|
||||
services.AddTransient<TokenService>();
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
public static IServiceCollection AddProxyServices(this IServiceCollection services)
|
||||
{
|
||||
// add before routing
|
||||
services.Configure<ForwardedHeadersOptions>(options =>
|
||||
{
|
||||
options.ForwardedHeaders = ForwardedHeaders.XForwardedFor | ForwardedHeaders.XForwardedProto;
|
||||
});
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
public static IServiceCollection AddRoutingServices(this IServiceCollection services)
|
||||
{
|
||||
// add after proxy
|
||||
services.AddRouting(options =>
|
||||
{
|
||||
options.LowercaseUrls = true;
|
||||
});
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
public static IServiceCollection AddIdentityServices(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
var connectionString = configuration.GetValue<string?>(Appsettings.Database) ?? throw new Exception($"{Appsettings.Database} value not set (appsettings)");
|
||||
|
||||
services.AddIdentity<InsightUser, InsightRole>(options =>
|
||||
{
|
||||
|
||||
})
|
||||
.AddMongoDbStores<InsightUser, InsightRole, ObjectId>(connectionString, Settings.Database)
|
||||
.AddDefaultTokenProviders()
|
||||
.AddSignInManager();
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
public static IServiceCollection AddCustomAuthentication(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
// REWRITE TO COOKIE ONLY FOR WEB
|
||||
|
||||
services.AddAuthentication(options =>
|
||||
{
|
||||
options.DefaultScheme = "Custom";
|
||||
options.DefaultChallengeScheme = "Custom";
|
||||
})
|
||||
.AddCookie("Cookies", options =>
|
||||
{
|
||||
//options.Cookie.Domain = "insight.webmatic.de";
|
||||
options.Cookie.Name = "insight";
|
||||
options.LoginPath = "/account/login";
|
||||
options.LogoutPath = "/account/logout";
|
||||
options.ExpireTimeSpan = TimeSpan.FromHours(1);
|
||||
options.SlidingExpiration = true;
|
||||
|
||||
options.Events.OnRedirectToLogin = options =>
|
||||
{
|
||||
if (options.Request.Path.StartsWithSegments("/api") && options.Response.StatusCode == 200)
|
||||
options.Response.StatusCode = 401;
|
||||
else
|
||||
options.Response.Redirect(options.RedirectUri);
|
||||
|
||||
return Task.CompletedTask;
|
||||
};
|
||||
})
|
||||
.AddJwtBearer("Bearer", options =>
|
||||
{
|
||||
options.RequireHttpsMetadata = false;
|
||||
options.SaveToken = true;
|
||||
|
||||
options.TokenValidationParameters.ValidateActor = false;
|
||||
|
||||
options.TokenValidationParameters.ValidAudience = configuration.GetSection("Jwt:Audience").Value;
|
||||
options.TokenValidationParameters.ValidateAudience = true;
|
||||
|
||||
options.TokenValidationParameters.ValidIssuer = configuration.GetSection("Jwt:Issuer").Value;
|
||||
options.TokenValidationParameters.ValidateIssuer = true;
|
||||
|
||||
options.TokenValidationParameters.IssuerSigningKey = new SymmetricSecurityKey(
|
||||
Encoding.UTF8.GetBytes(configuration.GetSection("Jwt:Key").Value ?? throw new Exception("Configuration for [Jwt:Key] not found"))
|
||||
);
|
||||
|
||||
options.TokenValidationParameters.ValidateIssuerSigningKey = true;
|
||||
options.TokenValidationParameters.ValidateLifetime = true;
|
||||
})
|
||||
.AddPolicyScheme("Custom", "Custom", options =>
|
||||
{
|
||||
options.ForwardDefaultSelector = context =>
|
||||
{
|
||||
if (context.Request.Headers[HeaderNames.Authorization] is StringValues auth && auth.ToString().StartsWith("Bearer "))
|
||||
return "Bearer";
|
||||
else
|
||||
return "Cookies";
|
||||
};
|
||||
});
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
public static IServiceCollection AddBearerAuthentication(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
services.AddAuthentication(options =>
|
||||
{
|
||||
options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
|
||||
options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
|
||||
options.DefaultSignInScheme = JwtBearerDefaults.AuthenticationScheme;
|
||||
})
|
||||
.AddJwtBearer(options =>
|
||||
{
|
||||
options.RequireHttpsMetadata = false;
|
||||
options.SaveToken = true;
|
||||
|
||||
options.TokenValidationParameters.ValidateActor = false;
|
||||
|
||||
options.TokenValidationParameters.ValidAudience = configuration.GetValue<string?>(Appsettings.JwtAudience) ?? throw new Exception($"{Appsettings.JwtAudience} value not set (appsettings)");
|
||||
options.TokenValidationParameters.ValidateAudience = true;
|
||||
|
||||
options.TokenValidationParameters.ValidIssuer = configuration.GetValue<string?>(Appsettings.JwtIssuer) ?? throw new Exception($"{Appsettings.JwtIssuer} value not set (appsettings)");
|
||||
options.TokenValidationParameters.ValidateIssuer = true;
|
||||
|
||||
options.TokenValidationParameters.IssuerSigningKey = new SymmetricSecurityKey(
|
||||
Encoding.UTF8.GetBytes(configuration.GetValue<string?>(Appsettings.JwtKey) ?? throw new Exception($"{Appsettings.JwtKey} value not set (appsettings)"))
|
||||
);
|
||||
|
||||
options.TokenValidationParameters.ValidateIssuerSigningKey = true;
|
||||
options.TokenValidationParameters.ValidateLifetime = true;
|
||||
});
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
//private static IServiceCollection AddIdentityServices2(this IServiceCollection services, IConfiguration configuration)
|
||||
//{
|
||||
// var identityOptions = new MongoDbIdentityConfiguration
|
||||
// {
|
||||
// MongoDbSettings = new MongoDbSettings
|
||||
// {
|
||||
// ConnectionString = configuration.GetSection("ConnectionStrings:Mongo").Value,
|
||||
// DatabaseName = "insight"
|
||||
// },
|
||||
// IdentityOptionsAction = options =>
|
||||
// {
|
||||
// options.User.RequireUniqueEmail = true;
|
||||
// options.User.AllowedUserNameCharacters = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789@.-_";
|
||||
|
||||
// options.Password.RequireDigit = false;
|
||||
// options.Password.RequiredLength = 8;
|
||||
// options.Password.RequireNonAlphanumeric = false;
|
||||
// options.Password.RequireUppercase = false;
|
||||
// options.Password.RequireLowercase = false;
|
||||
|
||||
// options.SignIn.RequireConfirmedAccount = false;
|
||||
// options.SignIn.RequireConfirmedEmail = false;
|
||||
// options.SignIn.RequireConfirmedPhoneNumber = false;
|
||||
|
||||
// options.Lockout.MaxFailedAccessAttempts = 5;
|
||||
// options.Lockout.DefaultLockoutTimeSpan = TimeSpan.FromMinutes(5);
|
||||
// }
|
||||
// };
|
||||
|
||||
// services.ConfigureMongoDbIdentity<InsightUser, InsightRole, ObjectId>(identityOptions)
|
||||
// .AddDefaultTokenProviders()
|
||||
// .AddSignInManager<InsightUser>();
|
||||
|
||||
// return services;
|
||||
//}
|
||||
|
||||
//private static IServiceCollection AddIdentityAuthentication(this IServiceCollection services, IConfiguration configuration)
|
||||
//{
|
||||
// services.AddAuthentication(options =>
|
||||
// {
|
||||
// options.DefaultAuthenticateScheme =
|
||||
// });
|
||||
// cookieBuilder.ApplicationCookie = builder.AddApplicationCookie();
|
||||
// cookieBuilder.ExternalCookie = builder.AddExternalCookie();
|
||||
// cookieBuilder.TwoFactorRememberMeCookie = builder.AddTwoFactorRememberMeCookie();
|
||||
// cookieBuilder.TwoFactorUserIdCookie = builder.AddTwoFactorUserIdCookie();
|
||||
// .AddCookie(options =>
|
||||
// {
|
||||
// options.
|
||||
// };
|
||||
// .AddIdentityCookies();
|
||||
// .AddCookie(options =>
|
||||
// {
|
||||
// // Specify where to redirect un-authenticated users
|
||||
// options.LoginPath = "/account/login";
|
||||
|
||||
// // Specify the name of the auth cookie.
|
||||
// // ASP.NET picks a dumb name by default.
|
||||
// options.Cookie.Name = "insight";
|
||||
// });
|
||||
|
||||
// return services;
|
||||
//}
|
||||
}
|
||||
|
|
@ -0,0 +1,25 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net8.0</TargetFramework>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<Nullable>enable</Nullable>
|
||||
<RootNamespace>Insight.Infrastructure.Web</RootNamespace>
|
||||
<Product>Insight</Product>
|
||||
<AssemblyVersion>2023.12.15.0</AssemblyVersion>
|
||||
<SatelliteResourceLanguages>none</SatelliteResourceLanguages>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.AspNetCore.Http.Extensions" Version="2.2.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Authentication.JwtBearer" Version="8.0.0" />
|
||||
<PackageReference Include="Microsoft.IdentityModel.Tokens" Version="7.0.3" />
|
||||
<PackageReference Include="System.IdentityModel.Tokens.Jwt" Version="7.0.3" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<ProjectReference Include="..\Insight.Infrastructure\Insight.Infrastructure.csproj" />
|
||||
</ItemGroup>
|
||||
|
||||
</Project>
|
||||
|
|
@ -0,0 +1,9 @@
|
|||
namespace Insight.Infrastructure.Models;
|
||||
|
||||
public class TokenOptions(string key, int expires, Uri? audience = null, Uri? issuer = null)
|
||||
{
|
||||
public string Key { get; set; } = key;
|
||||
public int Expires { get; set; } = expires;
|
||||
public Uri? Audience { get; set; } = audience;
|
||||
public Uri? Issuer { get; set; } = issuer;
|
||||
}
|
||||
|
|
@ -10,24 +10,17 @@ using System.Text;
|
|||
|
||||
namespace Insight.Infrastructure.Services;
|
||||
|
||||
public class TokenService
|
||||
public class TokenService(TokenOptions options, IdentityService identityService, IMongoDatabase database)
|
||||
{
|
||||
private readonly TokenOptions _options;
|
||||
private readonly IdentityService _identityService;
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public TokenService(TokenOptions options, IdentityService identityService, IMongoDatabase database)
|
||||
{
|
||||
_options = options;
|
||||
_identityService = identityService;
|
||||
_database = database;
|
||||
}
|
||||
private readonly TokenOptions _options = options;
|
||||
private readonly IdentityService _identityService = identityService;
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async Task<TokenResponse> GetAsync(string email, string password, string? code = null, IPAddress? ipa = null)
|
||||
{
|
||||
var user = await _identityService.LoginAsync(email, password, code).ConfigureAwait(false);
|
||||
|
||||
var accessToken = await CreateAccessTokenAsync(user, ipa).ConfigureAwait(false);
|
||||
var accessToken = await CreateAccessTokenAsync(user).ConfigureAwait(false);
|
||||
var refreshToken = await CreateRefreshTokenAsync(user, ipa).ConfigureAwait(false);
|
||||
|
||||
return new TokenResponse
|
||||
|
|
@ -42,7 +35,7 @@ public class TokenService
|
|||
{
|
||||
if (string.IsNullOrWhiteSpace(refreshToken)) throw new ArgumentNullException(nameof(refreshToken));
|
||||
|
||||
var user = await _database.User().Find(p => p.RefreshTokens.Any(t => t.Token == refreshToken)).FirstOrDefaultAsync();
|
||||
var user = await _database.User().Find(p => p.RefreshTokens != null && p.RefreshTokens.Any(t => t.Token == refreshToken)).FirstOrDefaultAsync();
|
||||
if (user is null || user.RefreshTokens is null) throw new InvalidDataException("Invalid Refresh Token");
|
||||
|
||||
var token = user.RefreshTokens.First(p => p.Token == refreshToken);
|
||||
|
|
@ -73,7 +66,7 @@ public class TokenService
|
|||
var newRefreshToken = await CreateRefreshTokenAsync(user, ipa).ConfigureAwait(false);
|
||||
|
||||
// create access token
|
||||
var accessToken = await CreateAccessTokenAsync(user, ipa).ConfigureAwait(false);
|
||||
var accessToken = await CreateAccessTokenAsync(user).ConfigureAwait(false);
|
||||
|
||||
return new TokenResponse
|
||||
{
|
||||
|
|
@ -87,7 +80,7 @@ public class TokenService
|
|||
{
|
||||
if (string.IsNullOrWhiteSpace(refreshToken)) throw new ArgumentNullException(nameof(refreshToken));
|
||||
|
||||
var user = await _database.User().Find(p => p.RefreshTokens.Any(t => t.Token == refreshToken)).FirstOrDefaultAsync();
|
||||
var user = await _database.User().Find(p => p.RefreshTokens != null && p.RefreshTokens.Any(t => t.Token == refreshToken)).FirstOrDefaultAsync();
|
||||
if (user is null || user.RefreshTokens is null) throw new InvalidDataException("Invalid Refresh Token");
|
||||
|
||||
var token = user.RefreshTokens.First(p => p.Token == refreshToken);
|
||||
|
|
@ -102,7 +95,7 @@ public class TokenService
|
|||
token.ReasonRevoked = reason;
|
||||
}
|
||||
|
||||
private async Task<(string, int)> CreateAccessTokenAsync(InsightUser user, IPAddress? ipa = null)
|
||||
private async Task<(string, int)> CreateAccessTokenAsync(InsightUser user)
|
||||
{
|
||||
var claims = await _identityService.GetClaimsAsync(user).ConfigureAwait(false);
|
||||
|
||||
|
|
@ -1,16 +0,0 @@
|
|||
using Insight.Infrastructure.Models;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using System.Text.Json;
|
||||
|
||||
namespace Insight.Infrastructure;
|
||||
|
||||
public static class HttpResponseExtensions
|
||||
{
|
||||
public static void AddPagination<TData>(this HttpResponse response, PagedList<TData> pagelist)
|
||||
{
|
||||
response.Headers.Add("X-Pagination", JsonSerializer.Serialize(pagelist.Meta as PagedHeaderData, new JsonSerializerOptions
|
||||
{
|
||||
PropertyNamingPolicy = JsonNamingPolicy.CamelCase
|
||||
}));
|
||||
}
|
||||
}
|
||||
|
|
@ -1,12 +1,11 @@
|
|||
using Insight.Infrastructure.Models;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using MongoDB.Bson;
|
||||
using MongoDB.Bson.Serialization;
|
||||
using MongoDB.Driver;
|
||||
|
||||
namespace Insight.Infrastructure;
|
||||
|
||||
public static class MongoCollectionExtensions
|
||||
public static partial class MongoCollectionExtensions
|
||||
{
|
||||
private const int _maximumLimit = 100;
|
||||
|
||||
|
|
@ -30,24 +29,6 @@ public static class MongoCollectionExtensions
|
|||
return new PagedList<TData>(data, offset, limit, total);
|
||||
}
|
||||
|
||||
public static async Task<PagedList<TData>> GetPagedAsync<TData>(
|
||||
this IMongoCollection<TData> collection,
|
||||
HttpRequest request,
|
||||
HttpResponse response,
|
||||
FilterDefinition<TData>? filter = null,
|
||||
SortDefinition<TData>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default)
|
||||
{
|
||||
var result = await GetPagedAsync(collection, filter, sort, offset, limit, cancellationToken).ConfigureAwait(false);
|
||||
|
||||
request?.AddPagination(result);
|
||||
response?.AddPagination(result);
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
public static async Task<PagedList<TResult>> GetPagedAsync<TData, TResult>(
|
||||
this IMongoCollection<TData> collection,
|
||||
IAggregateFluent<BsonDocument> query,
|
||||
|
|
@ -62,21 +43,4 @@ public static class MongoCollectionExtensions
|
|||
|
||||
return new PagedList<TResult>(data.Select(x => BsonSerializer.Deserialize<TResult>(x)), offset, limit, total);
|
||||
}
|
||||
|
||||
public static async Task<PagedList<TResult>> GetPagedAsync<TData, TResult>(
|
||||
this IMongoCollection<TData> collection,
|
||||
HttpRequest request,
|
||||
HttpResponse response,
|
||||
IAggregateFluent<BsonDocument> query,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default)
|
||||
{
|
||||
var result = await GetPagedAsync<TData, TResult>(collection, query, offset, limit, cancellationToken).ConfigureAwait(false);
|
||||
|
||||
request?.AddPagination(result);
|
||||
response?.AddPagination(result);
|
||||
|
||||
return result;
|
||||
}
|
||||
}
|
||||
|
|
@ -1,24 +1,13 @@
|
|||
using AspNetCore.Identity.MongoDbCore.Extensions;
|
||||
using AspNetCore.Identity.MongoDbCore.Infrastructure;
|
||||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Services;
|
||||
using Microsoft.AspNetCore.Authentication.JwtBearer;
|
||||
using Microsoft.AspNetCore.Builder;
|
||||
using Microsoft.AspNetCore.HttpOverrides;
|
||||
using Microsoft.AspNetCore.Identity;
|
||||
using Insight.Infrastructure.Services;
|
||||
using Microsoft.Extensions.Configuration;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using Microsoft.IdentityModel.Tokens;
|
||||
using Microsoft.Net.Http.Headers;
|
||||
using MongoDB.Bson;
|
||||
using MongoDB.Driver;
|
||||
using MongoDB.Driver.Core.Configuration;
|
||||
using System.Text;
|
||||
|
||||
namespace Insight.Infrastructure;
|
||||
|
||||
public static class ServiceExtensions
|
||||
public static partial class ServiceExtensions
|
||||
{
|
||||
public static IServiceCollection AddDatabase(this IServiceCollection services, IConfiguration configuration, ILoggerFactory? loggerFactory = null)
|
||||
{
|
||||
|
|
@ -42,221 +31,6 @@ public static class ServiceExtensions
|
|||
{
|
||||
services.AddTransient<IdentityService>();
|
||||
services.AddTransient<AuthenticatorService>();
|
||||
services.AddTransient<AccountService>();
|
||||
services.AddTransient<CustomerService>();
|
||||
services.AddTransient<HostService>();
|
||||
services.AddTransient<AgentService>();
|
||||
services.AddTransient<InventoryService>();
|
||||
return services;
|
||||
}
|
||||
|
||||
public static IServiceCollection AddIdentityServices(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
var connectionString = configuration.GetValue<string?>(Appsettings.Database) ?? throw new Exception($"{Appsettings.Database} value not set (appsettings)");
|
||||
|
||||
services.AddIdentity<InsightUser, InsightRole>(options =>
|
||||
{
|
||||
|
||||
})
|
||||
.AddMongoDbStores<InsightUser, InsightRole, ObjectId>(connectionString, Settings.Database)
|
||||
.AddDefaultTokenProviders()
|
||||
.AddSignInManager();
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
public static IServiceCollection AddTokenServices(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
var options = new Models.TokenOptions(
|
||||
key: configuration.GetValue<string?>(Appsettings.JwtKey) ?? throw new Exception($"{Appsettings.JwtKey} value not set (appsettings)"),
|
||||
expires: configuration.GetValue<int?>(Appsettings.JwtExp) ?? throw new Exception($"{Appsettings.JwtExp} value not set (appsettings)"),
|
||||
audience: configuration.GetValue<Uri?>(Appsettings.JwtAudience) ?? throw new Exception($"{Appsettings.JwtAudience} value not set (appsettings)"),
|
||||
issuer: configuration.GetValue<Uri?>(Appsettings.JwtIssuer) ?? throw new Exception($"{Appsettings.JwtIssuer} value not set (appsettings)"));
|
||||
|
||||
services.AddSingleton(options);
|
||||
services.AddTransient<TokenService>();
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
public static IServiceCollection AddCustomAuthentication(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
// REWRITE TO COOKIE ONLY FOR WEB
|
||||
|
||||
services.AddAuthentication(options =>
|
||||
{
|
||||
options.DefaultScheme = "Custom";
|
||||
options.DefaultChallengeScheme = "Custom";
|
||||
})
|
||||
.AddCookie("Cookies", options =>
|
||||
{
|
||||
//options.Cookie.Domain = "insight.webmatic.de";
|
||||
options.Cookie.Name = "insight";
|
||||
options.LoginPath = "/account/login";
|
||||
options.LogoutPath = "/account/logout";
|
||||
options.ExpireTimeSpan = TimeSpan.FromHours(1);
|
||||
options.SlidingExpiration = true;
|
||||
|
||||
options.Events.OnRedirectToLogin = options =>
|
||||
{
|
||||
if (options.Request.Path.StartsWithSegments("/api") && options.Response.StatusCode == 200)
|
||||
options.Response.StatusCode = 401;
|
||||
else
|
||||
options.Response.Redirect(options.RedirectUri);
|
||||
|
||||
return Task.CompletedTask;
|
||||
};
|
||||
})
|
||||
.AddJwtBearer("Bearer", options =>
|
||||
{
|
||||
options.RequireHttpsMetadata = false;
|
||||
options.SaveToken = true;
|
||||
|
||||
options.TokenValidationParameters.ValidateActor = false;
|
||||
|
||||
options.TokenValidationParameters.ValidAudience = configuration.GetSection("Jwt:Audience").Value;
|
||||
options.TokenValidationParameters.ValidateAudience = true;
|
||||
|
||||
options.TokenValidationParameters.ValidIssuer = configuration.GetSection("Jwt:Issuer").Value;
|
||||
options.TokenValidationParameters.ValidateIssuer = true;
|
||||
|
||||
options.TokenValidationParameters.IssuerSigningKey = new SymmetricSecurityKey(
|
||||
Encoding.UTF8.GetBytes(configuration.GetSection("Jwt:Key").Value ?? throw new ArgumentNullException(nameof(TokenValidationParameters), "Jwt:Key"))
|
||||
);
|
||||
|
||||
options.TokenValidationParameters.ValidateIssuerSigningKey = true;
|
||||
options.TokenValidationParameters.ValidateLifetime = true;
|
||||
})
|
||||
.AddPolicyScheme("Custom", "Custom", options =>
|
||||
{
|
||||
options.ForwardDefaultSelector = context =>
|
||||
{
|
||||
string authorization = context.Request.Headers[HeaderNames.Authorization];
|
||||
|
||||
if (!string.IsNullOrEmpty(authorization) && authorization.StartsWith("Bearer ")) return "Bearer";
|
||||
|
||||
return "Cookies";
|
||||
};
|
||||
});
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
public static IServiceCollection AddBearerAuthentication(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
services.AddAuthentication(options =>
|
||||
{
|
||||
options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
|
||||
options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
|
||||
options.DefaultSignInScheme = JwtBearerDefaults.AuthenticationScheme;
|
||||
})
|
||||
.AddJwtBearer(options =>
|
||||
{
|
||||
options.RequireHttpsMetadata = false;
|
||||
options.SaveToken = true;
|
||||
|
||||
options.TokenValidationParameters.ValidateActor = false;
|
||||
|
||||
options.TokenValidationParameters.ValidAudience = configuration.GetValue<string?>(Appsettings.JwtAudience) ?? throw new Exception($"{Appsettings.JwtAudience} value not set (appsettings)");
|
||||
options.TokenValidationParameters.ValidateAudience = true;
|
||||
|
||||
options.TokenValidationParameters.ValidIssuer = configuration.GetValue<string?>(Appsettings.JwtIssuer) ?? throw new Exception($"{Appsettings.JwtIssuer} value not set (appsettings)");
|
||||
options.TokenValidationParameters.ValidateIssuer = true;
|
||||
|
||||
options.TokenValidationParameters.IssuerSigningKey = new SymmetricSecurityKey(
|
||||
Encoding.UTF8.GetBytes(configuration.GetValue<string?>(Appsettings.JwtKey) ?? throw new Exception($"{Appsettings.JwtKey} value not set (appsettings)"))
|
||||
);
|
||||
|
||||
options.TokenValidationParameters.ValidateIssuerSigningKey = true;
|
||||
options.TokenValidationParameters.ValidateLifetime = true;
|
||||
});
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
public static IServiceCollection AddProxyServices(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
// add before routing
|
||||
services.Configure<ForwardedHeadersOptions>(options =>
|
||||
{
|
||||
options.ForwardedHeaders = ForwardedHeaders.XForwardedFor | ForwardedHeaders.XForwardedProto;
|
||||
});
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
public static IServiceCollection AddRoutingServices(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
// add after proxy
|
||||
services.AddRouting(options =>
|
||||
{
|
||||
options.LowercaseUrls = true;
|
||||
});
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
private static IServiceCollection AddIdentityServices2(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
var identityOptions = new MongoDbIdentityConfiguration
|
||||
{
|
||||
MongoDbSettings = new MongoDbSettings
|
||||
{
|
||||
ConnectionString = configuration.GetSection("ConnectionStrings:Mongo").Value,
|
||||
DatabaseName = "insight"
|
||||
},
|
||||
IdentityOptionsAction = options =>
|
||||
{
|
||||
options.User.RequireUniqueEmail = true;
|
||||
options.User.AllowedUserNameCharacters = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789@.-_";
|
||||
|
||||
options.Password.RequireDigit = false;
|
||||
options.Password.RequiredLength = 8;
|
||||
options.Password.RequireNonAlphanumeric = false;
|
||||
options.Password.RequireUppercase = false;
|
||||
options.Password.RequireLowercase = false;
|
||||
|
||||
options.SignIn.RequireConfirmedAccount = false;
|
||||
options.SignIn.RequireConfirmedEmail = false;
|
||||
options.SignIn.RequireConfirmedPhoneNumber = false;
|
||||
|
||||
options.Lockout.MaxFailedAccessAttempts = 5;
|
||||
options.Lockout.DefaultLockoutTimeSpan = TimeSpan.FromMinutes(5);
|
||||
}
|
||||
};
|
||||
|
||||
services.ConfigureMongoDbIdentity<InsightUser, InsightRole, ObjectId>(identityOptions)
|
||||
.AddDefaultTokenProviders()
|
||||
.AddSignInManager<InsightUser>();
|
||||
|
||||
return services;
|
||||
}
|
||||
|
||||
private static IServiceCollection AddIdentityAuthentication(this IServiceCollection services, IConfiguration configuration)
|
||||
{
|
||||
services.AddAuthentication(options =>
|
||||
{
|
||||
//options.DefaultAuthenticateScheme =
|
||||
});
|
||||
//cookieBuilder.ApplicationCookie = builder.AddApplicationCookie();
|
||||
//cookieBuilder.ExternalCookie = builder.AddExternalCookie();
|
||||
//cookieBuilder.TwoFactorRememberMeCookie = builder.AddTwoFactorRememberMeCookie();
|
||||
//cookieBuilder.TwoFactorUserIdCookie = builder.AddTwoFactorUserIdCookie();
|
||||
//.AddCookie(options =>
|
||||
//{
|
||||
// options.
|
||||
//};
|
||||
//.AddIdentityCookies();
|
||||
//.AddCookie(options =>
|
||||
//{
|
||||
// // Specify where to redirect un-authenticated users
|
||||
// options.LoginPath = "/account/login";
|
||||
|
||||
// // Specify the name of the auth cookie.
|
||||
// // ASP.NET picks a dumb name by default.
|
||||
// options.Cookie.Name = "insight";
|
||||
//});
|
||||
|
||||
return services;
|
||||
}
|
||||
}
|
||||
|
|
@ -1,28 +1,21 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net7.0</TargetFramework>
|
||||
<TargetFramework>net8.0</TargetFramework>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<Nullable>enable</Nullable>
|
||||
<RootNamespace>Insight.Infrastructure</RootNamespace>
|
||||
<Product>Insight</Product>
|
||||
<AssemblyVersion>2023.12.14.0</AssemblyVersion>
|
||||
<ImplicitUsings>true</ImplicitUsings>
|
||||
<Nullable>enable</Nullable>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
|
||||
<DebugType>none</DebugType>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Release|AnyCPU'">
|
||||
<DebugType>none</DebugType>
|
||||
<AssemblyVersion>2023.12.15.0</AssemblyVersion>
|
||||
<SatelliteResourceLanguages>none</SatelliteResourceLanguages>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.AspNetCore.Authentication.JwtBearer" Version="7.0.13" />
|
||||
<PackageReference Include="MongoDB.Driver" Version="2.23.0" />
|
||||
<PackageReference Include="Microsoft.AspNetCore.Http.Abstractions" Version="2.2.0" />
|
||||
<PackageReference Include="AspNetCore.Identity.MongoDbCore" Version="3.1.2" />
|
||||
<PackageReference Include="System.IdentityModel.Tokens.Jwt" Version="7.0.3" />
|
||||
<PackageReference Include="Vaitr.Scheduler" Version="2023.12.6" />
|
||||
<PackageReference Include="MongoDB.Driver" Version="2.23.1" />
|
||||
<PackageReference Include="Vaitr.Scheduler" Version="2023.12.15.1" />
|
||||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
|
|
|
|||
|
|
@ -1,17 +0,0 @@
|
|||
namespace Insight.Infrastructure.Models;
|
||||
|
||||
public class TokenOptions
|
||||
{
|
||||
public string Key { get; set; }
|
||||
public int Expires { get; set; }
|
||||
public Uri? Audience { get; set; }
|
||||
public Uri? Issuer { get; set; }
|
||||
|
||||
public TokenOptions(string key, int expires, Uri? audience = null, Uri? issuer = null)
|
||||
{
|
||||
Key = key;
|
||||
Expires = expires;
|
||||
Audience = audience;
|
||||
Issuer = issuer;
|
||||
}
|
||||
}
|
||||
|
|
@ -1,35 +0,0 @@
|
|||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Models;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using MongoDB.Driver;
|
||||
|
||||
namespace Insight.Infrastructure.Services;
|
||||
|
||||
public class AccountService
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
private readonly ILogger<AccountService> _logger;
|
||||
|
||||
public AccountService(IMongoDatabase database, ILogger<AccountService> logger)
|
||||
{
|
||||
_database = database;
|
||||
_logger = logger;
|
||||
}
|
||||
|
||||
public Task<PagedList<InsightUser>> GetAsync(
|
||||
FilterDefinition<InsightUser>? filter = null,
|
||||
SortDefinition<InsightUser>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default) => _database.User().GetPagedAsync(filter, sort, offset, limit, cancellationToken);
|
||||
|
||||
public Task<PagedList<InsightUser>> GetAsync(
|
||||
HttpRequest request,
|
||||
HttpResponse response,
|
||||
FilterDefinition<InsightUser>? filter = null,
|
||||
SortDefinition<InsightUser>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default) => _database.User().GetPagedAsync(request, response, filter, sort, offset, limit, cancellationToken);
|
||||
}
|
||||
|
|
@ -1,35 +0,0 @@
|
|||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Models;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using MongoDB.Driver;
|
||||
|
||||
namespace Insight.Infrastructure.Services;
|
||||
|
||||
public class AgentService
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
private readonly ILogger<AgentService> _logger;
|
||||
|
||||
public AgentService(IMongoDatabase database, ILogger<AgentService> logger)
|
||||
{
|
||||
_database = database;
|
||||
_logger = logger;
|
||||
}
|
||||
|
||||
public Task<PagedList<AgentEntity>> GetAsync(
|
||||
FilterDefinition<AgentEntity>? filter = null,
|
||||
SortDefinition<AgentEntity>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default) => _database.Agent().GetPagedAsync(filter, sort, offset, limit, cancellationToken);
|
||||
|
||||
public Task<PagedList<AgentEntity>> GetAsync(
|
||||
HttpRequest request,
|
||||
HttpResponse response,
|
||||
FilterDefinition<AgentEntity>? filter = null,
|
||||
SortDefinition<AgentEntity>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default) => _database.Agent().GetPagedAsync(request, response, filter, sort, offset, limit, cancellationToken);
|
||||
}
|
||||
|
|
@ -7,16 +7,9 @@ using System.Text.Encodings.Web;
|
|||
|
||||
namespace Insight.Infrastructure.Services;
|
||||
|
||||
public class AuthenticatorService
|
||||
public class AuthenticatorService(UserManager<InsightUser> userManager)
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
private readonly UserManager<InsightUser> _userManager;
|
||||
|
||||
public AuthenticatorService(IMongoDatabase database, UserManager<InsightUser> userManager)
|
||||
{
|
||||
_database = database;
|
||||
_userManager = userManager;
|
||||
}
|
||||
private readonly UserManager<InsightUser> _userManager = userManager;
|
||||
|
||||
public async Task<bool> GetStatusAsync(InsightUser user)
|
||||
{
|
||||
|
|
@ -79,7 +72,7 @@ public class AuthenticatorService
|
|||
return await _userManager.GenerateNewTwoFactorRecoveryCodesAsync(user, count).ConfigureAwait(false);
|
||||
}
|
||||
|
||||
public string GenerateQrCode(string email, string unformattedKey)
|
||||
public static string GenerateQrCode(string email, string unformattedKey)
|
||||
{
|
||||
var encoder = UrlEncoder.Default;
|
||||
|
||||
|
|
|
|||
|
|
@ -1,35 +0,0 @@
|
|||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Models;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using MongoDB.Driver;
|
||||
|
||||
namespace Insight.Infrastructure.Services;
|
||||
|
||||
public class CustomerService
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
private readonly ILogger<CustomerService> _logger;
|
||||
|
||||
public CustomerService(IMongoDatabase database, ILogger<CustomerService> logger)
|
||||
{
|
||||
_database = database;
|
||||
_logger = logger;
|
||||
}
|
||||
|
||||
public Task<PagedList<CustomerEntity>> GetAsync(
|
||||
FilterDefinition<CustomerEntity>? filter = null,
|
||||
SortDefinition<CustomerEntity>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default) => _database.Customer().GetPagedAsync(filter, sort, offset, limit, cancellationToken);
|
||||
|
||||
public Task<PagedList<CustomerEntity>> GetAsync(
|
||||
HttpRequest request,
|
||||
HttpResponse response,
|
||||
FilterDefinition<CustomerEntity>? filter = null,
|
||||
SortDefinition<CustomerEntity>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default) => _database.Customer().GetPagedAsync(request, response, filter, sort, offset, limit, cancellationToken);
|
||||
}
|
||||
|
|
@ -1,35 +0,0 @@
|
|||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Models;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using MongoDB.Driver;
|
||||
|
||||
namespace Insight.Infrastructure.Services;
|
||||
|
||||
public class HostService
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
private readonly ILogger<HostService> _logger;
|
||||
|
||||
public HostService(IMongoDatabase database, ILogger<HostService> logger)
|
||||
{
|
||||
_database = database;
|
||||
_logger = logger;
|
||||
}
|
||||
|
||||
public Task<PagedList<HostEntity>> GetAsync(
|
||||
FilterDefinition<HostEntity>? filter = null,
|
||||
SortDefinition<HostEntity>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default) => _database.Host().GetPagedAsync(filter, sort, offset, limit, cancellationToken);
|
||||
|
||||
public Task<PagedList<HostEntity>> GetAsync(
|
||||
HttpRequest request,
|
||||
HttpResponse response,
|
||||
FilterDefinition<HostEntity>? filter = null,
|
||||
SortDefinition<HostEntity>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default) => _database.Host().GetPagedAsync(request, response, filter, sort, offset, limit, cancellationToken);
|
||||
}
|
||||
|
|
@ -5,18 +5,10 @@ using System.Security.Claims;
|
|||
|
||||
namespace Insight.Infrastructure.Services;
|
||||
|
||||
public class IdentityService
|
||||
public class IdentityService(UserManager<InsightUser> userManager, RoleManager<InsightRole> roleManager)
|
||||
{
|
||||
private readonly UserManager<InsightUser> _userManager;
|
||||
private readonly RoleManager<InsightRole> _roleManager;
|
||||
private readonly ILogger<IdentityService> _logger;
|
||||
|
||||
public IdentityService(UserManager<InsightUser> userManager, RoleManager<InsightRole> roleManager, ILogger<IdentityService> logger)
|
||||
{
|
||||
_userManager = userManager;
|
||||
_roleManager = roleManager;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly UserManager<InsightUser> _userManager = userManager;
|
||||
private readonly RoleManager<InsightRole> _roleManager = roleManager;
|
||||
|
||||
public async Task SeedAsync()
|
||||
{
|
||||
|
|
|
|||
|
|
@ -1,35 +0,0 @@
|
|||
using Insight.Infrastructure.Entities;
|
||||
using Insight.Infrastructure.Models;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using MongoDB.Driver;
|
||||
|
||||
namespace Insight.Infrastructure.Services;
|
||||
|
||||
public class InventoryService
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
private readonly ILogger<InventoryService> _logger;
|
||||
|
||||
public InventoryService(IMongoDatabase database, ILogger<InventoryService> logger)
|
||||
{
|
||||
_database = database;
|
||||
_logger = logger;
|
||||
}
|
||||
|
||||
public Task<PagedList<HostApplicationEntity>> GetAsync(
|
||||
FilterDefinition<HostApplicationEntity>? filter = null,
|
||||
SortDefinition<HostApplicationEntity>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default) => _database.HostApplication().GetPagedAsync(filter, sort, offset, limit, cancellationToken);
|
||||
|
||||
public Task<PagedList<HostApplicationEntity>> GetAsync(
|
||||
HttpRequest request,
|
||||
HttpResponse response,
|
||||
FilterDefinition<HostApplicationEntity>? filter = null,
|
||||
SortDefinition<HostApplicationEntity>? sort = null,
|
||||
int offset = 0,
|
||||
int limit = 10,
|
||||
CancellationToken cancellationToken = default) => _database.HostApplication().GetPagedAsync(request, response, filter, sort, offset, limit, cancellationToken);
|
||||
}
|
||||
|
|
@ -1,20 +1,22 @@
|
|||
<Project Sdk="Microsoft.NET.Sdk">
|
||||
|
||||
<PropertyGroup>
|
||||
<TargetFramework>net7.0</TargetFramework>
|
||||
<TargetFramework>net8.0</TargetFramework>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<RootNamespace>Insight.Remote.Shared</RootNamespace>
|
||||
<Product>Insight</Product>
|
||||
<AssemblyName>Insight.Remote.Shared</AssemblyName>
|
||||
<AssemblyVersion>2023.12.14.0</AssemblyVersion>
|
||||
<AssemblyVersion>2023.12.15.0</AssemblyVersion>
|
||||
<Nullable>enable</Nullable>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<GeneratePackageOnBuild>True</GeneratePackageOnBuild>
|
||||
<AllowUnsafeBlocks>True</AllowUnsafeBlocks>
|
||||
<SatelliteResourceLanguages>none</SatelliteResourceLanguages>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.IO.RecyclableMemoryStream" Version="3.0.0" />
|
||||
<PackageReference Include="System.ServiceProcess.ServiceController" Version="7.0.1" />
|
||||
<PackageReference Include="System.ServiceProcess.ServiceController" Version="8.0.0" />
|
||||
<PackageReference Include="SkiaSharp.Views.Desktop.Common" Version="2.88.6" />
|
||||
</ItemGroup>
|
||||
|
||||
|
|
|
|||
|
|
@ -2,16 +2,9 @@
|
|||
|
||||
namespace Insight.Remote.Shared.Models;
|
||||
|
||||
public class CursorInfo
|
||||
public class CursorInfo(byte[] imageBytes, Point hotspot, string cssOverride = "")
|
||||
{
|
||||
public byte[] ImageBytes { get; set; }
|
||||
public Point HotSpot { get; set; }
|
||||
public string CssOverride { get; set; }
|
||||
|
||||
public CursorInfo(byte[] imageBytes, Point hotspot, string cssOverride = "")
|
||||
{
|
||||
ImageBytes = imageBytes;
|
||||
HotSpot = hotspot;
|
||||
CssOverride = cssOverride;
|
||||
}
|
||||
public byte[] ImageBytes { get; set; } = imageBytes;
|
||||
public Point HotSpot { get; set; } = hotspot;
|
||||
public string CssOverride { get; set; } = cssOverride;
|
||||
}
|
||||
|
|
@ -1,13 +1,7 @@
|
|||
namespace Insight.Remote.Shared.Models;
|
||||
|
||||
public readonly struct SentFrame
|
||||
public readonly struct SentFrame(int frameSize, DateTimeOffset timestamp)
|
||||
{
|
||||
public SentFrame(int frameSize, DateTimeOffset timestamp)
|
||||
{
|
||||
FrameSize = frameSize;
|
||||
Timestamp = timestamp;
|
||||
}
|
||||
|
||||
public DateTimeOffset Timestamp { get; }
|
||||
public int FrameSize { get; }
|
||||
public DateTimeOffset Timestamp { get; } = timestamp;
|
||||
public int FrameSize { get; } = frameSize;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -235,7 +235,7 @@ public static class SECUR32
|
|||
MaxTokenInfoClass
|
||||
}
|
||||
[StructLayout(LayoutKind.Sequential)]
|
||||
public struct QUOTA_LIMITS
|
||||
public readonly struct QUOTA_LIMITS
|
||||
{
|
||||
readonly UInt32 PagedPoolLimit;
|
||||
readonly UInt32 NonPagedPoolLimit;
|
||||
|
|
|
|||
|
|
@ -9,18 +9,11 @@ using Vaitr.Bus;
|
|||
|
||||
namespace Insight.Remote.Shared.Network.Handlers;
|
||||
|
||||
public class RemoteHandler : IMessageHandler<RemoteSession>
|
||||
public class RemoteHandler(Bus bus, Streamer streamer, ILogger<RemoteHandler> logger) : IMessageHandler<RemoteSession>
|
||||
{
|
||||
private readonly Bus _bus;
|
||||
private readonly Streamer _streamer;
|
||||
private readonly ILogger<RemoteHandler> _logger;
|
||||
|
||||
public RemoteHandler(Bus bus, Streamer streamer, ILogger<RemoteHandler> logger)
|
||||
{
|
||||
_bus = bus;
|
||||
_streamer = streamer;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly Bus _bus = bus;
|
||||
private readonly Streamer _streamer = streamer;
|
||||
private readonly ILogger<RemoteHandler> _logger = logger;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(RemoteSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -48,16 +41,18 @@ public class RemoteHandler : IMessageHandler<RemoteSession>
|
|||
|
||||
private async Task OnSessionResponse(RemoteSession session, RemoteSessionResponse sessionResponse, CancellationToken cancellationToken)
|
||||
{
|
||||
_logger.LogInformation($"Remote {session.Id} => SessionResponse");
|
||||
if (session.Id is not string sessionId) return;
|
||||
|
||||
_logger.LogInformation("Remote {session} => SessionResponse", sessionId);
|
||||
|
||||
session.Id = sessionResponse.SessionId;
|
||||
|
||||
await _bus.PublishAsync(new IdentityChanged(session.Id));
|
||||
await _bus.PublishAsync(new IdentityChanged(sessionId), cancellationToken);
|
||||
}
|
||||
|
||||
private async Task OnCastRequest(RemoteSession session, CastRequest castRequest, CancellationToken cancellationToken)
|
||||
{
|
||||
_logger.LogInformation($"Remote {session.Id} => CastRequest");
|
||||
_logger.LogInformation("Remote {session.Id} => CastRequest", session.Id);
|
||||
|
||||
//if (request.RequesterName is null || request.ConnectionId is null) return;
|
||||
|
||||
|
|
@ -105,7 +100,7 @@ public class RemoteHandler : IMessageHandler<RemoteSession>
|
|||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError("{exception}", ex.Message);
|
||||
}
|
||||
|
||||
//DesktopStream? viewer = _viewerPool.Values.FirstOrDefault(p => p.ConnectionId == request.ConnectionId);
|
||||
|
|
@ -121,7 +116,7 @@ public class RemoteHandler : IMessageHandler<RemoteSession>
|
|||
|
||||
private async Task OnCastAbort(RemoteSession session, CastAbort castAbort, CancellationToken cancellationToken)
|
||||
{
|
||||
_logger.LogInformation($"Remote {session.Id} => CastAbort");
|
||||
_logger.LogInformation("Remote {session} => CastAbort", session.Id);
|
||||
|
||||
await _streamer.CancelAsync(castAbort, cancellationToken);
|
||||
}
|
||||
|
|
@ -148,7 +143,7 @@ public class RemoteHandler : IMessageHandler<RemoteSession>
|
|||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.ToString());
|
||||
_logger.LogError("{exception}", ex.ToString());
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -4,26 +4,23 @@ using Insight.Domain.Network;
|
|||
using Insight.Domain.Network.Remote.Messages;
|
||||
using Insight.Remote.Shared.Messages;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using System.ServiceProcess;
|
||||
using Vaitr.Bus;
|
||||
using Vaitr.Network;
|
||||
|
||||
namespace Insight.Remote.Shared.Network;
|
||||
|
||||
public class RemoteSession : TcpSession<IMessage>
|
||||
public class RemoteSession(
|
||||
Bus bus,
|
||||
IEnumerable<IMessageHandler<RemoteSession>> handlers,
|
||||
ISerializer<IMessage> serializer,
|
||||
ILogger<RemoteSession> logger) : TcpSession<IMessage>(serializer, logger)
|
||||
{
|
||||
public string? Id { get; set; }
|
||||
public string? AccessKey { get; set; }
|
||||
public RemoteControlMode Mode { get; } = RunningAsService() ? RemoteControlMode.Unattended : RemoteControlMode.Attended;
|
||||
|
||||
private readonly Bus _bus;
|
||||
private readonly IEnumerable<IMessageHandler<RemoteSession>> _handlers;
|
||||
|
||||
public RemoteSession(Bus bus, IEnumerable<IMessageHandler<RemoteSession>> handlers, ISerializer<IMessage> serializer, ILogger<RemoteSession> logger) : base(serializer, logger)
|
||||
{
|
||||
_bus = bus;
|
||||
_handlers = handlers;
|
||||
}
|
||||
private readonly Bus _bus = bus;
|
||||
private readonly IEnumerable<IMessageHandler<RemoteSession>> _handlers = handlers;
|
||||
|
||||
protected override async ValueTask OnConnectedAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
|
|
@ -45,9 +42,10 @@ public class RemoteSession : TcpSession<IMessage>
|
|||
await _bus.PublishAsync(new ConnectionStateChanged(ConnectionState.Disconnected));
|
||||
}
|
||||
|
||||
protected override async ValueTask OnSentAsync(IPacketContext<IMessage> context, CancellationToken cancellationToken)
|
||||
protected override ValueTask OnSentAsync(IPacketContext<IMessage> context, CancellationToken cancellationToken)
|
||||
{
|
||||
//await base.OnSentAsync(context, cancellationToken);
|
||||
return default;
|
||||
}
|
||||
|
||||
protected override async ValueTask OnReceivedAsync(IPacketContext<IMessage> context, CancellationToken cancellationToken)
|
||||
|
|
@ -67,12 +65,14 @@ public class RemoteSession : TcpSession<IMessage>
|
|||
}
|
||||
}
|
||||
|
||||
protected override async ValueTask OnHeartbeatAsync(CancellationToken cancellationToken)
|
||||
protected override ValueTask OnHeartbeatAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
_logger.LogInformation("Remote ({ep?}) Heartbeat", RemoteEndPoint);
|
||||
|
||||
return default;
|
||||
}
|
||||
|
||||
private async ValueTask OnWindowsSessionSwitchedAsync(WindowsSessionSwitched message, CancellationToken cancellationToken)
|
||||
private ValueTask OnWindowsSessionSwitchedAsync(WindowsSessionSwitched message, CancellationToken cancellationToken)
|
||||
{
|
||||
try
|
||||
{
|
||||
|
|
@ -80,23 +80,24 @@ public class RemoteSession : TcpSession<IMessage>
|
|||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError("{exception}", ex.Message);
|
||||
}
|
||||
|
||||
return default;
|
||||
}
|
||||
|
||||
private async ValueTask OnWindowsSessionEndingAsync(WindowsSessionEnding message, CancellationToken cancellationToken)
|
||||
private static ValueTask OnWindowsSessionEndingAsync(WindowsSessionEnding message, CancellationToken cancellationToken)
|
||||
{
|
||||
//await DisconnectViewersAsync();
|
||||
return default;
|
||||
}
|
||||
|
||||
private static bool RunningAsService()
|
||||
{
|
||||
return false;
|
||||
|
||||
if (OperatingSystem.IsWindows())
|
||||
{
|
||||
return ServiceController.GetServices().Any(serviceController => serviceController.ServiceName.Equals("remotecontrol"));
|
||||
}
|
||||
//if (OperatingSystem.IsWindows())
|
||||
//{
|
||||
// return ServiceController.GetServices().Any(serviceController => serviceController.ServiceName.Equals("remotecontrol"));
|
||||
//}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
|
|
|||
|
|
@ -10,7 +10,7 @@ public class Runtime : IHostedService
|
|||
private readonly CancellationTokenSource _cts = new();
|
||||
|
||||
private Task? _desktopTask;
|
||||
private Thread? _uiThread;
|
||||
private readonly Thread? _uiThread;
|
||||
|
||||
private readonly IDesktopApp _desktopApp;
|
||||
private readonly IDispatcher _dispatcher;
|
||||
|
|
@ -31,20 +31,21 @@ public class Runtime : IHostedService
|
|||
_lifetime.ApplicationStopping.Register(_cts.Cancel);
|
||||
}
|
||||
|
||||
public async Task StartAsync(CancellationToken cancellationToken)
|
||||
public Task StartAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
// init app (os specific providers)
|
||||
_desktopTask = _desktopApp.InitAsync(RemoteControlMode.Attended, _cts.Token);
|
||||
|
||||
// init dispatcher
|
||||
if (false) // if mode is attended (interactive)
|
||||
{
|
||||
// init ui thread
|
||||
_uiThread = await _dispatcher.RunAsync(_cts.Token);
|
||||
}
|
||||
// init ui dispatcher / if mode is attended (interactive)
|
||||
//if (true)
|
||||
//{
|
||||
// _uiThread = await _dispatcher.RunAsync(_cts.Token);
|
||||
//}
|
||||
|
||||
// todo
|
||||
// report unattended accesskey to api ($"https://localhost:7024?mode=Unattended&sessionId={appState.SessionId}&accessKey={appState.AccessKey}")
|
||||
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
public async Task StopAsync(CancellationToken cancellationToken)
|
||||
|
|
|
|||
|
|
@ -14,7 +14,16 @@ using Vaitr.Network;
|
|||
|
||||
namespace Insight.Remote.Shared.Services;
|
||||
|
||||
public class Streamer : IDisposable
|
||||
public class Streamer(
|
||||
Bus bus,
|
||||
ISessionPool<RemoteSession, IMessage> remotePool,
|
||||
IFileProvider fileProvider,
|
||||
IClipboardProvider clipboardProvider,
|
||||
IAudioProvider audioProvider,
|
||||
IInputProvider inputProvider,
|
||||
ICursorProvider cursorProvider,
|
||||
IScreenProvider screenProvider,
|
||||
ILogger<Streamer> logger) : IDisposable
|
||||
{
|
||||
public int ImageQuality { get; set; } = 50;
|
||||
public bool HasControl { get; set; } = true;
|
||||
|
|
@ -34,37 +43,15 @@ public class Streamer : IDisposable
|
|||
private readonly ConcurrentQueue<DateTimeOffset> _fpsQueue = new();
|
||||
private readonly ConcurrentQueue<SentFrame> _sentFrames = new();
|
||||
|
||||
private readonly Bus _bus;
|
||||
private readonly ISessionPool<RemoteSession, IMessage> _remotePool;
|
||||
private readonly IFileProvider _fileProvider;
|
||||
private readonly IClipboardProvider _clipboardProvider;
|
||||
private readonly IAudioProvider _audioProvider;
|
||||
private readonly IInputProvider _inputProvider;
|
||||
private readonly ICursorProvider _cursorProvider;
|
||||
private readonly IScreenProvider _screenProvider;
|
||||
private readonly ILogger<Streamer> _logger;
|
||||
|
||||
public Streamer(
|
||||
Bus bus,
|
||||
ISessionPool<RemoteSession, IMessage> remotePool,
|
||||
IFileProvider fileProvider,
|
||||
IClipboardProvider clipboardProvider,
|
||||
IAudioProvider audioProvider,
|
||||
IInputProvider inputProvider,
|
||||
ICursorProvider cursorProvider,
|
||||
IScreenProvider screenProvider,
|
||||
ILogger<Streamer> logger)
|
||||
{
|
||||
_bus = bus;
|
||||
_remotePool = remotePool;
|
||||
_fileProvider = fileProvider;
|
||||
_clipboardProvider = clipboardProvider;
|
||||
_audioProvider = audioProvider;
|
||||
_inputProvider = inputProvider;
|
||||
_cursorProvider = cursorProvider;
|
||||
_screenProvider = screenProvider;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly Bus _bus = bus;
|
||||
private readonly ISessionPool<RemoteSession, IMessage> _remotePool = remotePool;
|
||||
private readonly IFileProvider _fileProvider = fileProvider;
|
||||
private readonly IClipboardProvider _clipboardProvider = clipboardProvider;
|
||||
private readonly IAudioProvider _audioProvider = audioProvider;
|
||||
private readonly IInputProvider _inputProvider = inputProvider;
|
||||
private readonly ICursorProvider _cursorProvider = cursorProvider;
|
||||
private readonly IScreenProvider _screenProvider = screenProvider;
|
||||
private readonly ILogger<Streamer> _logger = logger;
|
||||
|
||||
public async Task InitAsync(CastRequest request, CancellationToken cancellationToken)
|
||||
{
|
||||
|
|
@ -108,7 +95,7 @@ public class Streamer : IDisposable
|
|||
catch (OperationCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError("{exception}", ex.Message);
|
||||
}
|
||||
finally
|
||||
{
|
||||
|
|
@ -268,7 +255,7 @@ public class Streamer : IDisposable
|
|||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
|
||||
_logger.LogError("{exception}", ex.Message);
|
||||
}
|
||||
finally
|
||||
{
|
||||
|
|
@ -331,15 +318,20 @@ public class Streamer : IDisposable
|
|||
// }
|
||||
//}
|
||||
|
||||
public async Task CancelAsync(CastAbort castAbort, CancellationToken cancellationToken)
|
||||
public Task CancelAsync(CastAbort castAbort, CancellationToken cancellationToken)
|
||||
{
|
||||
_cts?.Cancel();
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
public async Task FrameReceivedAsync(CastScreenReceived screenDataReceived, CancellationToken cancellationToken)
|
||||
public Task FrameReceivedAsync(CastScreenReceived screenDataReceived, CancellationToken cancellationToken)
|
||||
{
|
||||
if (screenDataReceived.Timestamp is null) return Task.CompletedTask;
|
||||
|
||||
_lastFrameReceived = screenDataReceived.Timestamp.Value.ToLocalTime();
|
||||
_framesSentSinceLastReceipt = 0;
|
||||
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
public async Task CursorReceivedAsync(CastCursorReceived cursorCallbackData, CancellationToken cancellationToken)
|
||||
|
|
|
|||
|
|
@ -2,7 +2,8 @@
|
|||
|
||||
<PropertyGroup>
|
||||
<OutputType>Exe</OutputType>
|
||||
<TargetFramework>net7.0-windows</TargetFramework>
|
||||
<TargetFramework>net8.0-windows</TargetFramework>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<UseWPF>true</UseWPF>
|
||||
<UseWindowsForms>true</UseWindowsForms>
|
||||
<Product>Remote Control</Product>
|
||||
|
|
@ -12,10 +13,11 @@
|
|||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<Nullable>enable</Nullable>
|
||||
<AllowUnsafeBlocks>True</AllowUnsafeBlocks>
|
||||
<SatelliteResourceLanguages>none</SatelliteResourceLanguages>
|
||||
</PropertyGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="7.0.1" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="8.0.0" />
|
||||
<PackageReference Include="NAudio.Wasapi" Version="2.2.1" />
|
||||
<PackageReference Include="SharpDX.Direct3D11" Version="4.2.0" />
|
||||
</ItemGroup>
|
||||
|
|
|
|||
|
|
@ -4,28 +4,18 @@ using SharpDX.DXGI;
|
|||
|
||||
namespace Insight.Remote.Windows.Models;
|
||||
|
||||
public class DirectXOutput : IDisposable
|
||||
public class DirectXOutput(Adapter1 adapter,
|
||||
SharpDX.Direct3D11.Device device,
|
||||
OutputDuplication outputDuplication,
|
||||
Texture2D texture2D,
|
||||
DisplayModeRotation rotation) : IDisposable
|
||||
{
|
||||
public DirectXOutput(Adapter1 adapter,
|
||||
SharpDX.Direct3D11.Device device,
|
||||
OutputDuplication outputDuplication,
|
||||
Texture2D texture2D,
|
||||
DisplayModeRotation rotation)
|
||||
{
|
||||
Adapter = adapter;
|
||||
Device = device;
|
||||
OutputDuplication = outputDuplication;
|
||||
Texture2D = texture2D;
|
||||
Rotation = rotation;
|
||||
Bounds = new Rectangle(0, 0, texture2D.Description.Width, texture2D.Description.Height);
|
||||
}
|
||||
|
||||
public Adapter1 Adapter { get; }
|
||||
public Rectangle Bounds { get; set; }
|
||||
public SharpDX.Direct3D11.Device Device { get; }
|
||||
public OutputDuplication OutputDuplication { get; }
|
||||
public DisplayModeRotation Rotation { get; }
|
||||
public Texture2D Texture2D { get; }
|
||||
public Adapter1 Adapter { get; } = adapter;
|
||||
public Rectangle Bounds { get; set; } = new Rectangle(0, 0, texture2D.Description.Width, texture2D.Description.Height);
|
||||
public SharpDX.Direct3D11.Device Device { get; } = device;
|
||||
public OutputDuplication OutputDuplication { get; } = outputDuplication;
|
||||
public DisplayModeRotation Rotation { get; } = rotation;
|
||||
public Texture2D Texture2D { get; } = texture2D;
|
||||
|
||||
public void Dispose()
|
||||
{
|
||||
|
|
|
|||
|
|
@ -9,44 +9,33 @@ using Microsoft.Extensions.Logging;
|
|||
using Microsoft.Win32;
|
||||
using System.Collections.Concurrent;
|
||||
using System.Diagnostics;
|
||||
using System.Windows;
|
||||
using System.Runtime.Versioning;
|
||||
using Vaitr.Bus;
|
||||
|
||||
namespace Insight.Remote.Windows.Services;
|
||||
|
||||
internal class WinApp : IDesktopApp
|
||||
[SupportedOSPlatform("windows")]
|
||||
internal class WinApp(
|
||||
IInputProvider inputProvider,
|
||||
ICursorProvider cursorProvider,
|
||||
IAudioProvider audioProvider,
|
||||
IClipboardProvider clipboardProvider,
|
||||
IDispatcher dispatcher,
|
||||
MainViewModel mainViewModel,
|
||||
Bus bus,
|
||||
ILogger<WinApp> logger) : IDesktopApp
|
||||
{
|
||||
private MainWindow? _mainWindow;
|
||||
private bool _disposed;
|
||||
|
||||
private readonly IInputProvider _inputProvider;
|
||||
private readonly ICursorProvider _cursorProvider;
|
||||
private readonly IAudioProvider _audioProvider;
|
||||
private readonly IClipboardProvider _clipboardProvider;
|
||||
private readonly IDispatcher _dispatcher;
|
||||
private readonly MainViewModel _maiViewModel;
|
||||
private readonly Bus _bus;
|
||||
private readonly ILogger<WinApp> _logger;
|
||||
|
||||
public WinApp(
|
||||
IInputProvider inputProvider,
|
||||
ICursorProvider cursorProvider,
|
||||
IAudioProvider audioProvider,
|
||||
IClipboardProvider clipboardProvider,
|
||||
IDispatcher dispatcher,
|
||||
MainViewModel mainViewModel,
|
||||
Bus bus,
|
||||
ILogger<WinApp> logger)
|
||||
{
|
||||
_inputProvider = inputProvider;
|
||||
_cursorProvider = cursorProvider;
|
||||
_audioProvider = audioProvider;
|
||||
_clipboardProvider = clipboardProvider;
|
||||
_dispatcher = dispatcher;
|
||||
_maiViewModel = mainViewModel;
|
||||
_bus = bus;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly IInputProvider _inputProvider = inputProvider;
|
||||
private readonly ICursorProvider _cursorProvider = cursorProvider;
|
||||
private readonly IAudioProvider _audioProvider = audioProvider;
|
||||
private readonly IClipboardProvider _clipboardProvider = clipboardProvider;
|
||||
private readonly IDispatcher _dispatcher = dispatcher;
|
||||
private readonly MainViewModel _maiViewModel = mainViewModel;
|
||||
private readonly Bus _bus = bus;
|
||||
private readonly ILogger<WinApp> _logger = logger;
|
||||
|
||||
public async Task InitAsync(RemoteControlMode mode, CancellationToken cancellationToken)
|
||||
{
|
||||
|
|
@ -100,7 +89,7 @@ internal class WinApp : IDesktopApp
|
|||
catch (TaskCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError("{exception}", ex.Message);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -143,7 +132,7 @@ internal class WinApp : IDesktopApp
|
|||
catch (TaskCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError("{exception}", ex.Message);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -153,26 +142,21 @@ internal class WinApp : IDesktopApp
|
|||
|
||||
private async ValueTask OnCastRequestAsync(CastRequest request, CancellationToken cancellationToken)
|
||||
{
|
||||
if (true) // test
|
||||
{
|
||||
await _bus.PublishAsync(new CastRequestDemand(request, true), cancellationToken);
|
||||
return;
|
||||
}
|
||||
// test (bypass)
|
||||
//if (request.Mode != RemoteControlMode.Unattended)
|
||||
//{
|
||||
// var result = await _dispatcher.InvokeAsync(() =>
|
||||
// {
|
||||
// return System.Windows.MessageBox.Show($"Accept connection request from {request.RequesterName}?", "Connection Request",
|
||||
// MessageBoxButton.YesNo,
|
||||
// MessageBoxImage.Question);
|
||||
// }, cancellationToken);
|
||||
|
||||
if (request.Mode != RemoteControlMode.Unattended)
|
||||
{
|
||||
var result = await _dispatcher.InvokeAsync(() =>
|
||||
{
|
||||
return System.Windows.MessageBox.Show($"Accept connection request from {request.RequesterName}?", "Connection Request",
|
||||
MessageBoxButton.YesNo,
|
||||
MessageBoxImage.Question);
|
||||
}, cancellationToken);
|
||||
|
||||
switch (result)
|
||||
{
|
||||
case MessageBoxResult.No: await _bus.PublishAsync(new CastRequestDemand(request, false), cancellationToken); return;
|
||||
}
|
||||
}
|
||||
// switch (result)
|
||||
// {
|
||||
// case MessageBoxResult.No: await _bus.PublishAsync(new CastRequestDemand(request, false), cancellationToken); return;
|
||||
// }
|
||||
//}
|
||||
|
||||
await _bus.PublishAsync(new CastRequestDemand(request, true), cancellationToken);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -7,19 +7,13 @@ using Vaitr.Bus;
|
|||
|
||||
namespace Insight.Remote.Windows.Services;
|
||||
|
||||
internal class WinAudioProvider : IAudioProvider
|
||||
internal class WinAudioProvider(Bus bus, ILogger<WinAudioProvider> logger) : IAudioProvider
|
||||
{
|
||||
private WasapiLoopbackCapture? _capturer;
|
||||
private WaveFormat? _targetFormat;
|
||||
|
||||
private readonly Bus _bus;
|
||||
private readonly ILogger<WinAudioProvider> _logger;
|
||||
|
||||
public WinAudioProvider(Bus bus, ILogger<WinAudioProvider> logger)
|
||||
{
|
||||
_bus = bus;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly Bus _bus = bus;
|
||||
private readonly ILogger<WinAudioProvider> _logger = logger;
|
||||
|
||||
public async Task InitAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -8,18 +8,12 @@ using Clipboard = System.Windows.Clipboard;
|
|||
|
||||
namespace Insight.Remote.Windows.Services;
|
||||
|
||||
internal class WinClipboardProvider : IClipboardProvider
|
||||
internal class WinClipboardProvider(Bus bus, ILogger<WinClipboardProvider> logger) : IClipboardProvider
|
||||
{
|
||||
private readonly ConcurrentQueue<string> _setQueue = new();
|
||||
|
||||
private readonly Bus _bus;
|
||||
private readonly ILogger<WinClipboardProvider> _logger;
|
||||
|
||||
public WinClipboardProvider(Bus bus, ILogger<WinClipboardProvider> logger)
|
||||
{
|
||||
_bus = bus;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly Bus _bus = bus;
|
||||
private readonly ILogger<WinClipboardProvider> _logger = logger;
|
||||
|
||||
public async Task InitAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
|
|
@ -79,7 +73,7 @@ internal class WinClipboardProvider : IClipboardProvider
|
|||
catch (TaskCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError("{exception}", ex.Message);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -8,20 +8,15 @@ using System.Runtime.InteropServices;
|
|||
|
||||
namespace Insight.Remote.Windows.Services;
|
||||
|
||||
internal class WinCursorProvider : ICursorProvider
|
||||
internal class WinCursorProvider(ILogger<WinCursorProvider> logger) : ICursorProvider
|
||||
{
|
||||
private readonly SemaphoreSlim _semaphore = new(1, 1);
|
||||
private readonly ILogger<WinCursorProvider> _logger;
|
||||
private readonly ILogger<WinCursorProvider> _logger = logger;
|
||||
|
||||
private User32.CursorInfo _cursor = new();
|
||||
private CastCursor _lastCursor = new();
|
||||
private nint _lastHandle = 0;
|
||||
private byte[] _lastIconBytes = Array.Empty<byte>();
|
||||
|
||||
public WinCursorProvider(ILogger<WinCursorProvider> logger)
|
||||
{
|
||||
_logger = logger;
|
||||
}
|
||||
private byte[] _lastIconBytes = [];
|
||||
|
||||
public async Task<CastCursor?> GetAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
|
|
@ -73,7 +68,7 @@ internal class WinCursorProvider : ICursorProvider
|
|||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError("{exception}", ex.Message);
|
||||
return null;
|
||||
}
|
||||
finally
|
||||
|
|
@ -92,10 +87,10 @@ internal class WinCursorProvider : ICursorProvider
|
|||
|
||||
User32.SetCursorPos(x, y);
|
||||
}
|
||||
catch (TaskCanceledException) { }
|
||||
catch (OperationCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError("{exception}", ex.Message);
|
||||
}
|
||||
finally
|
||||
{
|
||||
|
|
@ -107,6 +102,6 @@ internal class WinCursorProvider : ICursorProvider
|
|||
{
|
||||
X = 0,
|
||||
Y = 0,
|
||||
Icon = Array.Empty<byte>()
|
||||
Icon = []
|
||||
};
|
||||
}
|
||||
|
|
@ -6,20 +6,14 @@ using Application = System.Windows.Application;
|
|||
|
||||
namespace Insight.Remote.Windows.Services;
|
||||
|
||||
internal class WinDispatcher : IDispatcher
|
||||
internal class WinDispatcher(IHostApplicationLifetime lifetime, ILogger<WinDispatcher> logger) : IDispatcher
|
||||
{
|
||||
private Application? _app;
|
||||
|
||||
private readonly ManualResetEvent _appSignal = new(false);
|
||||
|
||||
private readonly IHostApplicationLifetime _lifetime;
|
||||
private readonly ILogger<WinDispatcher> _logger;
|
||||
|
||||
public WinDispatcher(IHostApplicationLifetime lifetime, ILogger<WinDispatcher> logger)
|
||||
{
|
||||
_lifetime = lifetime;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly IHostApplicationLifetime _lifetime = lifetime;
|
||||
private readonly ILogger<WinDispatcher> _logger = logger;
|
||||
|
||||
public async Task<Thread> RunAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
|
|
@ -56,7 +50,7 @@ internal class WinDispatcher : IDispatcher
|
|||
catch (TaskCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError("{exception}", ex.Message);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -5,6 +5,7 @@ using Microsoft.Extensions.Logging;
|
|||
using System.Collections.Concurrent;
|
||||
using System.Diagnostics;
|
||||
using System.IO;
|
||||
using System.Runtime.Versioning;
|
||||
using System.Security.AccessControl;
|
||||
using System.Security.Principal;
|
||||
using System.Windows;
|
||||
|
|
@ -12,17 +13,13 @@ using MessageBoxOptions = System.Windows.MessageBoxOptions;
|
|||
|
||||
namespace Insight.Remote.Windows.Services;
|
||||
|
||||
internal class WinFileProvider : IFileProvider
|
||||
[SupportedOSPlatform("windows")]
|
||||
internal class WinFileProvider(ILogger<WinFileProvider> logger) : IFileProvider
|
||||
{
|
||||
private static MessageBoxResult? _result;
|
||||
private static readonly ConcurrentDictionary<string, FileStream> _partialTransfers = new();
|
||||
private static readonly SemaphoreSlim _writeLock = new(1, 1);
|
||||
private readonly ILogger<WinFileProvider> _logger;
|
||||
|
||||
public WinFileProvider(ILogger<WinFileProvider> logger)
|
||||
{
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly ILogger<WinFileProvider> _logger = logger;
|
||||
|
||||
public string GetBaseDirectory()
|
||||
{
|
||||
|
|
@ -89,7 +86,7 @@ internal class WinFileProvider : IFileProvider
|
|||
}
|
||||
}
|
||||
|
||||
public async Task UploadFile(FileUpload fileUpload, Streamer viewer, Action<double> progressUpdateCallback, CancellationToken cancelToken)
|
||||
public Task UploadFile(FileUpload fileUpload, Streamer viewer, Action<double> progressUpdateCallback, CancellationToken cancelToken)
|
||||
{
|
||||
try
|
||||
{
|
||||
|
|
@ -99,9 +96,11 @@ internal class WinFileProvider : IFileProvider
|
|||
{
|
||||
_logger.LogError(ex, "Error while uploading file.");
|
||||
}
|
||||
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
private void SetFileOrFolderPermissions(string path)
|
||||
private static void SetFileOrFolderPermissions(string path)
|
||||
{
|
||||
FileSystemSecurity ds;
|
||||
|
||||
|
|
|
|||
|
|
@ -6,20 +6,14 @@ using System.Threading.Channels;
|
|||
|
||||
namespace Insight.Remote.Windows.Services;
|
||||
|
||||
internal class WinInputProvider : IInputProvider
|
||||
internal class WinInputProvider(IScreenProvider screenProvider, ILogger<WinInputProvider> logger) : IInputProvider
|
||||
{
|
||||
private volatile bool _inputBlocked;
|
||||
|
||||
private readonly Channel<Action> _inputs = Channel.CreateUnbounded<Action>(new UnboundedChannelOptions { AllowSynchronousContinuations = false });
|
||||
|
||||
private readonly IScreenProvider _screenProvider;
|
||||
private readonly ILogger<WinInputProvider> _logger;
|
||||
|
||||
public WinInputProvider(IScreenProvider screenProvider, ILogger<WinInputProvider> logger)
|
||||
{
|
||||
_screenProvider = screenProvider;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly IScreenProvider _screenProvider = screenProvider;
|
||||
private readonly ILogger<WinInputProvider> _logger = logger;
|
||||
|
||||
public async Task InitAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
|
|
@ -31,10 +25,10 @@ internal class WinInputProvider : IInputProvider
|
|||
await Task.Delay(1000, cancellationToken);
|
||||
}
|
||||
}
|
||||
catch (TaskCanceledException) { }
|
||||
catch (OperationCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.ToString());
|
||||
_logger.LogError("{exception}", ex.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -68,7 +62,7 @@ internal class WinInputProvider : IInputProvider
|
|||
catch (OperationCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.Message);
|
||||
_logger.LogError("{exception}", ex.Message);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -83,10 +77,10 @@ internal class WinInputProvider : IInputProvider
|
|||
{
|
||||
await semaphore.WaitAsync(cancellationToken);
|
||||
}
|
||||
catch (TaskCanceledException) { }
|
||||
catch (OperationCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.ToString());
|
||||
_logger.LogError("{exception}", ex.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -110,13 +104,13 @@ internal class WinInputProvider : IInputProvider
|
|||
};
|
||||
|
||||
var input = new User32.INPUT() { type = User32.InputType.KEYBOARD, U = union };
|
||||
_ = User32.SendInput(1, new User32.INPUT[] { input }, User32.INPUT.Size);
|
||||
_ = User32.SendInput(1, [input], User32.INPUT.Size);
|
||||
}, cancellationToken);
|
||||
}
|
||||
catch (TaskCanceledException) { }
|
||||
catch (OperationCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.ToString());
|
||||
_logger.LogError("{exception}", ex.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -140,13 +134,13 @@ internal class WinInputProvider : IInputProvider
|
|||
}
|
||||
};
|
||||
var input = new User32.INPUT() { type = User32.InputType.KEYBOARD, U = union };
|
||||
_ = User32.SendInput(1, new User32.INPUT[] { input }, User32.INPUT.Size);
|
||||
_ = User32.SendInput(1, [input], User32.INPUT.Size);
|
||||
}, cancellationToken);
|
||||
}
|
||||
catch (TaskCanceledException) { }
|
||||
catch (OperationCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.ToString());
|
||||
_logger.LogError("{exception}", ex.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -209,13 +203,13 @@ internal class WinInputProvider : IInputProvider
|
|||
var normalizedY = xyPercent.Item2 * 65535D;
|
||||
var union = new User32.InputUnion() { mi = new User32.MOUSEINPUT() { dwFlags = User32.MOUSEEVENTF.ABSOLUTE | mouseEvent | User32.MOUSEEVENTF.VIRTUALDESK, dx = (int)normalizedX, dy = (int)normalizedY, time = 0, mouseData = 0, dwExtraInfo = User32.GetMessageExtraInfo() } };
|
||||
var input = new User32.INPUT() { type = User32.InputType.MOUSE, U = union };
|
||||
_ = User32.SendInput(1, new User32.INPUT[] { input }, User32.INPUT.Size);
|
||||
_ = User32.SendInput(1, [input], User32.INPUT.Size);
|
||||
}, cancellationToken);
|
||||
}
|
||||
catch (TaskCanceledException) { }
|
||||
catch (OperationCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.ToString());
|
||||
_logger.LogError("{exception}", ex.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -231,13 +225,13 @@ internal class WinInputProvider : IInputProvider
|
|||
var normalizedY = xyPercent.Item2 * 65535D;
|
||||
var union = new User32.InputUnion() { mi = new User32.MOUSEINPUT() { dwFlags = User32.MOUSEEVENTF.ABSOLUTE | User32.MOUSEEVENTF.MOVE | User32.MOUSEEVENTF.VIRTUALDESK, dx = (int)normalizedX, dy = (int)normalizedY, time = 0, mouseData = 0, dwExtraInfo = User32.GetMessageExtraInfo() } };
|
||||
var input = new User32.INPUT() { type = User32.InputType.MOUSE, U = union };
|
||||
_ = User32.SendInput(1, new User32.INPUT[] { input }, User32.INPUT.Size);
|
||||
_ = User32.SendInput(1, [input], User32.INPUT.Size);
|
||||
}, cancellationToken);
|
||||
}
|
||||
catch (TaskCanceledException) { }
|
||||
catch (OperationCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.ToString());
|
||||
_logger.LogError("{exception}", ex.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -257,13 +251,13 @@ internal class WinInputProvider : IInputProvider
|
|||
}
|
||||
var union = new User32.InputUnion() { mi = new User32.MOUSEINPUT() { dwFlags = User32.MOUSEEVENTF.WHEEL, dx = 0, dy = 0, time = 0, mouseData = deltaY, dwExtraInfo = User32.GetMessageExtraInfo() } };
|
||||
var input = new User32.INPUT() { type = User32.InputType.MOUSE, U = union };
|
||||
_ = User32.SendInput(1, new User32.INPUT[] { input }, User32.INPUT.Size);
|
||||
_ = User32.SendInput(1, [input], User32.INPUT.Size);
|
||||
}, cancellationToken);
|
||||
}
|
||||
catch (TaskCanceledException) { }
|
||||
catch (OperationCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.ToString());
|
||||
_logger.LogError("{exception}", ex.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -276,10 +270,10 @@ internal class WinInputProvider : IInputProvider
|
|||
SendKeys.SendWait(transferText);
|
||||
}, cancellationToken);
|
||||
}
|
||||
catch (TaskCanceledException) { }
|
||||
catch (OperationCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.ToString());
|
||||
_logger.LogError("{exception}", ex.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -308,7 +302,7 @@ internal class WinInputProvider : IInputProvider
|
|||
}
|
||||
};
|
||||
var input = new User32.INPUT() { type = User32.InputType.KEYBOARD, U = union };
|
||||
_ = User32.SendInput(1, new User32.INPUT[] { input }, User32.INPUT.Size);
|
||||
_ = User32.SendInput(1, [input], User32.INPUT.Size);
|
||||
}
|
||||
}
|
||||
catch { }
|
||||
|
|
@ -318,7 +312,7 @@ internal class WinInputProvider : IInputProvider
|
|||
catch (TaskCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.ToString());
|
||||
_logger.LogError("{exception}", ex.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -337,7 +331,7 @@ internal class WinInputProvider : IInputProvider
|
|||
catch (TaskCanceledException) { }
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex.ToString());
|
||||
_logger.LogError("{exception}", ex.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -37,11 +37,13 @@ using SkiaSharp.Views.Desktop;
|
|||
using System.Diagnostics.CodeAnalysis;
|
||||
using System.Drawing.Imaging;
|
||||
using System.Runtime.InteropServices;
|
||||
using System.Runtime.Versioning;
|
||||
using Vaitr.Bus;
|
||||
using Result = RemoteControl.Shared.Result;
|
||||
|
||||
namespace Insight.Remote.Windows.Services;
|
||||
|
||||
[SupportedOSPlatform("windows")]
|
||||
internal class WinScreenCapturer : IScreenProvider
|
||||
{
|
||||
public event EventHandler<Rectangle>? ScreenChanged;
|
||||
|
|
@ -72,8 +74,8 @@ internal class WinScreenCapturer : IScreenProvider
|
|||
private bool _initialized;
|
||||
|
||||
private readonly SemaphoreSlim _semaphore = new(1, 1);
|
||||
private readonly Dictionary<string, int> _bitBltScreens = new();
|
||||
private readonly Dictionary<string, DirectXOutput> _directxScreens = new();
|
||||
private readonly Dictionary<string, int> _bitBltScreens = [];
|
||||
private readonly Dictionary<string, DirectXOutput> _directxScreens = [];
|
||||
|
||||
private readonly Bus _bus;
|
||||
private readonly ILogger<WinScreenCapturer> _logger;
|
||||
|
|
@ -86,7 +88,7 @@ internal class WinScreenCapturer : IScreenProvider
|
|||
SystemEvents.DisplaySettingsChanged += SystemEvents_DisplaySettingsChanged;
|
||||
}
|
||||
|
||||
public async Task InitAsync(CancellationToken cancellationToken)
|
||||
public Task InitAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
Win32Interop.SwitchToInputDesktop();
|
||||
|
||||
|
|
@ -94,6 +96,8 @@ internal class WinScreenCapturer : IScreenProvider
|
|||
InitDirectX();
|
||||
|
||||
_initialized = true;
|
||||
|
||||
return Task.CompletedTask;
|
||||
}
|
||||
|
||||
public void SetSelectedScreen(string displayName)
|
||||
|
|
|
|||
|
|
@ -2,9 +2,7 @@
|
|||
using Insight.Remote.Shared.Messages;
|
||||
using Insight.Remote.Shared.Native.Windows;
|
||||
using Insight.Remote.Shared.Reactive;
|
||||
using Insight.Remote.Shared.Services;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Diagnostics;
|
||||
using System.Security.Principal;
|
||||
using Vaitr.Bus;
|
||||
|
|
@ -28,7 +26,7 @@ public class MainViewModel : ViewModelBase
|
|||
|
||||
private string? _lastId;
|
||||
|
||||
private readonly List<IDisposable> _subscriptions = new();
|
||||
private readonly List<IDisposable> _subscriptions = [];
|
||||
|
||||
private readonly Bus _bus;
|
||||
private readonly IDispatcher _dispatcher;
|
||||
|
|
@ -152,6 +150,6 @@ public class FakeMainViewModel : ViewModelBase
|
|||
public RelayCommand ElevateToAdminCommand { get; } = new(() => { });
|
||||
public RelayCommand ElevateToServiceCommand { get; } = new(() => { });
|
||||
|
||||
public bool IsAdministrator => false;
|
||||
public static bool IsAdministrator => false;
|
||||
public string StatusMessage { get; set; } = "test";
|
||||
}
|
||||
|
|
@ -25,7 +25,7 @@ public partial class MainWindow : Window
|
|||
private void Window_Loaded(object sender, RoutedEventArgs e)
|
||||
{
|
||||
if (DesignerProperties.GetIsInDesignMode(this)) return;
|
||||
if (DataContext is not MainViewModel vm) return;
|
||||
if (DataContext is not MainViewModel) return;
|
||||
}
|
||||
|
||||
private void Window_Closing(object sender, CancelEventArgs e)
|
||||
|
|
|
|||
|
|
@ -8,7 +8,7 @@ public static class Async
|
|||
this IAsyncEnumerable<T> source,
|
||||
Func<T, Task> body,
|
||||
int maxDegreeOfParallelism = DataflowBlockOptions.Unbounded,
|
||||
TaskScheduler scheduler = null)
|
||||
TaskScheduler? scheduler = null)
|
||||
{
|
||||
var options = new ExecutionDataflowBlockOptions
|
||||
{
|
||||
|
|
@ -31,7 +31,7 @@ public static class Async
|
|||
this IEnumerable<T> source,
|
||||
Func<T, Task> body,
|
||||
int maxDegreeOfParallelism = DataflowBlockOptions.Unbounded,
|
||||
TaskScheduler scheduler = null)
|
||||
TaskScheduler? scheduler = null)
|
||||
{
|
||||
var options = new ExecutionDataflowBlockOptions
|
||||
{
|
||||
|
|
|
|||
|
|
@ -2,13 +2,15 @@
|
|||
|
||||
<PropertyGroup>
|
||||
<OutputType>Exe</OutputType>
|
||||
<TargetFramework>net7.0</TargetFramework>
|
||||
<TargetFramework>net8.0</TargetFramework>
|
||||
<LangVersion>latest</LangVersion>
|
||||
<Product>Insight</Product>
|
||||
<AssemblyName>server</AssemblyName>
|
||||
<AssemblyVersion>2023.12.14.0</AssemblyVersion>
|
||||
<RootNamespace>Insight.Server</RootNamespace>
|
||||
<ImplicitUsings>enable</ImplicitUsings>
|
||||
<Nullable>enable</Nullable>
|
||||
<SatelliteResourceLanguages>none</SatelliteResourceLanguages>
|
||||
</PropertyGroup>
|
||||
|
||||
<PropertyGroup Condition="'$(Configuration)|$(Platform)'=='Debug|AnyCPU'">
|
||||
|
|
@ -38,8 +40,8 @@
|
|||
</ItemGroup>
|
||||
|
||||
<ItemGroup>
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.Systemd" Version="7.0.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="7.0.1" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.Systemd" Version="8.0.0" />
|
||||
<PackageReference Include="Microsoft.Extensions.Hosting.WindowsServices" Version="8.0.0" />
|
||||
<PackageReference Include="Serilog.Extensions.Logging.File" Version="3.0.0" />
|
||||
<!--Unix Serilog stuff-->
|
||||
</ItemGroup>
|
||||
|
|
|
|||
|
|
@ -7,18 +7,16 @@ using Vaitr.Network;
|
|||
|
||||
namespace Insight.Server.Network.Agent;
|
||||
|
||||
public class AgentSession : TcpSession<IMessage>
|
||||
public class AgentSession(
|
||||
AgentHandler agentHandler,
|
||||
IEnumerable<IMessageHandler<AgentSession>> handlers,
|
||||
ISerializer<IMessage> serializer,
|
||||
ILogger<AgentSession> logger) : TcpSession<IMessage>(serializer, logger)
|
||||
{
|
||||
public string? Id { get; set; }
|
||||
|
||||
private readonly AgentHandler _agentHandler;
|
||||
private readonly IEnumerable<IMessageHandler<AgentSession>> _handlers;
|
||||
|
||||
public AgentSession(AgentHandler agentHandler, IEnumerable<IMessageHandler<AgentSession>> handlers, ISerializer<IMessage> serializer, ILogger<AgentSession> logger) : base(serializer, logger)
|
||||
{
|
||||
_agentHandler = agentHandler;
|
||||
_handlers = handlers;
|
||||
}
|
||||
private readonly AgentHandler _agentHandler = agentHandler;
|
||||
private readonly IEnumerable<IMessageHandler<AgentSession>> _handlers = handlers;
|
||||
|
||||
protected override async ValueTask OnConnectedAsync(CancellationToken cancellationToken)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -8,16 +8,10 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class AgentHandler : IMessageHandler<AgentSession>
|
||||
public class AgentHandler(IMongoDatabase database, ILogger<AgentHandler> logger) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
private readonly ILogger<AgentHandler> _logger;
|
||||
|
||||
public AgentHandler(IMongoDatabase database, ILogger<AgentHandler> logger)
|
||||
{
|
||||
_database = database;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
private readonly ILogger<AgentHandler> _logger = logger;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
|
|||
|
|
@ -5,14 +5,9 @@ using Microsoft.Extensions.Logging;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class CustomHandler : IMessageHandler<AgentSession>
|
||||
public class CustomHandler(ILogger<CustomHandler> logger) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly ILogger<CustomHandler> _logger;
|
||||
|
||||
public CustomHandler(ILogger<CustomHandler> logger)
|
||||
{
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly ILogger<CustomHandler> _logger = logger;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -24,8 +19,9 @@ public class CustomHandler : IMessageHandler<AgentSession>
|
|||
}
|
||||
}
|
||||
|
||||
private async ValueTask OnResponseAsync(AgentSession sender, Response response, CancellationToken cancellationToken)
|
||||
private ValueTask OnResponseAsync(AgentSession sender, Response response, CancellationToken cancellationToken)
|
||||
{
|
||||
_logger.LogWarning($"Response: {response.ResponseData}");
|
||||
_logger.LogWarning("Response: {response}", response.ResponseData);
|
||||
return default;
|
||||
}
|
||||
}
|
||||
|
|
@ -7,14 +7,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class DriveHandler : IMessageHandler<AgentSession>
|
||||
public class DriveHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public DriveHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -39,7 +34,7 @@ public class DriveHandler : IMessageHandler<AgentSession>
|
|||
|
||||
var driveBulk = new List<WriteModel<HostDriveEntity>>();
|
||||
|
||||
if (drives is not null && drives.Any())
|
||||
if (drives is not null && drives.Count != 0)
|
||||
{
|
||||
foreach (var drive in drives)
|
||||
{
|
||||
|
|
@ -83,16 +78,16 @@ public class DriveHandler : IMessageHandler<AgentSession>
|
|||
|
||||
var volumeBulk = new List<WriteModel<HostVolumeEntity>>();
|
||||
|
||||
if (drives is not null && drives.Any())
|
||||
if (drives is not null && drives.Count != 0)
|
||||
{
|
||||
foreach (var drive in drives)
|
||||
{
|
||||
var driveId = await _database.HostDrive()
|
||||
.Find(p => p.Host == hostEntity.Id && p.Index == drive.Index)
|
||||
.Project(p => p.Id)
|
||||
.FirstOrDefaultAsync();
|
||||
.FirstOrDefaultAsync(cancellationToken: default);
|
||||
|
||||
if (drive.Volumes is not null && drive.Volumes.Any())
|
||||
if (drive.Volumes is not null && drive.Volumes.Count != 0)
|
||||
{
|
||||
foreach (var volume in drive.Volumes)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -3,22 +3,14 @@ using Insight.Domain.Interfaces;
|
|||
using Insight.Domain.Network;
|
||||
using Insight.Domain.Network.Agent.Messages;
|
||||
using Insight.Infrastructure.Entities;
|
||||
using Microsoft.Extensions.Logging;
|
||||
using MongoDB.Driver;
|
||||
using static Insight.Domain.Network.Agent.Messages.Event;
|
||||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class EventHandler : IMessageHandler<AgentSession>
|
||||
public class EventHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
private readonly ILogger<EventHandler> _logger;
|
||||
|
||||
public EventHandler(IMongoDatabase database, ILogger<EventHandler> logger)
|
||||
{
|
||||
_database = database;
|
||||
_logger = logger;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -75,13 +67,13 @@ public class EventHandler : IMessageHandler<AgentSession>
|
|||
_ => null
|
||||
};
|
||||
|
||||
CategoryEnum? category = @event.Category.ToLower() switch
|
||||
CategoryEnum? category = @event.Category?.ToLower() switch
|
||||
{
|
||||
"network" => CategoryEnum.Network,
|
||||
"application" => CategoryEnum.Application,
|
||||
"security" => CategoryEnum.Security,
|
||||
"system" => CategoryEnum.System,
|
||||
_ => null
|
||||
_ => CategoryEnum.None
|
||||
};
|
||||
|
||||
var date = DateTime.Now;
|
||||
|
|
@ -114,55 +106,59 @@ public class EventHandler : IMessageHandler<AgentSession>
|
|||
_ => null
|
||||
};
|
||||
|
||||
CategoryEnum? category = null;
|
||||
switch (@event.Category)
|
||||
var category = CategoryEnum.None;
|
||||
|
||||
if (@event.Category is not null)
|
||||
{
|
||||
case var _ when @event.Category.Contains("network", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Network;
|
||||
break;
|
||||
switch (@event.Category)
|
||||
{
|
||||
case var _ when @event.Category.Contains("network", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Network;
|
||||
break;
|
||||
|
||||
case var _ when @event.Category.Contains("application", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Application;
|
||||
break;
|
||||
case var _ when @event.Category.Contains("application", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Application;
|
||||
break;
|
||||
|
||||
case var _ when @event.Category.Contains("security", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Security;
|
||||
break;
|
||||
case var _ when @event.Category.Contains("security", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Security;
|
||||
break;
|
||||
|
||||
case var _ when @event.Category.Contains("system", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.System;
|
||||
break;
|
||||
case var _ when @event.Category.Contains("system", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.System;
|
||||
break;
|
||||
|
||||
case var _ when @event.Category.Contains("printservice", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Printer;
|
||||
break;
|
||||
case var _ when @event.Category.Contains("printservice", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Printer;
|
||||
break;
|
||||
|
||||
case var _ when @event.Category.Contains("taskscheduler", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Task;
|
||||
break;
|
||||
case var _ when @event.Category.Contains("taskscheduler", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Task;
|
||||
break;
|
||||
|
||||
case var _ when @event.Category.Contains("terminalservices", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.RDP;
|
||||
break;
|
||||
case var _ when @event.Category.Contains("terminalservices", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.RDP;
|
||||
break;
|
||||
|
||||
case var _ when @event.Category.Contains("smbclient", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Network;
|
||||
break;
|
||||
case var _ when @event.Category.Contains("smbclient", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Network;
|
||||
break;
|
||||
|
||||
case var _ when @event.Category.Contains("smbserver", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Network;
|
||||
break;
|
||||
case var _ when @event.Category.Contains("smbserver", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.Network;
|
||||
break;
|
||||
|
||||
case var _ when @event.Category.Contains("storagespaces", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.System;
|
||||
break;
|
||||
case var _ when @event.Category.Contains("storagespaces", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.System;
|
||||
break;
|
||||
|
||||
case var _ when @event.Category.Contains("diagnostics", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.System;
|
||||
break;
|
||||
case var _ when @event.Category.Contains("diagnostics", StringComparison.InvariantCultureIgnoreCase):
|
||||
category = CategoryEnum.System;
|
||||
break;
|
||||
|
||||
default:
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
var date = DateTime.Now;
|
||||
|
|
@ -175,7 +171,7 @@ public class EventHandler : IMessageHandler<AgentSession>
|
|||
EventId = @event.EventId.ToString(),
|
||||
Status = status.ToString(),
|
||||
Source = @event.Source,
|
||||
Category = category?.ToString(),
|
||||
Category = category.ToString(),
|
||||
Message = @event.Message
|
||||
};
|
||||
|
||||
|
|
@ -183,7 +179,7 @@ public class EventHandler : IMessageHandler<AgentSession>
|
|||
return log;
|
||||
}
|
||||
|
||||
private bool FilterEventId(Event @event)
|
||||
private static bool FilterEventId(Event @event)
|
||||
{
|
||||
var filter = new List<int>
|
||||
{
|
||||
|
|
@ -234,10 +230,8 @@ public class EventHandler : IMessageHandler<AgentSession>
|
|||
return false;
|
||||
}
|
||||
|
||||
private bool FilterMonitoringHostLog(HostLogEntity hostLog)
|
||||
private static bool FilterMonitoringHostLog(HostLogEntity hostLog)
|
||||
{
|
||||
//_logger.LogDebug($"try filter event: {hostLog.Category}.{hostLog.Source}.{hostLog.Status}");
|
||||
|
||||
if (Enum.TryParse(hostLog.Status, out StatusType status) is false) return true;
|
||||
|
||||
if (hostLog.Category == CategoryEnum.System.ToString())
|
||||
|
|
|
|||
|
|
@ -7,14 +7,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class InterfaceHandler : IMessageHandler<AgentSession>
|
||||
public class InterfaceHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public InterfaceHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -39,7 +34,7 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
|
||||
// interfaces
|
||||
|
||||
if (interfaces is not null && interfaces.Any())
|
||||
if (interfaces is not null && interfaces.Count != 0)
|
||||
{
|
||||
var interfaceBulk = new List<WriteModel<HostInterfaceEntity>>();
|
||||
|
||||
|
|
@ -95,7 +90,7 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
|
||||
// addresses
|
||||
|
||||
if (interfaces is not null && interfaces.Any())
|
||||
if (interfaces is not null && interfaces.Count != 0)
|
||||
{
|
||||
var addressBulk = new List<WriteModel<HostInterfaceAddressEntity>>();
|
||||
|
||||
|
|
@ -104,9 +99,9 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
var interfaceId = await _database.HostInterface()
|
||||
.Find(p => p.Host == hostEntity.Id && p.Index == @interface.Index)
|
||||
.Project(p => p.Id)
|
||||
.FirstOrDefaultAsync();
|
||||
.FirstOrDefaultAsync(cancellationToken: default);
|
||||
|
||||
if (@interface.Addresses is not null && @interface.Addresses.Any())
|
||||
if (@interface.Addresses is not null && @interface.Addresses.Count != 0)
|
||||
{
|
||||
foreach (var address in @interface.Addresses)
|
||||
{
|
||||
|
|
@ -146,7 +141,7 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
|
||||
// gateways
|
||||
|
||||
if (interfaces is not null && interfaces.Any())
|
||||
if (interfaces is not null && interfaces.Count != 0)
|
||||
{
|
||||
var gatewayBulk = new List<WriteModel<HostInterfaceGatewayEntity>>();
|
||||
|
||||
|
|
@ -155,9 +150,9 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
var interfaceId = await _database.HostInterface()
|
||||
.Find(p => p.Host == hostEntity.Id && p.Index == @interface.Index)
|
||||
.Project(p => p.Id)
|
||||
.FirstOrDefaultAsync();
|
||||
.FirstOrDefaultAsync(cancellationToken: default);
|
||||
|
||||
if (@interface.Gateways is not null && @interface.Gateways.Any())
|
||||
if (@interface.Gateways is not null && @interface.Gateways.Count != 0)
|
||||
{
|
||||
foreach (var gateway in @interface.Gateways)
|
||||
{
|
||||
|
|
@ -195,7 +190,7 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
|
||||
// nameservers
|
||||
|
||||
if (interfaces is not null && interfaces.Any())
|
||||
if (interfaces is not null && interfaces.Count != 0)
|
||||
{
|
||||
var nameserverBulk = new List<WriteModel<HostInterfaceNameserverEntity>>();
|
||||
|
||||
|
|
@ -204,9 +199,9 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
var interfaceId = await _database.HostInterface()
|
||||
.Find(p => p.Host == hostEntity.Id && p.Index == @interface.Index)
|
||||
.Project(p => p.Id)
|
||||
.FirstOrDefaultAsync();
|
||||
.FirstOrDefaultAsync(cancellationToken: default);
|
||||
|
||||
if (@interface.Dns is not null && @interface.Dns.Any())
|
||||
if (@interface.Dns is not null && @interface.Dns.Count != 0)
|
||||
{
|
||||
foreach (var nameserver in @interface.Dns)
|
||||
{
|
||||
|
|
@ -244,7 +239,7 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
|
||||
// routes
|
||||
|
||||
if (interfaces is not null && interfaces.Any())
|
||||
if (interfaces is not null && interfaces.Count != 0)
|
||||
{
|
||||
var routeBulk = new List<WriteModel<HostInterfaceRouteEntity>>();
|
||||
|
||||
|
|
@ -253,9 +248,9 @@ public class InterfaceHandler : IMessageHandler<AgentSession>
|
|||
var interfaceId = await _database.HostInterface()
|
||||
.Find(p => p.Host == hostEntity.Id && p.Index == @interface.Index)
|
||||
.Project(p => p.Id)
|
||||
.FirstOrDefaultAsync();
|
||||
.FirstOrDefaultAsync(cancellationToken: default);
|
||||
|
||||
if (@interface.Routes is not null && @interface.Routes.Any())
|
||||
if (@interface.Routes is not null && @interface.Routes.Count != 0)
|
||||
{
|
||||
foreach (var route in @interface.Routes)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -6,14 +6,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers
|
||||
{
|
||||
public class MainboardHandler : IMessageHandler<AgentSession>
|
||||
public class MainboardHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public MainboardHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
|
|||
|
|
@ -7,14 +7,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class MemoryHandler : IMessageHandler<AgentSession>
|
||||
public class MemoryHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public MemoryHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -39,7 +34,7 @@ public class MemoryHandler : IMessageHandler<AgentSession>
|
|||
|
||||
var bulk = new List<WriteModel<HostMemoryEntity>>();
|
||||
|
||||
if (memory is not null && memory.Any())
|
||||
if (memory is not null && memory.Count != 0)
|
||||
{
|
||||
foreach (var mem in memory)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -6,14 +6,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class OperationSystemHandler : IMessageHandler<AgentSession>
|
||||
public class OperationSystemHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public OperationSystemHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
|
|||
|
|
@ -7,14 +7,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class PrinterHandler : IMessageHandler<AgentSession>
|
||||
public class PrinterHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public PrinterHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -39,7 +34,7 @@ public class PrinterHandler : IMessageHandler<AgentSession>
|
|||
|
||||
var bulk = new List<WriteModel<HostPrinterEntity>>();
|
||||
|
||||
if (printers is not null && printers.Any())
|
||||
if (printers is not null && printers.Count != 0)
|
||||
{
|
||||
foreach (var printer in printers)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -7,14 +7,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class ProcessorHandler : IMessageHandler<AgentSession>
|
||||
public class ProcessorHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public ProcessorHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -39,7 +34,7 @@ public class ProcessorHandler : IMessageHandler<AgentSession>
|
|||
|
||||
var bulk = new List<WriteModel<HostProcessorEntity>>();
|
||||
|
||||
if (processors is not null && processors.Any())
|
||||
if (processors is not null && processors.Count != 0)
|
||||
{
|
||||
foreach (var processor in processors)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -7,14 +7,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class ServiceHandler : IMessageHandler<AgentSession>
|
||||
public class ServiceHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public ServiceHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -39,7 +34,7 @@ public class ServiceHandler : IMessageHandler<AgentSession>
|
|||
|
||||
var bulk = new List<WriteModel<HostServiceEntity>>();
|
||||
|
||||
if (services is not null && services.Any())
|
||||
if (services is not null && services.Count != 0)
|
||||
{
|
||||
foreach (var service in services)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -7,14 +7,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class SessionHandler : IMessageHandler<AgentSession>
|
||||
public class SessionHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public SessionHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -39,7 +34,7 @@ public class SessionHandler : IMessageHandler<AgentSession>
|
|||
|
||||
var bulk = new List<WriteModel<HostSessionEntity>>();
|
||||
|
||||
if (sessions is not null && sessions.Any())
|
||||
if (sessions is not null && sessions.Count != 0)
|
||||
{
|
||||
foreach (var sess in sessions)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -7,14 +7,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class SoftwareHandler : IMessageHandler<AgentSession>
|
||||
public class SoftwareHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public SoftwareHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -39,7 +34,7 @@ public class SoftwareHandler : IMessageHandler<AgentSession>
|
|||
|
||||
var bulk = new List<WriteModel<HostApplicationEntity>>();
|
||||
|
||||
if (applications is not null && applications.Any())
|
||||
if (applications is not null && applications.Count != 0)
|
||||
{
|
||||
foreach (var app in applications)
|
||||
{
|
||||
|
|
|
|||
|
|
@ -7,14 +7,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class StoragePoolHandler : IMessageHandler<AgentSession>
|
||||
public class StoragePoolHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public StoragePoolHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -39,7 +34,7 @@ public class StoragePoolHandler : IMessageHandler<AgentSession>
|
|||
|
||||
// storagepools
|
||||
|
||||
if (storagePools is not null && storagePools.Any())
|
||||
if (storagePools is not null && storagePools.Count != 0)
|
||||
{
|
||||
var storagepoolBulk = new List<WriteModel<HostStoragePoolEntity>>();
|
||||
|
||||
|
|
@ -55,12 +50,10 @@ public class StoragePoolHandler : IMessageHandler<AgentSession>
|
|||
|
||||
if (storagePool.States is not null)
|
||||
{
|
||||
states = new List<string>();
|
||||
states = [];
|
||||
|
||||
foreach (var state in storagePool.States)
|
||||
{
|
||||
states.Add(state.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
var storagePoolUpdate = Builders<HostStoragePoolEntity>.Update
|
||||
|
|
@ -98,7 +91,7 @@ public class StoragePoolHandler : IMessageHandler<AgentSession>
|
|||
|
||||
// physicaldisks
|
||||
|
||||
if (storagePools is not null && storagePools.Any())
|
||||
if (storagePools is not null && storagePools.Count != 0)
|
||||
{
|
||||
var physicalDiskBulk = new List<WriteModel<HostStoragePoolPhysicalDiskEntity>>();
|
||||
|
||||
|
|
@ -107,9 +100,9 @@ public class StoragePoolHandler : IMessageHandler<AgentSession>
|
|||
var storagePoolId = await _database.HostStoragePool()
|
||||
.Find(p => p.Host == hostEntity.Id && p.UniqueId == storagePool.UniqueId)
|
||||
.Project(p => p.Id)
|
||||
.FirstOrDefaultAsync();
|
||||
.FirstOrDefaultAsync(cancellationToken: default);
|
||||
|
||||
if (storagePool.PhysicalDisks is not null && storagePool.PhysicalDisks.Any())
|
||||
if (storagePool.PhysicalDisks is not null && storagePool.PhysicalDisks.Count != 0)
|
||||
{
|
||||
foreach (var physicalDisk in storagePool.PhysicalDisks)
|
||||
{
|
||||
|
|
@ -124,12 +117,10 @@ public class StoragePoolHandler : IMessageHandler<AgentSession>
|
|||
|
||||
if (physicalDisk.States is not null)
|
||||
{
|
||||
states = new List<string>();
|
||||
states = [];
|
||||
|
||||
foreach (var state in physicalDisk.States)
|
||||
{
|
||||
states.Add(state.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
var physicalDiskUpdate = Builders<HostStoragePoolPhysicalDiskEntity>.Update
|
||||
|
|
@ -177,20 +168,20 @@ public class StoragePoolHandler : IMessageHandler<AgentSession>
|
|||
|
||||
// virtual disks
|
||||
|
||||
if (storagePools is not null && storagePools.Any())
|
||||
if (storagePools is not null && storagePools.Count != 0)
|
||||
{
|
||||
var virtualDiskBulk = new List<WriteModel<HostStoragePoolVirtualDiskEntity>>();
|
||||
|
||||
foreach (var storagePool in storagePools)
|
||||
{
|
||||
if (storagePool.VirtualDisks is not null && storagePool.VirtualDisks.Any())
|
||||
if (storagePool.VirtualDisks is not null && storagePool.VirtualDisks.Count != 0)
|
||||
{
|
||||
foreach (var virtualDisk in storagePool.VirtualDisks)
|
||||
{
|
||||
var storagePoolId = await _database.HostStoragePool()
|
||||
.Find(p => p.Host == hostEntity.Id && p.UniqueId == storagePool.UniqueId)
|
||||
.Project(p => p.Id)
|
||||
.FirstOrDefaultAsync();
|
||||
.FirstOrDefaultAsync(cancellationToken: default);
|
||||
|
||||
var virtualDiskFilter = Builders<HostStoragePoolVirtualDiskEntity>.Filter.And(new List<FilterDefinition<HostStoragePoolVirtualDiskEntity>>
|
||||
{
|
||||
|
|
@ -203,12 +194,10 @@ public class StoragePoolHandler : IMessageHandler<AgentSession>
|
|||
|
||||
if (virtualDisk.States is not null)
|
||||
{
|
||||
states = new List<string>();
|
||||
states = [];
|
||||
|
||||
foreach (var state in virtualDisk.States)
|
||||
{
|
||||
states.Add(state.ToString());
|
||||
}
|
||||
}
|
||||
|
||||
var virtualDiskUpdate = Builders<HostStoragePoolVirtualDiskEntity>.Update
|
||||
|
|
|
|||
|
|
@ -6,14 +6,9 @@ using MongoDB.Driver;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class SystemInfoHandler : IMessageHandler<AgentSession>
|
||||
public class SystemInfoHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public SystemInfoHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -27,22 +22,24 @@ public class SystemInfoHandler : IMessageHandler<AgentSession>
|
|||
|
||||
private async ValueTask OnSystemInfoAsync(AgentSession session, SystemInfo? system, CancellationToken cancellationToken)
|
||||
{
|
||||
var agentEntity = await _database.Agent().Find(Builders<AgentEntity>.Filter.Eq(p => p.Id, session.Id)).FirstOrDefaultAsync(cancellationToken);
|
||||
var agentEntity = await _database.Agent().Find(Builders<AgentEntity>.Filter.Eq(p => p.Id, session?.Id)).FirstOrDefaultAsync(cancellationToken);
|
||||
if (agentEntity is null) return;
|
||||
|
||||
var hostEntity = await _database.Host().Find(Builders<HostEntity>.Filter.Eq(p => p.Agent, agentEntity.Id)).FirstOrDefaultAsync(cancellationToken);
|
||||
var hostEntity = await _database.Host().Find(Builders<HostEntity>.Filter.Eq(p => p.Agent, agentEntity?.Id)).FirstOrDefaultAsync(cancellationToken);
|
||||
if (hostEntity is null) return;
|
||||
|
||||
var date = DateTime.Now;
|
||||
|
||||
if (hostEntity.Id is null) return;
|
||||
|
||||
await _database.HostSystem().UpdateOneAsync(p => p.Host == hostEntity.Id, Builders<HostSystemEntity>.Update
|
||||
.SetOnInsert(p => p.Insert, date)
|
||||
.SetOnInsert(p => p.Host, hostEntity.Id)
|
||||
.Set(p => p.Update, date)
|
||||
.Set(p => p.BootUpTime, system.LastBootUpTime)
|
||||
.Set(p => p.LocalTime, system.LocalDateTime)
|
||||
.Set(p => p.Processes, system.Processes)
|
||||
.Set(p => p.License, system.License), new UpdateOptions
|
||||
.Set(p => p.BootUpTime, system?.LastBootUpTime)
|
||||
.Set(p => p.LocalTime, system?.LocalDateTime)
|
||||
.Set(p => p.Processes, system?.Processes)
|
||||
.Set(p => p.License, system?.License), new UpdateOptions
|
||||
{
|
||||
IsUpsert = true
|
||||
}, cancellationToken);
|
||||
|
|
|
|||
|
|
@ -11,14 +11,9 @@ using static Insight.Server.Models.MonitorMessage;
|
|||
|
||||
namespace Insight.Server.Network.Agent.Handlers;
|
||||
|
||||
public class TrapHandler : IMessageHandler<AgentSession>
|
||||
public partial class TrapHandler(IMongoDatabase database) : IMessageHandler<AgentSession>
|
||||
{
|
||||
private readonly IMongoDatabase _database;
|
||||
|
||||
public TrapHandler(IMongoDatabase database)
|
||||
{
|
||||
_database = database;
|
||||
}
|
||||
private readonly IMongoDatabase _database = database;
|
||||
|
||||
public async ValueTask HandleAsync<TMessage>(AgentSession sender, TMessage message, CancellationToken cancellationToken) where TMessage : IMessage
|
||||
{
|
||||
|
|
@ -85,7 +80,8 @@ public class TrapHandler : IMessageHandler<AgentSession>
|
|||
{
|
||||
monitoring = null;
|
||||
|
||||
if (packet is null || packet.Data is null || packet.Data.Any() is false) return false;
|
||||
if (packet is null || packet.Data is null || packet.Data.Count == 0)
|
||||
return false;
|
||||
|
||||
monitoring = new MonitorMessage
|
||||
{
|
||||
|
|
@ -96,9 +92,7 @@ public class TrapHandler : IMessageHandler<AgentSession>
|
|||
};
|
||||
|
||||
if (Enum.TryParse<ApplicationEnum>(packet.Community, true, out var application))
|
||||
{
|
||||
monitoring.Application = application;
|
||||
}
|
||||
|
||||
StatusEnum? status;
|
||||
string? task;
|
||||
|
|
@ -131,9 +125,12 @@ public class TrapHandler : IMessageHandler<AgentSession>
|
|||
return true;
|
||||
}
|
||||
|
||||
private static bool ParseAcronis(List<KeyValuePair<string, string>> data, out StatusEnum? status, out string? task, out string? message)
|
||||
[GeneratedRegex(@"\s+")]
|
||||
private static partial Regex AcronisRegex();
|
||||
|
||||
private static bool ParseAcronis(List<KeyValuePair<string, string?>> data, out StatusEnum? status, out string? task, out string? message)
|
||||
{
|
||||
status = data[0].Value.ToLower() switch
|
||||
status = data[0].Value?.ToLower() switch
|
||||
{
|
||||
"erfolgreich" => StatusEnum.Information,
|
||||
"success" => StatusEnum.Information,
|
||||
|
|
@ -149,49 +146,32 @@ public class TrapHandler : IMessageHandler<AgentSession>
|
|||
task = null;
|
||||
message = null;
|
||||
|
||||
var parsed = false;
|
||||
var trim = data[1].Value?.Split(':', StringSplitOptions.None);
|
||||
if (trim is null || trim.Length == 0) return false;
|
||||
|
||||
try
|
||||
{
|
||||
var trim = data[1].Value.Split(new string[] { ":" }, StringSplitOptions.None);
|
||||
task = trim[1].Split(new string[] { "'" }, StringSplitOptions.None)[1].Split("'")[0].Trim();
|
||||
message = trim[1].Split(new string[] { "' " }, StringSplitOptions.None)[1].Trim();
|
||||
task = trim[1].Split("'", StringSplitOptions.None)[1].Split("'")[0].Trim();
|
||||
message = trim[1].Split("' ", StringSplitOptions.None)[1].Trim();
|
||||
if (message is not null) return true;
|
||||
|
||||
parsed = true;
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
// skipped for base64 parse
|
||||
}
|
||||
if (data[1].Value is not string val) return false;
|
||||
|
||||
if (parsed) return true;
|
||||
var content = AcronisRegex().Replace(val, "");
|
||||
var bytes = Enumerable.Range(0, content.Length)
|
||||
.Where(x => x % 2 == 0)
|
||||
.Select(x => Convert.ToByte(content.Substring(x, 2), 16))
|
||||
.ToArray();
|
||||
|
||||
try
|
||||
{
|
||||
var content = Regex.Replace(data[1].Value, @"\s+", "");
|
||||
var bytes = Enumerable.Range(0, content.Length)
|
||||
.Where(x => x % 2 == 0)
|
||||
.Select(x => Convert.ToByte(content.Substring(x, 2), 16))
|
||||
.ToArray();
|
||||
content = Encoding.UTF8.GetString(bytes);
|
||||
|
||||
content = Encoding.UTF8.GetString(bytes);
|
||||
trim = content.Split(':', StringSplitOptions.None);
|
||||
if (trim is null || trim.Length == 0) return false;
|
||||
|
||||
var trim = content.Split(new string[] { ":" }, StringSplitOptions.None);
|
||||
task = trim[1].Split(new string[] { "'" }, StringSplitOptions.None)[1].Split("'")[0].Trim();
|
||||
message = trim[1].Split(new string[] { "' " }, StringSplitOptions.None)[1].Trim();
|
||||
|
||||
parsed = true;
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
//_logger.LogError("{ex}", ex);
|
||||
}
|
||||
|
||||
if (parsed) return true;
|
||||
return false;
|
||||
task = trim[1].Split("'", StringSplitOptions.None)[1].Split("'")[0].Trim();
|
||||
message = trim[1].Split("' ", StringSplitOptions.None)[1].Trim();
|
||||
return message is not null;
|
||||
}
|
||||
|
||||
private static bool ParseVeeam(List<KeyValuePair<string, string>> data, out StatusEnum? status, out string? task, out string? message)
|
||||
private static bool ParseVeeam(List<KeyValuePair<string, string?>> data, out StatusEnum? status, out string? task, out string? message)
|
||||
{
|
||||
status = null;
|
||||
task = null;
|
||||
|
|
@ -206,10 +186,10 @@ public class TrapHandler : IMessageHandler<AgentSession>
|
|||
if (Guid.TryParse(data[0].Value, out _))
|
||||
summary = true;
|
||||
|
||||
if (data[1].Value.ToLower() == "backup configuration job")
|
||||
if (data[1].Value?.ToLower() == "backup configuration job")
|
||||
return false;
|
||||
|
||||
status = (summary ? data[2].Value.ToLower() : data[3].Value.ToLower()) switch
|
||||
status = (summary ? data[2].Value?.ToLower() : data[3].Value?.ToLower()) switch
|
||||
{
|
||||
"success" => StatusEnum.Information,
|
||||
"warning" => StatusEnum.Warning,
|
||||
|
|
@ -230,7 +210,7 @@ public class TrapHandler : IMessageHandler<AgentSession>
|
|||
return false;
|
||||
}
|
||||
|
||||
private static bool ParseQnap(List<KeyValuePair<string, string>> data, out StatusEnum? status, out string? task, out string? message)
|
||||
private static bool ParseQnap(List<KeyValuePair<string, string?>> data, out StatusEnum? status, out string? task, out string? message)
|
||||
{
|
||||
status = StatusEnum.Information;
|
||||
task = null;
|
||||
|
|
@ -265,21 +245,15 @@ public class TrapHandler : IMessageHandler<AgentSession>
|
|||
};
|
||||
|
||||
foreach (var key in keywords)
|
||||
{
|
||||
if (Regex.IsMatch(string.Concat(data).ToLowerInvariant(), $@"\b{key.Key}\b"))
|
||||
{
|
||||
status = key.Value;
|
||||
}
|
||||
}
|
||||
|
||||
foreach (var kv in data)
|
||||
{
|
||||
message += kv.Value;
|
||||
}
|
||||
|
||||
parsed = true;
|
||||
}
|
||||
catch (Exception ex)
|
||||
catch (Exception)
|
||||
{
|
||||
//_logger.LogError("{ex}", ex);
|
||||
}
|
||||
|
|
|
|||
Some files were not shown because too many files have changed in this diff Show more
Loading…
Add table
Add a link
Reference in a new issue