using System.Collections.Generic; using System.IO; using System.Linq; using CliWrap; using System.Threading.Tasks; using System.Threading; using System; using iText.Kernel.Pdf; using iText.Kernel.Utils; namespace AsbCloudInfrastructure.Services.DrillingProgram.Convert { sealed internal class ConvertToPdf { internal static readonly string[] filesExtensions = { ".xlsx", ".xls", ".ods", ".odt", ".doc", ".docx", ".pdf" }; private static void MergeFiles(IEnumerable inputFiles, string outFile) { using var docResult = new PdfDocument(new PdfWriter(outFile)); var merger = new PdfMerger(docResult); foreach (var fileName in inputFiles) { using var doc = new PdfDocument(new PdfReader(fileName)); merger.Merge(doc, 1, doc.GetNumberOfPages()); doc.Close(); }; docResult.Close(); } private static (string programFile, string programArg) GetOptionsStartupProcess (string inputFileName, string resultFileDir) { (string programFile, string programArg) startupOptions; if (OperatingSystem.IsWindows()) { startupOptions.programFile = "C:\\Program Files\\LibreOffice\\program\\soffice.exe"; startupOptions.programArg = $"-headless -convert-to pdf {inputFileName} --outdir {resultFileDir}"; return startupOptions; } if(OperatingSystem.IsLinux()) { startupOptions.programFile = "/usr/bin/soffice"; startupOptions.programArg = $"--headless --convert-to pdf {inputFileName} --outdir {resultFileDir}"; return (startupOptions); } throw new NotSupportedException ("Вызов процесса в текущей операционной системе не возможен"); } private static async Task StartConvertProcessAsync(string inputFileName, string resultFileDir, CancellationToken token) { var (programFile, programArg) = GetOptionsStartupProcess(inputFileName, resultFileDir); var command = Cli.Wrap(programFile) .WithArguments(programArg); await command.ExecuteAsync(token); } public static async Task GetConverteAndMergedFileAsync(IEnumerable files, string resultPath, string convertedFilesDir, CancellationToken token) { var badFiles = files.Where(f => !filesExtensions.Contains(Path.GetExtension(f))); if (badFiles.Any()) { throw new FileFormatException($"Файлы: {string.Join(", ", badFiles)} - неподдерживаемого формата. " + $"Они не могут быть добавлены в список файлов для конвертации и слияния в общий файл программы бурения."); } var listFiles = files .Distinct() .Select(f => new { inputFile = f, convertedFile = Path.Combine(convertedFilesDir, "pdf", Path.ChangeExtension(Path.GetFileName(f), ".pdf")) }) .ToList(); foreach (var file in listFiles) { var fileExt = Path.GetExtension(file.inputFile).ToLower(); if (fileExt != ".pdf") { await StartConvertProcessAsync(file.inputFile, Path.GetDirectoryName(file.convertedFile)!, token); } } MergeFiles(listFiles.Select(c => c.convertedFile), resultPath); Directory.Delete(Path.Combine(convertedFilesDir, "pdf"), true); } } }