Compare commits

...

7 Commits

10 changed files with 110 additions and 191 deletions

View File

@@ -32,6 +32,7 @@ public class ReadDocumentQueryHandler : IRequestHandler<ReadDocumentQuery, Envel
/// Initializes a new instance of the <see cref="ReadDocumentQueryHandler"/> class.
/// </summary>
/// <param name="envelopeDocumentRepository">The repository used to access <see cref="EnvelopeDocument"/> entities.</param>
/// <param name="mapper"></param>
public ReadDocumentQueryHandler(IRepository<EnvelopeDocument> envelopeDocumentRepository, IMapper mapper)
{
_repo = envelopeDocumentRepository;
@@ -42,24 +43,23 @@ public class ReadDocumentQueryHandler : IRequestHandler<ReadDocumentQuery, Envel
/// Handles the <see cref="ReadDocumentQuery"/> and returns a <see cref="EnvelopeDocumentDto"/> based on the provided identifiers.
/// </summary>
/// <param name="query">The query containing the document ID or envelope ID to search for.</param>
/// <param name="cancellationToken">A token to monitor for cancellation requests.</param>
/// <param name="cancel">A token to monitor for cancellation requests.</param>
/// <returns>
/// A <see cref="EnvelopeDocumentDto"/> if a matching document is found; otherwise, <c>null</c>.
/// </returns>
/// <exception cref="InvalidOperationException">
/// Thrown when neither <see cref="ReadDocumentQuery.Id"/> nor <see cref="ReadDocumentQuery.EnvelopeId"/> is provided.
/// </exception>
[Obsolete("Use MediatR")]
public async Task<EnvelopeDocumentDto?> Handle(ReadDocumentQuery query, CancellationToken cancellationToken)
public async Task<EnvelopeDocumentDto?> Handle(ReadDocumentQuery query, CancellationToken cancel)
{
if (query.Id is not null)
{
var doc = await _repo.ReadOnly().Where(d => d.Id == query.Id).FirstOrDefaultAsync();
var doc = await _repo.ReadOnly().Where(d => d.Id == query.Id).FirstOrDefaultAsync(cancel);
return _mapper.Map<EnvelopeDocumentDto>(doc);
}
else if (query.EnvelopeId is not null)
{
var doc = await _repo.ReadOnly().Where(d => d.EnvelopeId == query.EnvelopeId).FirstOrDefaultAsync();
var doc = await _repo.ReadOnly().Where(d => d.EnvelopeId == query.EnvelopeId).FirstOrDefaultAsync(cancel);
return _mapper.Map<EnvelopeDocumentDto>(doc);
}

View File

@@ -1,10 +1,14 @@
using EnvelopeGenerator.Application.Dto.EnvelopeReceiver;
using EnvelopeGenerator.Application.Envelopes.Queries;
using AutoMapper;
using DigitalData.Core.Abstraction.Application.Repository;
using DigitalData.Core.Exceptions;
using EnvelopeGenerator.Application.Dto.EnvelopeReceiver;
using EnvelopeGenerator.Application.Envelopes.Queries;
using EnvelopeGenerator.Application.Extensions;
using EnvelopeGenerator.Application.Model;
using EnvelopeGenerator.Application.Receivers.Queries;
using EnvelopeGenerator.Extensions;
using MediatR;
using EnvelopeGenerator.Domain.Entities;
using Microsoft.EntityFrameworkCore;
namespace EnvelopeGenerator.Application.EnvelopeReceivers.Queries;
@@ -43,47 +47,7 @@ namespace EnvelopeGenerator.Application.EnvelopeReceivers.Queries;
/// Die Antwort enthält Details wie den Include, die Zuordnung zwischen Umschlag und Empfänger
/// sowie zusätzliche Metadaten.
/// </remarks>
public record ReadEnvelopeReceiverQuery : IRequest<IEnumerable<EnvelopeReceiverDto>>
{
/// <summary>
///
/// </summary>
public string? Key
{
get => Envelope?.Uuid is string uuid && Receiver?.Signature is string signature
? (uuid, signature).EncodeEnvelopeReceiverId()
: null;
init
{
if (value is null)
return;
(string? EnvelopeUuid, string? ReceiverSignature) = value.DecodeEnvelopeReceiverId();
if(string.IsNullOrEmpty(EnvelopeUuid) || string.IsNullOrEmpty(ReceiverSignature))
{
throw new BadRequestException("Der EnvelopeReceiverKey muss ein gültiger Base64-kodierter String sein, der die EnvelopeUuid und die ReceiverSignature enthält.");
}
Envelope = new ReadEnvelopeQuery()
{
Uuid = EnvelopeUuid
};
Receiver = new ReadReceiverQuery()
{
Signature = ReceiverSignature
};
}
}
/// <summary>
/// Der Umschlag, der mit dem Empfänger verknüpft ist.
/// </summary>
public ReadEnvelopeQuery? Envelope { get; set; }
/// <summary>
/// Der Empfänger, der mit dem Umschlag verknüpft ist.
/// </summary>
public ReadReceiverQuery? Receiver { get; set; }
};
public record ReadEnvelopeReceiverQuery : EnvelopeReceiverQueryBase<ReadEnvelopeQuery, ReadReceiverQuery>, IRequest<IEnumerable<EnvelopeReceiverDto>>;
/// <summary>
///
@@ -102,4 +66,61 @@ public static class Extensions
var q = new ReadEnvelopeReceiverQuery() { Key = key };
return mediator.Send(q, cancel).Then(envRcvs => envRcvs.FirstOrDefault());
}
}
/// <summary>
///
/// </summary>
public class ReadEnvelopeReceiverQueryHandler : IRequestHandler<ReadEnvelopeReceiverQuery, IEnumerable<EnvelopeReceiverDto>>
{
private readonly IRepository<EnvelopeReceiver> _repo;
private readonly IMapper _mapper;
/// <summary>
///
/// </summary>
/// <param name="envelopeReceiver"></param>
/// <param name="mapper"></param>
public ReadEnvelopeReceiverQueryHandler(IRepository<EnvelopeReceiver> envelopeReceiver, IMapper mapper)
{
_repo = envelopeReceiver;
_mapper = mapper;
}
/// <summary>
///
/// </summary>
/// <param name="request"></param>
/// <param name="cancel"></param>
/// <returns></returns>
/// <exception cref="BadRequestException"></exception>
public async Task<IEnumerable<EnvelopeReceiverDto>> Handle(ReadEnvelopeReceiverQuery request, CancellationToken cancel)
{
var q = _repo.Read().Where(request, notnull: false);
if (request.Envelope.Status is not null)
{
var status = request.Envelope.Status;
if (status.Min is not null)
q = q.Where(er => er.Envelope!.Status >= status.Min);
if (status.Max is not null)
q = q.Where(er => er.Envelope!.Status <= status.Max);
if (status.Include?.Length > 0)
q = q.Where(er => status.Include.Contains(er.Envelope!.Status));
if (status.Ignore is not null)
q = q.Where(er => !status.Ignore.Contains(er.Envelope!.Status));
}
var envRcvs = await q.Include(er => er.Envelope).ThenInclude(e => e!.Documents).ThenInclude(d => d.Elements)
.Include(er => er.Envelope).ThenInclude(e => e!.History)
.Include(er => er.Envelope).ThenInclude(e => e!.User)
.Include(er => er.Receiver)
.ToListAsync(cancel);
return _mapper.Map<IEnumerable<EnvelopeReceiverDto>>(envRcvs);
}
}

