Add Swiss QR Code extraction feature
Introduced DTOs for request and response to handle Swiss QR Code extraction from PDF documents. Implemented `ExtractSwissQrCodeHandler` to process the extraction using `ISwissQrCodeProcessor`. Added validation for the query with `ExtractSwissQrCodeValidator`. Developed unit tests to ensure correct behavior for successful and failure scenarios.
This commit is contained in:
@@ -0,0 +1,12 @@
|
||||
namespace DocumentOperator.Application.Common.DTOs;
|
||||
|
||||
/// <summary>
|
||||
/// Request to extract Swiss QR Code from a PDF document.
|
||||
/// The QR code must be located on the last page of the document.
|
||||
/// </summary>
|
||||
/// <param name="References">Array of reference strings to pass through in the response</param>
|
||||
/// <param name="Base64Pdf">PDF document encoded as Base64 string</param>
|
||||
public record ExtractSwissQrCodeRequest(
|
||||
IReadOnlyList<string> References,
|
||||
string Base64Pdf
|
||||
);
|
||||
@@ -0,0 +1,46 @@
|
||||
namespace DocumentOperator.Application.Common.DTOs;
|
||||
|
||||
/// <summary>
|
||||
/// Response containing extracted Swiss QR Code data and passed-through references.
|
||||
/// </summary>
|
||||
/// <param name="References">Reference strings passed through from the request</param>
|
||||
/// <param name="QrCodeData">Parsed Swiss QR Code data from the last page of the PDF</param>
|
||||
public record ExtractSwissQrCodeResponse(
|
||||
IReadOnlyList<string> References,
|
||||
SwissQrCodeDataDto QrCodeData
|
||||
);
|
||||
|
||||
/// <summary>
|
||||
/// Swiss QR Code data according to Swiss QR Bill Standard 2.0
|
||||
/// </summary>
|
||||
public record SwissQrCodeDataDto(
|
||||
string QrType,
|
||||
string Version,
|
||||
string CodingType,
|
||||
string Iban,
|
||||
AddressDataDto Creditor,
|
||||
AddressDataDto? UltimateCreditor,
|
||||
decimal? Amount,
|
||||
string Currency,
|
||||
AddressDataDto? UltimateDebtor,
|
||||
string ReferenceType,
|
||||
string? Reference,
|
||||
string? UnstructuredMessage,
|
||||
string? BillInformation,
|
||||
IReadOnlyList<string>? AlternativeProcedureParameters
|
||||
);
|
||||
|
||||
/// <summary>
|
||||
/// Address data (creditor or debtor) in Swiss QR Code
|
||||
/// </summary>
|
||||
public record AddressDataDto(
|
||||
string AddressType,
|
||||
string Name,
|
||||
string? Street,
|
||||
string? BuildingNumber,
|
||||
string? AddressLine1,
|
||||
string? AddressLine2,
|
||||
string PostalCode,
|
||||
string City,
|
||||
string Country
|
||||
);
|
||||
@@ -0,0 +1,33 @@
|
||||
using DocumentOperator.Application.Common.Interfaces;
|
||||
using MediatR;
|
||||
|
||||
namespace DocumentOperator.Application.Features.Documents.ExtractSwissQrCode;
|
||||
|
||||
/// <summary>
|
||||
/// Handles extraction of Swiss QR Code from PDF documents.
|
||||
/// Uses ISwissQrCodeProcessor to extract QR code from the last page and parse it.
|
||||
/// </summary>
|
||||
public sealed class ExtractSwissQrCodeHandler : IRequestHandler<ExtractSwissQrCodeQuery, ExtractSwissQrCodeResult>
|
||||
{
|
||||
private readonly ISwissQrCodeProcessor _qrCodeProcessor;
|
||||
|
||||
public ExtractSwissQrCodeHandler(ISwissQrCodeProcessor qrCodeProcessor)
|
||||
{
|
||||
_qrCodeProcessor = qrCodeProcessor;
|
||||
}
|
||||
|
||||
public async Task<ExtractSwissQrCodeResult> Handle(ExtractSwissQrCodeQuery request, CancellationToken cancellationToken)
|
||||
{
|
||||
// Convert Base64 string to byte array
|
||||
byte[] pdfBytes = request.PdfContent.ToByteArray();
|
||||
|
||||
// Extract and parse Swiss QR Code from last page
|
||||
var qrCodeData = await _qrCodeProcessor.ExtractSwissQrCodeAsync(pdfBytes, cancellationToken);
|
||||
|
||||
// Return references (passed through) + QR code data
|
||||
return new ExtractSwissQrCodeResult(
|
||||
References: request.References,
|
||||
QrCodeData: qrCodeData
|
||||
);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,26 @@
|
||||
using DocumentOperator.Domain.Models.ValueObjects;
|
||||
using DocumentOperator.Domain.ValueObjects;
|
||||
using MediatR;
|
||||
|
||||
namespace DocumentOperator.Application.Features.Documents.ExtractSwissQrCode;
|
||||
|
||||
/// <summary>
|
||||
/// Query to extract Swiss QR Code data from a PDF document.
|
||||
/// Returns references (passed through) and parsed QR code data.
|
||||
/// </summary>
|
||||
/// <param name="References">Array of reference strings to pass through in the response</param>
|
||||
/// <param name="PdfContent">PDF document content as Base64 string</param>
|
||||
public record ExtractSwissQrCodeQuery(
|
||||
IReadOnlyList<string> References,
|
||||
Base64String PdfContent
|
||||
) : IRequest<ExtractSwissQrCodeResult>;
|
||||
|
||||
/// <summary>
|
||||
/// Result containing passed-through references and extracted Swiss QR Code data
|
||||
/// </summary>
|
||||
/// <param name="References">Reference strings passed through from request</param>
|
||||
/// <param name="QrCodeData">Parsed Swiss QR Code data from the last page of the PDF</param>
|
||||
public record ExtractSwissQrCodeResult(
|
||||
IReadOnlyList<string> References,
|
||||
SwissQrCodeData QrCodeData
|
||||
);
|
||||
@@ -0,0 +1,21 @@
|
||||
using FluentValidation;
|
||||
|
||||
namespace DocumentOperator.Application.Features.Documents.ExtractSwissQrCode;
|
||||
|
||||
/// <summary>
|
||||
/// Validates ExtractSwissQrCodeQuery before handler execution.
|
||||
/// Ensures references array and PDF content are provided.
|
||||
/// </summary>
|
||||
public sealed class ExtractSwissQrCodeValidator : AbstractValidator<ExtractSwissQrCodeQuery>
|
||||
{
|
||||
public ExtractSwissQrCodeValidator()
|
||||
{
|
||||
RuleFor(x => x.References)
|
||||
.NotNull()
|
||||
.WithMessage("References array is required.");
|
||||
|
||||
RuleFor(x => x.PdfContent)
|
||||
.NotNull()
|
||||
.WithMessage("PDF content is required.");
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user