Files
monorepo/LCU.API.Internal.FileOperations/LCU.Api.Internal.FileOperations/Controllers/PdfController.cs
T
2026-04-27 10:50:07 -05:00

185 lines
8.4 KiB
C#

using System;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Serilog;
using LCU.Api.Internal.FileOperations.Services;
using LCU.Library.Internal.FileOperationsModels.Models;
using LCU.Library.Internal.Exceptions;
using LCU.Library.Internal.FileOperationsModels.Models.HtmlToPdfModels;
using LCU.Api.Internal.FileOperations.Extensions;
using LCU.Api.Internal.FileOperations.Services.QueueServices;
using LCU.Api.Internal.FileOperations.Services.PdfServices;
namespace LCU.Api.Internal.FileOperations.Controllers;
[ApiController]
[Route("api/[controller]")]
public class PdfController : ControllerBase
{
private readonly IQueueFileOperationsService _queueFileOperationsService;
private readonly IPdfParserService _pdfParserService;
private readonly IBatchPdfParserService _batchPdfParserService;
private readonly IDirectFileService _directFileService;
private readonly IHtmlToPdfService _htmlToPdfService;
public PdfController(IQueueFileOperationsService queueFileOperationsService,
IPdfParserService pdfParserService,
IBatchPdfParserService batchPdfParserService,
IDirectFileService directFileService,
IHtmlToPdfService htmlToPdfService)
{
_queueFileOperationsService = queueFileOperationsService;
_batchPdfParserService = batchPdfParserService;
_pdfParserService = pdfParserService;
_directFileService = directFileService;
_htmlToPdfService = htmlToPdfService;
}
[HttpPost("QueueBatchPdfParser")]
[ProducesResponseType(202)]
[ProducesResponseType(400)]
[ProducesResponseType(500)]
public async Task<IActionResult> QueueBatchPdfParser([FromBody] BatchParsePdfRequest request)
{
try
{
var requestResponse = _batchPdfParserService.IsRequestValid(request, new RequestResponse());
if (!requestResponse.IsSuccessful)
{
return BadRequest($"Request is invalid. Response: {String.Join("\n ", requestResponse.MessageStack.ToArray())}");
}
await _queueFileOperationsService.QueueFileOperations(request, FileOperationType.BatchPdfParser);
return Accepted();
}
catch (ServiceException exception)
{
return StatusCode(StatusCodes.Status500InternalServerError, exception.Message);
}
catch (Exception exception)
{
Log.Error(exception, "Unexpected Exception");
return StatusCode(StatusCodes.Status500InternalServerError);
}
}
/// <remarks>
/// This will parse a PDF from a starting page to and a stopping page, save new pdf to RootPath,
/// and returns the PDF name. The PDF name will be set to ParsedPdfname or the default "{pdfParserRequest.PdfName}.{pdfParserRequest.StartingPage}.pdf".
///
/// Notes:
/// - Page numbers range from 1-x.
/// - If PDF exists it will automatically overwrite.
/// - Original PDF can be open at the time of parsing.
/// </remarks>
/// <param name="pdfParserRequest"></param>
/// <returns></returns>
[HttpPost("ParsePdf")]
[ProducesResponseType(200)]
[ProducesResponseType(typeof(ParsePdfRequest), 400)]
[ProducesResponseType(500)]
public IActionResult ParsePdf([FromBody] ParsePdfRequest pdfParserRequest)
{
try
{
if (!ModelState.IsValid)
{
return BadRequest(ModelState.GetErrorMessages());
}
var result = _pdfParserService.ParsePdf(pdfParserRequest);
return Ok(result);
}
catch (ServiceException exception)
{
return StatusCode(StatusCodes.Status500InternalServerError, exception.Message);
}
catch (Exception exception)
{
Log.Error(exception, "Unexpected Exception");
return StatusCode(StatusCodes.Status500InternalServerError);
}
}
[HttpGet("GetPdfContent/{pdfPath}")]
[ProducesResponseType(200)]
[ProducesResponseType(400)]
[ProducesResponseType(500)]
public IActionResult GetPdfContent([FromRoute] string pdfPath)
{
if (string.IsNullOrWhiteSpace(pdfPath))
{
return BadRequest("PDF Path is required");
}
try
{
var result = _directFileService.GetFileBytes(pdfPath);
return new FileContentResult(result, "application/pdf");
}
catch (ArgumentException ae)
{
Log.Error(ae, $"Request for bad PDF path {pdfPath}");
return BadRequest("PDF path not found");
}
catch (Exception ex)
{
Log.Error(ex, $"Unexpected error retrieving PDF path {pdfPath}");
return StatusCode(StatusCodes.Status500InternalServerError);
}
}
/// <remarks>
/// ConvertHmtlToPdf will take the HtmlToPdfRequest and generate a HTML file filling in the tags with the supplied data.
/// It will then utilize Chrome functionality to print a pdf and save it to a location. Finally converting to byte array and returning.
///
/// HtmlToPdfRequest:
/// - HtmlTemplateFilePath: (REQUIRED) File Path of the main html template that the HTML file will start to build.
/// - PdfName: (REQUIRED) What the PDF and HTML files will be called.
/// - KeepHtmlFile: (Defaults = False) Mostly for testing purposes. If set to true it will keep the generated HTML file.
/// - KeepPdfFile: (Defaults = False) Mostly for testing purposes. If set to true it will keep the generated PDF file
/// - HtmlSaveFilePath: (REQUIRED) Location that the generated HTML file will be temporarily (KeepHtmlFile = false) stored.
/// - PdfSaveFilePath: (REQUIRED) Location that the generated PDF file will be temporarily (KeepHtmlFile = false) stored.
/// - BodyTagValues: Tags that will be filled in with supplied values.
/// - TagValues:
/// - Tag: (REQUIRED) Name of the tag in the HTML. In HTML should be surrounded by {}. This tag does not need {}.
/// - Value: (REQUIRED) Value in which will replace the {TagName}.
/// - BodyValueCollections: List of ValueCollections that give us the ability to replace a tag that is associated with a HTML Template. The ValucollectionItems is
/// looped through to generate what will replace the tag. Common use case would be a list of items or a table of items.
/// - CollectionTag: (REQUIRED) Name of the tag in the HTML. In HTML should be surrounded by {}. This tag does not need {}.
/// - CollectionHtmlTemplateFilePath: (REQUIRED) File Path of the collections html template that the HTML file will start to build.
/// - ValueCollectionItems: List of ValueCollectionItems that can be looped through to help build out what the CollectionTag will be replaced with.
/// ValueCollection has a nested ValueCollectionItems, giving the ability to create infinite amount of nested collections within collections.
/// - TagValues: List of TagValues
/// - ValueCollections: List of ValueCollections
///
/// Notes:
/// - In HTML templates tags should be surrounded by braces {TagName}. The request does not need the braces {}.
/// - Any unused tags surrounded by braces will be removed at the end of the process.
/// - Can use \\\\zeus\DataIntegrationsQA\\PDFCreation\\ folder to store templates, generated HTML files, and generated PDF
/// - \\\\zeus\DataIntegrationsQA\\PDFCreation\\Html_Templates
/// - \\\\zeus\DataIntegrationsQA\\PDFCreation\\Html_Drop
/// - \\\\zeus\DataIntegrationsQA\\PDFCreation\\PDF_Drop
/// </remarks>
[HttpPost("ConvertHtmlToPdf")]
[ProducesResponseType(200)]
[ProducesResponseType(400)]
[ProducesResponseType(500)]
public IActionResult ConvertHtmlToPdf([FromBody] HtmlToPdfRequest htmlToPdfRequest)
{
try
{
var result = _htmlToPdfService.ConvertHtmlToPdf(htmlToPdfRequest);
return new FileContentResult(result, "application/pdf");
}
catch (ServiceException exception)
{
return StatusCode(StatusCodes.Status500InternalServerError, exception.Message);
}
catch (Exception exception)
{
Log.Error(exception, "Unexpected Exception");
return StatusCode(StatusCodes.Status500InternalServerError);
}
}
}