View File

@@ -1,87 +0,0 @@
using AutoMapper;
using DigitalData.Core.Abstraction.Application.Repository;
using EnvelopeGenerator.Application.Dto.EnvelopeReceiver;
using EnvelopeGenerator.Domain.Entities;
using MediatR;
using Microsoft.EntityFrameworkCore;
namespace EnvelopeGenerator.Application.EnvelopeReceivers.Queries;
/// <summary>
///
/// </summary>
public class ReadEnvelopeReceiverQueryHandler : IRequestHandler<ReadEnvelopeReceiverQuery, IEnumerable<EnvelopeReceiverDto>>
{
private readonly IRepository<EnvelopeReceiver> _repo;
private readonly IMapper _mapper;
/// <summary>
///
/// </summary>
/// <param name="envelopeReceiver"></param>
/// <param name="mapper"></param>
public ReadEnvelopeReceiverQueryHandler(IRepository<EnvelopeReceiver> envelopeReceiver, IMapper mapper)
{
_repo = envelopeReceiver;
_mapper = mapper;
}
/// <summary>
///
/// </summary>
/// <param name="request"></param>
/// <param name="cancel"></param>
/// <returns></returns>
/// <exception cref="NotImplementedException"></exception>
public async Task<IEnumerable<EnvelopeReceiverDto>> Handle(ReadEnvelopeReceiverQuery request, CancellationToken cancel)
{
var q = _repo.Read();
if(request.Envelope is not null)
{
var env = request.Envelope;
if (env.Id is not null)
q = q.Where(er => er.EnvelopeId == env.Id);
if (env.Status is not null)
{
if(env.Status.Min is not null)
q = q.Where(er => er.Envelope.Status >= env.Status.Min);
if(env.Status.Max is not null)
q = q.Where(er => er.Envelope.Status <= env.Status.Max);
if(env.Status .Include?.Length > 0)
q = q.Where(er => env.Status.Include.Contains(er.Envelope.Status));
if(env.Status.Ignore is not null)
q = q.Where(er => !env.Status.Ignore.Contains(er.Envelope.Status));
}
if (env.Uuid is not null)
q = q.Where(er => er.Envelope.Uuid == env.Uuid);
}
if (request.Receiver is not null)
{
var rcv = request.Receiver;
if (rcv.Id is not null)
q = q.Where(r => r.ReceiverId == rcv.Id);
if (rcv.EmailAddress is not null)
q = q.Where(r => r.Receiver.EmailAddress == rcv.EmailAddress);
if (rcv.Signature is not null)
q = q.Where(er => er.Receiver.Signature == rcv.Signature);
}
var envRcvs = await q.Include(er => er.Envelope).ThenInclude(e => e.Documents).ThenInclude(d => d.Elements)
.Include(er => er.Envelope).ThenInclude(e => e.History)
.Include(er => er.Envelope).ThenInclude(e => e.User)
.Include(er => er.Receiver)
.ToListAsync(cancel);
return _mapper.Map<IEnumerable<EnvelopeReceiverDto>>(envRcvs);
}
}

