using System.Diagnostics; using System.Text; using Azaion.CommonSecurity.DTO; using Azaion.CommonSecurity.DTO.Commands; using MessagePack; using NetMQ; using NetMQ.Sockets; using Serilog; using Exception = System.Exception; namespace Azaion.CommonSecurity.Services; public class LoaderClient(LoaderClientConfig config, ILogger logger, CancellationToken ct = default) { private readonly DealerSocket _dealer = new(); private readonly Guid _clientId = Guid.NewGuid(); public void StartClient() { try { using var process = new Process(); process.StartInfo = new ProcessStartInfo { FileName = SecurityConstants.EXTERNAL_LOADER_PATH, Arguments = $"--port {config.ZeroMqPort} --api {config.ApiUrl}", CreateNoWindow = true }; process.OutputDataReceived += (_, e) => { if (e.Data != null) Console.WriteLine(e.Data); }; process.ErrorDataReceived += (_, e) => { if (e.Data != null) Console.WriteLine(e.Data); }; process.Start(); } catch (Exception e) { logger.Error(e.Message); throw; } } public void Connect() { _dealer.Options.Identity = Encoding.UTF8.GetBytes(_clientId.ToString("N")); _dealer.Connect($"tcp://{config.ZeroMqHost}:{config.ZeroMqPort}"); } public void Send(RemoteCommand command) => _dealer.SendFrame(MessagePackSerializer.Serialize(command)); public MemoryStream LoadFile(string filename, string folder) { try { Send(RemoteCommand.Create(CommandType.Load, new LoadFileData(filename, folder))); var retries = 10; var tryNum = 0; while (!ct.IsCancellationRequested && tryNum++ < retries) { if (!_dealer.TryReceiveFrameBytes(TimeSpan.FromMilliseconds(150), out var bytes)) continue; var resultCommand = MessagePackSerializer.Deserialize(bytes, cancellationToken: ct); if (resultCommand.Data?.Length == 0) throw new Exception($"Can't load {filename}. Returns 0 bytes"); return new MemoryStream(resultCommand.Data!); } throw new Exception($"Can't load file {filename} after {retries} retries"); } catch (Exception e) { logger.Error(e, e.Message); throw; } } }