refactor(BurnPdfCommand): simplify BurnPdfCommand and improve envelope/document handling

- Updated `BurnPdfCommand` to accept `EnvelopeId` or `EnvelopeUuid` instead of full `EnvelopeQueryBase` and document data.
- Reworked `BurnPdfCommandHandler` to fetch envelope and document from repositories, including proper validations and exceptions.
- Removed direct dependency on `Signature` repository; annotations now retrieved via document elements.
- Added detailed exception handling for missing envelope, document, or byte data.
- Minor namespace and using cleanup.
This commit is contained in:
tekh 2025-11-10 12:58:04 +01:00
parent ffffc2d470
commit b8a2ad97ef

View File

@ -1,7 +1,9 @@
using DigitalData.Core.Abstraction.Application.Repository;
using DigitalData.Core.Exceptions;
using EnvelopeGenerator.Application.Common.Configurations;
using EnvelopeGenerator.Application.Exceptions;
using EnvelopeGenerator.Application.Common.Dto.PSPDFKitInstant;
using EnvelopeGenerator.Application.Common.Extensions;
using EnvelopeGenerator.Application.Exceptions;
using EnvelopeGenerator.Domain.Constants;
using EnvelopeGenerator.Domain.Entities;
using GdPicture14;
@ -10,36 +12,13 @@ using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.Logging;
using Microsoft.Extensions.Options;
using Newtonsoft.Json;
using EnvelopeGenerator.Application.Common.Extensions;
using EnvelopeGenerator.Application.Common.Query;
namespace EnvelopeGenerator.Application.Pdf;
/// <summary>
///
/// </summary>
public record BurnPdfCommand : IRequest<byte[]?>
{
/// <summary>
///
/// </summary>
public EnvelopeQueryBase? Envelope { get; set; }
/// <summary>
///
/// </summary>
public byte[]? Document { get; set; }
/// <summary>
///
/// </summary>
public List<string>? InstantJSONList { get; set; }
/// <summary>
///
/// </summary>
public bool ByCronService { get; set; } = true;
}
public record BurnPdfCommand(int? EnvelopeId = null, string? EnvelopeUuid = null) : IRequest<byte[]>;
/// <summary>
///
@ -50,23 +29,27 @@ public class BurnPdfCommandHandler : IRequestHandler<BurnPdfCommand, byte[]>
private readonly AnnotationManager _manager;
private readonly IRepository<Signature> _signRepo;
private readonly ILogger<BurnPdfCommandHandler> _logger;
private readonly IRepository<Envelope> _envRepo;
private readonly IRepository<Domain.Entities.DocumentStatus> _docStatusRepo;
/// <summary>
///
/// </summary>
/// <param name="pdfBurnerParams"></param>
/// <param name="manager"></param>
/// <param name="signRepo"></param>
/// <param name="logger"></param>
public BurnPdfCommandHandler(IOptions<PDFBurnerParams> pdfBurnerParams, AnnotationManager manager, IRepository<Signature> signRepo, ILogger<BurnPdfCommandHandler> logger)
/// <param name="envRepo"></param>
/// <param name="docStatusRepo"></param>
public BurnPdfCommandHandler(IOptions<PDFBurnerParams> pdfBurnerParams, AnnotationManager manager, ILogger<BurnPdfCommandHandler> logger, IRepository<Envelope> envRepo, IRepository<Domain.Entities.DocumentStatus> docStatusRepo)
{
_options = pdfBurnerParams.Value;
_manager = manager;
_signRepo = signRepo;
_docStatusRepo = docStatusRepo;
_logger = logger;
_envRepo = envRepo;
}
@ -79,15 +62,31 @@ public class BurnPdfCommandHandler : IRequestHandler<BurnPdfCommand, byte[]>
/// <exception cref="NotImplementedException"></exception>
public async Task<byte[]> Handle(BurnPdfCommand request, CancellationToken cancel)
{
// read the elements of envelope with their annotations
var elements = await _signRepo
.Where(sig => sig.Document.EnvelopeId == request.Envelope.Id)
.Include(sig => sig.Annotations)
.ToListAsync(cancel);
var envQuery =
request.EnvelopeId is not null ? _envRepo.Where(env => env.Id == request.EnvelopeId) :
request.EnvelopeUuid is not null ? _envRepo.Where(env => env.Uuid == request.EnvelopeUuid) :
throw new BadRequestException("Request validation failed: Either Envelope Id or Envelope Uuid must be provided.");
return elements.Count > 0
? BurnElementAnnotsToPDF(request.Document, elements)
: BurnInstantJSONAnnotsToPDF(request.Document, request.InstantJSONList);
var envelope = await envQuery
.Include(env => env.Documents!).ThenInclude(doc => doc.Elements!).ThenInclude(element => element.Annotations)
.FirstOrDefaultAsync(cancel)
?? throw new BadRequestException($"Envelope could not be found. Request details:\n" +
System.Text.Json.JsonSerializer.Serialize(request, Format.Json.ForDiagnostics));
var doc = envelope.Documents?.FirstOrDefault()
?? throw new NotFoundException($"Document could not be located within the specified envelope. Request details:\n" +
System.Text.Json.JsonSerializer.Serialize(request, Format.Json.ForDiagnostics));
if (doc.ByteData is null)
throw new InvalidOperationException($"Document byte data is missing, indicating a potential data integrity issue. Request details:\n" +
System.Text.Json.JsonSerializer.Serialize(request, Format.Json.ForDiagnostics));
return doc.Elements?.SelectMany(e => e.Annotations ?? Enumerable.Empty<ElementAnnotation>()).Where(annot => annot is not null).Any() ?? false
? BurnElementAnnotsToPDF(doc.ByteData, doc.Elements)
: BurnInstantJSONAnnotsToPDF(doc.ByteData, await _docStatusRepo
.Where(status => status.EnvelopeId == envelope.Id)
.Select(status => status.Value)
.ToListAsync(cancel));
}
private byte[] BurnElementAnnotsToPDF(byte[] pSourceBuffer, List<Signature> elements)