View File

@@ -1,23 +1,14 @@
using MediatR;
using EnvelopeGenerator.Domain;
using EnvelopeGenerator.Application.Model;
namespace EnvelopeGenerator.Application.Envelopes.Queries;
/// <summary>
/// Repräsentiert eine Abfrage für Umschläge.
/// </summary>
public class ReadEnvelopeQuery : IRequest
public record ReadEnvelopeQuery : EnvelopeQueryBase, IRequest
{
/// <summary>
/// Die eindeutige Kennung des Umschlags.
/// </summary>
public int? Id { get; init; }
/// <summary>
/// Die universell eindeutige Kennung des Umschlags.
/// </summary>
public string? Uuid { get; init; }
/// <summary>
/// Abfrage des Include des Umschlags
/// </summary>
@@ -52,6 +43,7 @@ public class ReadEnvelopeQuery : IRequest
/// MessageDeletionSent (3004): Löschbenachrichtigung wurde gesendet.
/// MessageCompletionSent (3005): Abschlussbenachrichtigung wurde gesendet.
/// </summary>
public record EnvelopeStatus
{
/// <summary>

View File

@@ -4,23 +4,24 @@ using EnvelopeGenerator.Domain;
using EnvelopeGenerator.Domain.Entities;
using MediatR;
using Microsoft.EntityFrameworkCore;
using EnvelopeGenerator.Application.Extensions;
namespace EnvelopeGenerator.Application.Histories.Commands;
/// <summary>
///
/// </summary>
public record CreateHistoryCommand : IRequest<long?>
public record CreateHistoryCommand : EnvelopeReceiverQueryBase, IRequest<long?>
{
/// <summary>
///
/// </summary>
public int EnvelopeId { get; set; }
public int? EnvelopeId { get; set; }
/// <summary>
///
/// </summary>
public string UserReference { get; set; } = null!;
public string? UserReference { get; set; }
/// <summary>
///
@@ -41,16 +42,6 @@ public record CreateHistoryCommand : IRequest<long?>
///
/// </summary>
public string? Comment { get; set; }
/// <summary>
///
/// </summary>
public EnvelopeQueryBase? Envelope { get; init; }
/// <summary>
/// /
/// </summary>
public ReceiverQueryBase? Receiver { get; init; }
}
/// <summary>
@@ -81,9 +72,17 @@ public class CreateHistoryCommandHandler : IRequestHandler<CreateHistoryCommand,
await _repo.CreateAsync(request, cancel);
// check if created
var record = await _repo.ReadOnly()
.Where(h => h.EnvelopeId == request.EnvelopeId)
.Where(h => h.UserReference == request.UserReference)
var query = _repo.ReadOnly();
query = request.EnvelopeId is null
? query.Where(request.Envelope)
: query.Where(h => h.EnvelopeId == request.EnvelopeId);
query = request.UserReference is null
? query.Where(request.Receiver)
: query.Where(h => h.UserReference == request.UserReference);
var record = await query
.Where(h => h.ActionDate == request.ActionDate)
.SingleOrDefaultAsync(cancel);

View File

@@ -13,5 +13,5 @@ public record EnvelopeQueryBase
/// <summary>
/// Die universell eindeutige Kennung des Umschlags.
/// </summary>
public virtual string? Uuid { get; set; }
public virtual string? Uuid { get; init; }
}

View File

@@ -1,23 +1,9 @@
namespace EnvelopeGenerator.Application.Receivers.Queries;
using EnvelopeGenerator.Application.Model;
namespace EnvelopeGenerator.Application.Receivers.Queries;
/// <summary>
/// Stellt eine Abfrage dar, um die Details eines Empfängers zu lesen.
/// um spezifische Informationen über einen Empfänger abzurufen.
/// </summary>
public record ReadReceiverQuery
{
/// <summary>
/// ID des Empfängers
/// </summary>
public int? Id { get; init; }
/// <summary>
/// E-Mail Adresse des Empfängers
/// </summary>
public string? EmailAddress { get; init; }
/// <summary>
/// Eindeutige Signatur des Empfängers
/// </summary>
public string? Signature { get; init; }
}
public record ReadReceiverQuery : ReceiverQueryBase;

View File

@@ -1,6 +1,8 @@
using DigitalData.UserManager.Domain.Entities;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
using EnvelopeGenerator.Domain.Interfaces;
#if NETFRAMEWORK
using System;
#endif
@@ -13,7 +15,7 @@ namespace EnvelopeGenerator.Domain.Entities
#endif
[Table("TBSIG_ENVELOPE_HISTORY", Schema = "dbo")]
public class EnvelopeHistory
public class EnvelopeHistory : IHasEnvelope, IHasReceiver
{
[Key]
[DatabaseGenerated(DatabaseGeneratedOption.Identity)]
@@ -39,7 +41,7 @@ public class EnvelopeHistory
[Column("ACTION_DATE", TypeName = "datetime")]
public DateTime? ActionDate { get; set; } = DateTime.Now;
[Column("COMMENT", TypeName = "nvarchar(max)")]
public string
#if NET
@@ -47,6 +49,14 @@ public class EnvelopeHistory
#endif
Comment { get; set; }
[ForeignKey("EnvelopeId")]
public virtual Envelope
#if NET
?
#endif
Envelope { get; set; }
[ForeignKey("UserReference")]
public virtual User
#if NET
?
@@ -54,6 +64,7 @@ public class EnvelopeHistory
Sender
{ get; set; }
[ForeignKey("UserReference")]
public virtual Receiver
#if NET
?

View File

@@ -155,14 +155,12 @@ public class EGDbContext : DbContext, IUserManagerDbContext, IMailDbContext
modelBuilder.Entity<DocumentStatus>()
.HasOne(ds => ds.Envelope)
.WithMany()
.HasForeignKey(ds => ds.EnvelopeId)
.HasPrincipalKey(e => e.Uuid);
.HasForeignKey(ds => ds.EnvelopeId);
modelBuilder.Entity<DocumentStatus>()
.HasOne(ds => ds.Receiver)
.WithMany()
.HasForeignKey(ds => ds.ReceiverId)
.HasPrincipalKey(e => e.Signature);
.HasForeignKey(ds => ds.ReceiverId);
modelBuilder.Entity<DocumentStatus>()
.HasOne(ds => ds.Receiver)

View File

@@ -24,7 +24,7 @@ public class EnvelopeController : BaseController
{
private readonly EnvelopeOldService envelopeService;
private readonly ActionService? actionService;
private readonly UrlEncoder _urlEncoder;
[Obsolete("Use MediatR")]
private readonly IEnvelopeHistoryService _histService;
[Obsolete("Use MediatR")]
@@ -35,13 +35,12 @@ public class EnvelopeController : BaseController
[Obsolete("Use MediatR")]
public EnvelopeController(DatabaseService database,
EnvelopeOldService envelope,
ILogger<EnvelopeController> logger, UrlEncoder urlEncoder,
ILogger<EnvelopeController> logger,
IEnvelopeHistoryService envelopeHistoryService,
IEnvelopeReceiverService envelopeReceiverService, IMediator mediator) : base(database, logger)
{
envelopeService = envelope;
actionService = database?.Services?.actionService;
_urlEncoder = urlEncoder;
_histService = envelopeHistoryService;
_envRcvService = envelopeReceiverService;
_mediator = mediator;