using File_Watcher.Models; using System.Diagnostics; using System.Net; using System.Net.Sockets; namespace File_Watcher.Helpers; internal static partial class HelperTCP { private record Record(BinaryReader BinaryReader, BinaryWriter BinaryWriter, NetworkStream NetworkStream); private static long _LastWrite; private static Record? _Record; private static TcpListener? _TcpListener; private static readonly object _Lock = new(); private static void OnAccept(IAsyncResult asyncResult) { if (_TcpListener is null) throw new NullReferenceException(nameof(_TcpListener)); lock (_Lock) { TcpClient tcpClient = _TcpListener.EndAcceptTcpClient(asyncResult); NetworkStream networkStream = tcpClient.GetStream(); _Record = new(new(networkStream), new(networkStream), networkStream); } } private static string ConvertSourceFileToPdf(string ghostPCLFileName, string reportFullPath) { string result = Path.ChangeExtension(reportFullPath, ".pdf"); if (!File.Exists(result)) { //string arguments = string.Concat("-i \"", sourceFile, "\" -o \"", result, "\""); string arguments = string.Concat("-dSAFER -dBATCH -dNOPAUSE -sOutputFile=\"", result, "\" -sDEVICE=pdfwrite \"", reportFullPath, "\""); //Process process = Process.Start(configData.LincPDFCFileName, arguments); Process process = Process.Start(ghostPCLFileName, arguments); _ = process.WaitForExit(30000); if (!File.Exists(result)) throw new Exception("PDF file wasn't created"); } return result; } private static void BeginAcceptTcpClient() { if (_TcpListener is null) throw new NullReferenceException(nameof(_TcpListener)); _ = _TcpListener.BeginAcceptTcpClient(OnAccept, null); } private static void ReadFiles(TransmissionControlProtocolConfiguration transmissionControlProtocolConfiguration) { List bytes = []; // byte nullByte = Convert.ToByte('\0'); string[] files = Directory.GetFiles(transmissionControlProtocolConfiguration.Destination, $"{transmissionControlProtocolConfiguration.IPAddress}-*.raw", SearchOption.TopDirectoryOnly); foreach (string file in files) { foreach (byte @byte in File.ReadAllBytes(file)) { // if (@byte.Equals(nullByte)) // continue; bytes.Add(@byte); } } if (bytes.Count > 0) { string bytesFile = Path.Combine(transmissionControlProtocolConfiguration.Destination, $"{transmissionControlProtocolConfiguration.IPAddress}-{DateTime.Now.Ticks}.pcl"); File.WriteAllBytes(bytesFile, bytes.ToArray()); string ghostPCLFileName = Path.Combine(AppContext.BaseDirectory, "gpcl6win64.exe"); if (!File.Exists(ghostPCLFileName)) throw new Exception("Ghost PCL FileName doesn't Exist!"); string sourceFileNamePdf = ConvertSourceFileToPdf(ghostPCLFileName, bytesFile); if (string.IsNullOrEmpty(sourceFileNamePdf)) throw new Exception("Ghost PCL FileName doesn't Exist!"); } } private static void CreateClient(AppSettings appSettings, ILogger logger) { logger.LogDebug(appSettings.TransmissionControlProtocolConfiguration.IPAddress); TcpClient tcpClient = new(appSettings.TransmissionControlProtocolConfiguration.IPAddress, appSettings.TransmissionControlProtocolConfiguration.Port); NetworkStream networkStream = tcpClient.GetStream(); _Record = new(new(networkStream), new(networkStream), networkStream); } private static void CreateTcpListener(AppSettings appSettings) { IPAddress ipAddress = IPAddress.Parse("127.0.0.1"); _TcpListener = new(ipAddress, appSettings.TransmissionControlProtocolConfiguration.Port); _TcpListener.Start(); BeginAcceptTcpClient(); } private static void NetworkStreamCanRead(TransmissionControlProtocolConfiguration transmissionControlProtocolConfiguration, NetworkStream networkStream) { List results = []; byte[] bytes = new byte[1024]; string directory = Path.GetFullPath(Path.Combine(transmissionControlProtocolConfiguration.Destination, transmissionControlProtocolConfiguration.IPAddress)); if (!Directory.Exists(directory)) _ = Directory.CreateDirectory(directory); do { int count = networkStream.Read(bytes, 0, bytes.Length); if (count > 0) results.AddRange(bytes.Take(count)); } while (networkStream.DataAvailable); if (results.Count > 0) File.WriteAllBytes(Path.Combine(directory, $"{DateTime.Now.Ticks}{directory[^1]}.raw"), results.ToArray()); } internal static bool ReadWrite(AppSettings appSettings, ILogger logger) { lock (_Lock) { if (!appSettings.TransmissionControlProtocolConfiguration.Server) ReadFiles(appSettings.TransmissionControlProtocolConfiguration); if (!appSettings.TransmissionControlProtocolConfiguration.Server && _Record is not null) { TimeSpan timeSpan = new(DateTime.Now.Ticks - _LastWrite); if (_LastWrite == 0 || timeSpan.TotalMinutes > 1) { try { _Record.NetworkStream.WriteByte(Convert.ToByte('\0')); _LastWrite = DateTime.Now.Ticks; } catch (Exception) { } } } if (!appSettings.TransmissionControlProtocolConfiguration.Server && (_Record?.NetworkStream is null || !_Record.NetworkStream.Socket.Connected)) CreateClient(appSettings, logger); else if (appSettings.TransmissionControlProtocolConfiguration.Server && _TcpListener is null) CreateTcpListener(appSettings); if (_Record?.NetworkStream is not null && _Record.NetworkStream.CanRead && _Record.NetworkStream.DataAvailable) NetworkStreamCanRead(appSettings.TransmissionControlProtocolConfiguration, _Record.NetworkStream); if (appSettings.TransmissionControlProtocolConfiguration.Server && _TcpListener is not null && _Record?.NetworkStream is not null && _Record.NetworkStream.CanWrite) { try { _Record.BinaryWriter.Write("json"); } catch (Exception) { BeginAcceptTcpClient(); } } } return true; } }