Compare commits
21 Commits
2692fee6d2
...
f877910a73
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
f877910a73 | ||
|
|
f6f4137332 | ||
|
|
486b717801 | ||
|
|
f2a09ea10e | ||
|
|
cc86e5fadd | ||
|
|
bce29aa31a | ||
|
|
95a1fd1355 | ||
|
|
613b2130a5 | ||
|
|
e4eb3e1192 | ||
|
|
1c4f7f2386 | ||
|
|
a7e4d6e58f | ||
|
|
b9c4f7da1c | ||
|
|
cec79e5b6d | ||
|
|
2f08991eeb | ||
|
|
21859ca6e6 | ||
|
|
27d9a149bc | ||
|
|
a76a079736 | ||
|
|
10341fd3cc | ||
|
|
05de44bc13 | ||
|
|
d2c45f71a0 | ||
|
|
42451a767b |
@@ -0,0 +1,18 @@
|
||||
using EnvelopeGenerator.Domain.Entities;
|
||||
|
||||
namespace EnvelopeGenerator.Application.Contracts.SQLExecutor;
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public interface IDocumentExecutor
|
||||
{
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="base64"></param>
|
||||
/// <param name="envelope_uuid"></param>
|
||||
/// <param name="cancellation"></param>
|
||||
/// <returns></returns>
|
||||
Task<EnvelopeDocument> CreateDocumentAsync(string base64, string envelope_uuid, CancellationToken cancellation = default);
|
||||
}
|
||||
@@ -3,6 +3,8 @@ using DigitalData.Core.Abstractions.Application;
|
||||
using DigitalData.Core.DTO;
|
||||
using EnvelopeGenerator.Application.DTOs.EnvelopeReceiver;
|
||||
using EnvelopeGenerator.Application.DTOs.Messaging;
|
||||
using EnvelopeGenerator.Application.Envelopes;
|
||||
using EnvelopeGenerator.Application.Receivers.Queries.Read;
|
||||
using EnvelopeGenerator.Domain.Entities;
|
||||
|
||||
namespace EnvelopeGenerator.Application.Contracts.Services;
|
||||
@@ -31,7 +33,7 @@ public interface IEnvelopeReceiverService : IBasicCRUDService<EnvelopeReceiverDt
|
||||
|
||||
Task<DataResult<bool>> IsExisting(string envelopeReceiverId);
|
||||
|
||||
Task<DataResult<IEnumerable<EnvelopeReceiverDto>>> ReadByUsernameAsync(string username, int? min_status = null, int? max_status = null, params int[] ignore_statuses);
|
||||
Task<DataResult<IEnumerable<EnvelopeReceiverDto>>> ReadByUsernameAsync(string username, int? min_status = null, int? max_status = null, EnvelopeQuery? envelopeQuery = null, ReadReceiverQuery? receiverQuery = null, params int[] ignore_statuses);
|
||||
|
||||
Task<DataResult<string?>> ReadLastUsedReceiverNameByMail(string mail);
|
||||
|
||||
|
||||
@@ -3,10 +3,30 @@ using Microsoft.AspNetCore.Mvc;
|
||||
|
||||
namespace EnvelopeGenerator.Application.DTOs
|
||||
{
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
[ApiExplorerSettings(IgnoreApi = true)]
|
||||
public record EmailTemplateDto(
|
||||
int Id,
|
||||
string Name,
|
||||
string Body,
|
||||
string Subject) : IUnique<int>;
|
||||
public record EmailTemplateDto : IUnique<int>
|
||||
{
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public int Id{ get; init; }
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public required string Name { get; init; }
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public required string Body { get; set; }
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public required string Subject { get; set; }
|
||||
};
|
||||
}
|
||||
@@ -1,4 +1,5 @@
|
||||
using EnvelopeGenerator.Common;
|
||||
using MediatR;
|
||||
|
||||
namespace EnvelopeGenerator.Application.EmailTemplates.Commands.Reset;
|
||||
|
||||
@@ -19,4 +20,4 @@ namespace EnvelopeGenerator.Application.EmailTemplates.Commands.Reset;
|
||||
/// 8 - DocumentRejected_REC (Für den ablehnenden Empfänger): Mail an den ablehnenden Empfänger, wenn das Dokument abgelehnt wird.
|
||||
/// 9 - DocumentRejected_REC_2 (Für sonstige Empfänger): Mail an andere Empfänger (Brief), wenn das Dokument abgelehnt wird.
|
||||
/// </param>
|
||||
public record ResetEnvelopeTemplateCommand(int? Id, Constants.EmailTemplateType? Type) : EmailTemplateQuery(Id, Type);
|
||||
public record ResetEnvelopeTemplateCommand(int? Id = null, Constants.EmailTemplateType? Type = null) : EmailTemplateQuery(Id, Type), IRequest;
|
||||
|
||||
@@ -0,0 +1,108 @@
|
||||
using DigitalData.Core.Abstractions.Infrastructure;
|
||||
using EnvelopeGenerator.Application.DTOs;
|
||||
using EnvelopeGenerator.Application.EmailTemplates.Queries.Read;
|
||||
using EnvelopeGenerator.Domain.Entities;
|
||||
using MediatR;
|
||||
|
||||
namespace EnvelopeGenerator.Application.EmailTemplates.Commands.Reset;
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public class ResetEnvelopeTemplateCommandHandler : IRequestHandler<ResetEnvelopeTemplateCommand>
|
||||
{
|
||||
private readonly IRepository<EmailTemplate> _repository;
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="repository"></param>
|
||||
public ResetEnvelopeTemplateCommandHandler(IRepository<EmailTemplate> repository)
|
||||
{
|
||||
_repository = repository;
|
||||
}
|
||||
|
||||
public async Task Handle(ResetEnvelopeTemplateCommand request, CancellationToken cancel)
|
||||
{
|
||||
var temps = request.Id is not null
|
||||
? await _repository.ReadAllAsync<EmailTemplateDto>(t => t.Id == request.Id, cancel)
|
||||
: request.Type is not null
|
||||
? await _repository.ReadAllAsync<EmailTemplateDto>(t => t.Name == request.Type.ToString(), cancel)
|
||||
: await _repository.ReadAllAsync<EmailTemplateDto>(ct: cancel);
|
||||
|
||||
foreach (var temp in temps)
|
||||
{
|
||||
var def = Defaults.Where(t => t.Name == temp.Name).FirstOrDefault();
|
||||
if(def is not null)
|
||||
await _repository.UpdateAsync(def, t => t.Id == temp.Id, cancel);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public static readonly IEnumerable<EmailTemplateDto> Defaults = new List<EmailTemplateDto>()
|
||||
{
|
||||
new(){
|
||||
Id = 1,
|
||||
Name = "DocumentReceived",
|
||||
Body = "Guten Tag [NAME_RECEIVER],<br />\r\n<br /><B><I>\r\n[NAME_SENDER]</I></B> hat Ihnen ein Dokument zum [SIGNATURE_TYPE] gesendet.<br />\r\n<br />\r\nÜber den folgenden Link können Sie das Dokument einsehen und elektronisch unterschreiben: <a href=\"[LINK_TO_DOCUMENT]\">[LINK_TO_DOCUMENT_TEXT]</a><br />\r\n<br />\r\n[MESSAGE]<br />\r\n<br />\r\nMit freundlichen Grüßen<br />\r\n<br />\r\n[NAME_PORTAL]",
|
||||
Subject = "Dokument erhalten: '[DOCUMENT_TITLE]'"
|
||||
},
|
||||
new(){
|
||||
Id = 2,
|
||||
Name = "DocumentDeleted",
|
||||
Body = "Guten Tag [NAME_RECEIVER],<br />\r\n<br /><B><I>\r\n[NAME_SENDER]</I></B> hat den Umschlag <B><I>'[DOCUMENT_TITLE]'</I></B> gelöscht/zurückgezogen.<br /><p>\rBegründung: <br /> <I>[REASON]</I> <p>\r\n<br />\r\nMit freundlichen Grüßen<br />\r\n<br />\r\n[NAME_PORTAL]",
|
||||
Subject = "Umschlag zurückgezogen: '[DOCUMENT_TITLE]'"
|
||||
},
|
||||
new(){
|
||||
Id = 3,
|
||||
Name = "DocumentSigned",
|
||||
Body = "Guten Tag [NAME_RECEIVER],<br />\r\n<br />\r\nhiermit bestätigen wir Ihnen die erfolgreiche Signatur für den Vorgang <B><I>'[DOCUMENT_TITLE]'</I></B>.<br />\r\nWenn alle Vertragspartner unterzeichnet haben, erhalten Sie ebenfalls per email ein unterschriebenes Exemplar mit dem Signierungszertifikat!\r\n<br />\r\nMit freundlichen Grüßen<br />\r\n<br />\r\n[NAME_PORTAL]",
|
||||
Subject = "Dokument unterschrieben: '[DOCUMENT_TITLE]'"
|
||||
},
|
||||
new(){
|
||||
Id = 4,
|
||||
Name = "DocumentCompleted",
|
||||
Body = "Guten Tag [NAME_RECEIVER],<br />\r\n<br />\r\nDer Signaturvorgang <B><I>'[DOCUMENT_TITLE]'</I></B> wurde erfolgreich abgeschlossen.<br />\r\n<br />\r\nSie erhalten das Dokument mit einem detaillierten Ergebnisbericht als Anhang zu dieser Email.<br />\r\n<br />\r\nMit freundlichen Grüßen<br />\r\n<br />\r\n[NAME_PORTAL]",
|
||||
Subject = "Umschlag abgeschlossen: '[DOCUMENT_TITLE]'"
|
||||
},
|
||||
new(){
|
||||
Id = 5,
|
||||
Name = "DocumentAccessCodeReceived",
|
||||
Body = "Guten Tag [NAME_RECEIVER],<br />\r\n<br /><B><I>\r\n[NAME_SENDER]</I></B> hat Ihnen ein Dokument zum [SIGNATURE_TYPE] gesendet. <br />\r\n<br />\r\nVerwenden Sie den folgenden Zugriffscode, um das Dokument einzusehen:<br />\r\n<br />\r\n[DOCUMENT_ACCESS_CODE]<br />\r\n<br />\r\nMit freundlichen Grüßen<br />\r\n<br />\r\n[NAME_PORTAL]",
|
||||
Subject = "Zugriffscode für Dokument erhalten: '[DOCUMENT_TITLE]'"
|
||||
},
|
||||
new(){
|
||||
Id = 6,
|
||||
Name = "DocumentRejected_ADM",
|
||||
Body = "Guten Tag [NAME_SENDER],<p><B><I>[NAME_RECEIVER]</I></B> hat den Umschlag <B><I>'[DOCUMENT_TITLE]'</I></B> mit folgendem Grund abgelehnt: <p>\r\n[REASON] \r\n<p>Der Umschlag wurde auf den Status Rejected gesetzt. <p> \r\nMit freundlichen Grüßen<br />\r\n<br />\r\n[NAME_PORTAL]",
|
||||
Subject = "'[DOCUMENT_TITLE]' - Unterzeichnungsvorgang zurückgezogen"
|
||||
},
|
||||
new(){
|
||||
Id = 9,
|
||||
Name = "DocumentRejected_REC",
|
||||
Body = "Guten Tag [NAME_RECEIVER],\r\n<p>Hiermit bestätigen wir Ihnen die Ablehnung des Unterzeichnungsvorganges <B><I>'[DOCUMENT_TITLE]'</I></B>!<p>Der Vertragsinhaber <B><I>[NAME_SENDER]</I></B> wurde über die Ablehnung informiert. <p> \r\nMit freundlichen Grüßen<br />\r\n<br />\r\n[NAME_PORTAL]",
|
||||
Subject = "'[DOCUMENT_TITLE]' - Bestätigung Ablehnung"
|
||||
},
|
||||
new(){
|
||||
Id = 10,
|
||||
Name = "DocumentRejected_REC_2",
|
||||
Body = "Guten Tag [NAME_RECEIVER],\r\n<p>Der Unterzeichnungsvorganges <B><I>'[DOCUMENT_TITLE]'</I></B> wurde durch einen anderen Vertragspartner abgelehnt! Ihre notwendige Unterzeichnung wurde verworfen.<p> Der Vertragsinhaber <B><I>[NAME_SENDER]</I></B> wird sich bei Bedarf mit Ihnen in Verbindung setzen. <p> \r\nMit freundlichen Grüßen<br />\r\n<br />\r\n[NAME_PORTAL]",
|
||||
Subject = "'[DOCUMENT_TITLE]' - Unterzeichnungsvorgang abgelehnt."
|
||||
},
|
||||
new(){
|
||||
Id = 11,
|
||||
Name = "DocumentShared",
|
||||
Body = "Guten Tag,<br /> <br /><B><I> [NAME_RECEIVER]</I></B> hat Ihnen ein Dokument zum Ansehen gesendet.<br /> <br /> Über den folgenden Link können Sie das Dokument einsehen: <a href=\"[LINK_TO_DOCUMENT]\">[LINK_TO_DOCUMENT_TEXT]</a><br /> <br /> <br /> Mit freundlichen Grüßen<br /> <br /> [NAME_PORTAL]",
|
||||
Subject = "Dokument geteilt: '[DOCUMENT_TITLE]'"
|
||||
},
|
||||
new(){
|
||||
Id = 12,
|
||||
Name = "TotpSecret",
|
||||
Body = "Guten Tag,<br /> <br />Sie können auf Ihren Zwei-Faktor-Authentifizierungscode zugreifen, indem Sie den unten stehenden QR-Code mit einer beliebigen Authentifizierungs-App auf Ihrem Telefon scannen (Google Authenticator, Microsoft Authenticator usw.). Dieser Code ist bis zum [TFA_EXPIRATION] gültig.<br /> <br /> <img src=\"data:image/png;base64,[TFA_QR_CODE]\" style=\"width: 13rem; height: 13rem;\"><br /> <br />\r\n<br /> Mit freundlichen Grüßen<br /> <br /> [NAME_PORTAL]",
|
||||
Subject = "2-Faktor-Verifizierung QR-Code"
|
||||
}
|
||||
};
|
||||
|
||||
}
|
||||
@@ -1,4 +1,5 @@
|
||||
using System.Text.Json.Serialization;
|
||||
using MediatR;
|
||||
using System.Text.Json.Serialization;
|
||||
|
||||
namespace EnvelopeGenerator.Application.EmailTemplates.Commands.Update;
|
||||
|
||||
@@ -12,7 +13,7 @@ namespace EnvelopeGenerator.Application.EmailTemplates.Commands.Update;
|
||||
/// <param name="Subject">
|
||||
/// (Optional) Der neue Betreff der E-Mail. Wenn null, bleibt der vorhandene Betreff unverändert.
|
||||
/// </param>
|
||||
public record UpdateEmailTemplateCommand(string? Body = null, string? Subject = null)
|
||||
public record UpdateEmailTemplateCommand(string? Body = null, string? Subject = null) : IRequest
|
||||
{
|
||||
/// <param>
|
||||
/// Die Abfrage, die die E-Mail-Vorlage darstellt, die aktualisiert werden soll.
|
||||
|
||||
@@ -0,0 +1,43 @@
|
||||
using DigitalData.Core.Abstractions.Infrastructure;
|
||||
using EnvelopeGenerator.Application.DTOs;
|
||||
using EnvelopeGenerator.Application.Exceptions;
|
||||
using EnvelopeGenerator.Domain.Entities;
|
||||
using MediatR;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.EntityFrameworkCore;
|
||||
|
||||
namespace EnvelopeGenerator.Application.EmailTemplates.Commands.Update;
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public class UpdateEmailTemplateCommandHandler : IRequestHandler<UpdateEmailTemplateCommand>
|
||||
{
|
||||
private readonly IRepository<EmailTemplate> _repository;
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="repository"></param>
|
||||
public UpdateEmailTemplateCommandHandler(IRepository<EmailTemplate> repository)
|
||||
{
|
||||
_repository = repository;
|
||||
}
|
||||
|
||||
public async Task Handle(UpdateEmailTemplateCommand request, CancellationToken cancel)
|
||||
{
|
||||
var temp = (request.EmailTemplateQuery?.Id is int id
|
||||
? await _repository.ReadOrDefaultAsync<EmailTemplateDto>(t => t.Id == id, single: false, cancel)
|
||||
: request!.EmailTemplateQuery!.Type is Common.Constants.EmailTemplateType type
|
||||
? await _repository.ReadOrDefaultAsync<EmailTemplateDto>(t => t.Name == type.ToString(), single: false, cancel)
|
||||
: throw new InvalidOperationException("Both id and type is null. Id: " + request.EmailTemplateQuery.Id + ". Type: " + request.EmailTemplateQuery.Type.ToString())) ?? throw new NotFoundException();
|
||||
|
||||
if(request.Body is not null)
|
||||
temp.Body = request.Body;
|
||||
|
||||
if (request.Subject is not null)
|
||||
temp.Subject = request.Subject;
|
||||
|
||||
await _repository.UpdateAsync(temp, t => t.Id == temp.Id, cancel);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,23 @@
|
||||
using AutoMapper;
|
||||
using EnvelopeGenerator.Domain.Entities;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Text;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace EnvelopeGenerator.Application.EmailTemplates.Queries.Read;
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public class ReadEmailTemplateMappingProfile : Profile
|
||||
{
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public ReadEmailTemplateMappingProfile()
|
||||
{
|
||||
CreateMap<EmailTemplate, ReadEmailTemplateResponse>();
|
||||
}
|
||||
}
|
||||
@@ -1,10 +1,12 @@
|
||||
namespace EnvelopeGenerator.Application.EmailTemplates.Queries.Read;
|
||||
using MediatR;
|
||||
|
||||
namespace EnvelopeGenerator.Application.EmailTemplates.Queries.Read;
|
||||
|
||||
|
||||
/// <summary>
|
||||
/// Stellt eine Abfrage dar, um eine E-Mail-Vorlage zu lesen.
|
||||
/// Diese Klasse erbt von <see cref="EmailTemplateQuery"/>.
|
||||
/// </summary>
|
||||
public record ReadEmailTemplateQuery : EmailTemplateQuery
|
||||
public record ReadEmailTemplateQuery : EmailTemplateQuery, IRequest<ReadEmailTemplateResponse?>
|
||||
{
|
||||
}
|
||||
|
||||
@@ -0,0 +1,50 @@
|
||||
using AutoMapper;
|
||||
using EnvelopeGenerator.Application.Contracts.Repositories;
|
||||
using EnvelopeGenerator.Application.DTOs;
|
||||
using EnvelopeGenerator.Common;
|
||||
using MediatR;
|
||||
using Microsoft.AspNetCore.Http;
|
||||
using Microsoft.Extensions.Logging;
|
||||
|
||||
namespace EnvelopeGenerator.Application.EmailTemplates.Queries.Read;
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public class ReadEmailTemplateQueryHandler : IRequestHandler<ReadEmailTemplateQuery, ReadEmailTemplateResponse?>
|
||||
{
|
||||
private readonly IMapper _mapper;
|
||||
|
||||
private readonly IEmailTemplateRepository _repository;
|
||||
|
||||
/// <summary>
|
||||
/// Initialisiert eine neue Instanz der <see cref="EmailTemplateController"/>-Klasse.
|
||||
/// </summary>
|
||||
/// <param name="mapper">
|
||||
/// <param name="repository">
|
||||
/// Die AutoMapper-Instanz, die zum Zuordnen von Objekten verwendet wird.
|
||||
/// </param>
|
||||
public ReadEmailTemplateQueryHandler(IMapper mapper, IEmailTemplateRepository repository)
|
||||
{
|
||||
_mapper = mapper;
|
||||
_repository = repository;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="request"></param>
|
||||
/// <param name="cancellationToken"></param>
|
||||
/// <returns></returns>
|
||||
/// <exception cref="InvalidOperationException"></exception>
|
||||
public async Task<ReadEmailTemplateResponse?> Handle(ReadEmailTemplateQuery request, CancellationToken cancellationToken)
|
||||
{
|
||||
var temp = request.Id is int id
|
||||
? await _repository.ReadByIdAsync(id)
|
||||
: request.Type is Constants.EmailTemplateType type
|
||||
? await _repository.ReadByNameAsync(type)
|
||||
: throw new InvalidOperationException("Either a valid integer ID or a valid EmailTemplateType must be provided in the request.");
|
||||
|
||||
return temp is null ? null : _mapper.Map<ReadEmailTemplateResponse>(temp);
|
||||
}
|
||||
}
|
||||
@@ -3,18 +3,35 @@
|
||||
/// <summary>
|
||||
/// Stellt die Antwort für eine Abfrage von E-Mail-Vorlagen bereit.
|
||||
/// </summary>
|
||||
/// <param name="Id">Die eindeutige Kennung der E-Mail-Vorlage.</param>
|
||||
/// <param name="Type">Der Typ der E-Mail-Vorlage.</param>
|
||||
/// <param name="AddedWhen">Das Datum und die Uhrzeit, wann die Vorlage hinzugefügt wurde.</param>
|
||||
/// <param name="Body">Der Inhalt (Body) der E-Mail-Vorlage. Kann null sein.</param>
|
||||
/// <param name="Subject">Der Betreff der E-Mail-Vorlage. Kann null sein.</param>
|
||||
/// <param name="ChangedWhen">Das Datum und die Uhrzeit, wann die Vorlage zuletzt geändert wurde. Kann null sein.</param>
|
||||
public record ReadEmailTemplateResponse(
|
||||
int Id,
|
||||
int Type,
|
||||
DateTime AddedWhen,
|
||||
string? Body = null,
|
||||
string? Subject = null,
|
||||
DateTime? ChangedWhen = null)
|
||||
public class ReadEmailTemplateResponse
|
||||
{
|
||||
/// <summary>
|
||||
/// Die eindeutige Kennung der E-Mail-Vorlage.
|
||||
/// </summary>
|
||||
public int Id { get; init; }
|
||||
|
||||
/// <summary>
|
||||
/// Der Typ der E-Mail-Vorlage.
|
||||
/// </summary>
|
||||
public int Type { get; init; }
|
||||
|
||||
/// <summary>
|
||||
/// Das Datum und die Uhrzeit, wann die Vorlage hinzugefügt wurde.
|
||||
/// </summary>
|
||||
public DateTime AddedWhen { get; init; }
|
||||
|
||||
/// <summary>
|
||||
/// Der Inhalt (Body) der E-Mail-Vorlage. Kann null sein.
|
||||
/// </summary>
|
||||
public string? Body { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Der Betreff der E-Mail-Vorlage. Kann null sein.
|
||||
/// </summary>
|
||||
public string? Subject { get; set; }
|
||||
|
||||
/// <summary>
|
||||
/// Das Datum und die Uhrzeit, wann die Vorlage zuletzt geändert wurde. Kann null sein.
|
||||
/// </summary>
|
||||
public DateTime? ChangedWhen { get; set; }
|
||||
}
|
||||
|
||||
@@ -14,7 +14,7 @@ namespace EnvelopeGenerator.Application.EnvelopeReceivers.Commands.Create;
|
||||
/// <param name="X">X-Position</param>
|
||||
/// <param name="Y">Y-Position</param>
|
||||
/// <param name="Page">Seite, auf der sie sich befindet</param>
|
||||
public record Signature([Required] int X, [Required] int Y, [Required] int Page);
|
||||
public record Signature([Required] double X, [Required] double Y, [Required] int Page);
|
||||
|
||||
/// <summary>
|
||||
/// DTO für Empfänger, die erstellt oder abgerufen werden sollen.
|
||||
@@ -39,8 +39,11 @@ public record ReceiverGetOrCreateCommand([Required] IEnumerable<Signature> Signa
|
||||
/// <param name="DataAsByte">
|
||||
/// Die Dokumentdaten im Byte-Array-Format. Wird verwendet, wenn das Dokument als Roh-Binärdaten bereitgestellt wird.
|
||||
/// </param>
|
||||
/// <param name="DataAsBase64">
|
||||
/// Die Dokumentdaten im Base64-String-Format. Wird verwendet, wenn das Dokument als Base64-codierter String bereitgestellt wird.
|
||||
/// </param>
|
||||
public record DocumentCreateCommand(byte[]? DataAsByte = null, string? DataAsBase64 = null);
|
||||
public record DocumentCreateCommand(byte[]? DataAsByte = null)
|
||||
{
|
||||
/// <summary>
|
||||
/// Die Dokumentdaten im Base64-String-Format. Wird verwendet, wenn das Dokument als Base64-codierter String bereitgestellt wird.
|
||||
/// </summary>
|
||||
public string? DataAsBase64 { get; set; }
|
||||
};
|
||||
#endregion
|
||||
@@ -0,0 +1,12 @@
|
||||
namespace EnvelopeGenerator.Application.Exceptions;
|
||||
|
||||
public class NotFoundException : Exception
|
||||
{
|
||||
public NotFoundException()
|
||||
{
|
||||
}
|
||||
|
||||
public NotFoundException(string? message) : base(message)
|
||||
{
|
||||
}
|
||||
}
|
||||
@@ -4,17 +4,14 @@ using EnvelopeGenerator.Common;
|
||||
|
||||
namespace EnvelopeGenerator.Application.Histories.Queries.Read;
|
||||
|
||||
//TODO: Add sender query
|
||||
/// <summary>
|
||||
/// Repräsentiert eine Abfrage für die Verlaufshistorie eines Umschlags.
|
||||
/// </summary>
|
||||
/// <param name="EnvelopeId">Die eindeutige Kennung des Umschlags.</param>
|
||||
/// <param name="Envelope">Die Abfrage, die den Umschlag beschreibt.</param>
|
||||
/// <param name="Receiver">Die Abfrage, die den Empfänger beschreibt.</param>
|
||||
/// <param name="Related">Abfrage, die angibt, worauf sich der Datensatz bezieht. Ob er sich auf den Empfänger, den Sender oder das System bezieht, wird durch 0, 1 bzw. 2 dargestellt.</param>
|
||||
/// <param name="OnlyLast">Abfrage zur Steuerung, ob nur der aktuelle Status oder der gesamte Datensatz zurückgegeben wird.</param>
|
||||
public record ReadHistoryQuery(
|
||||
int EnvelopeId,
|
||||
ReadEnvelopeQuery? Envelope = null,
|
||||
ReadReceiverQuery? Receiver = null,
|
||||
int? EnvelopeId = null,
|
||||
Constants.ReferenceType? Related = null,
|
||||
bool? OnlyLast = true);
|
||||
45
EnvelopeGenerator.Application/SQL/DocumentCreateReadSQL.cs
Normal file
45
EnvelopeGenerator.Application/SQL/DocumentCreateReadSQL.cs
Normal file
@@ -0,0 +1,45 @@
|
||||
using Dapper;
|
||||
using EnvelopeGenerator.Application.Contracts.SQLExecutor;
|
||||
using EnvelopeGenerator.Domain.Entities;
|
||||
|
||||
namespace EnvelopeGenerator.Application.SQL;
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public class DocumentCreateReadSQL : ISQL<EnvelopeDocument>
|
||||
{
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public string Raw => @"
|
||||
USE [DD_ECM]
|
||||
|
||||
DECLARE @BYTE_DATA1 as VARBINARY(MAX)
|
||||
SET @BYTE_DATA1 = CONVERT(VARBINARY(MAX),'@Base64')
|
||||
DECLARE @OUT_DOCID int
|
||||
|
||||
EXEC [dbo].[PRSIG_API_ADD_DOC]
|
||||
@ENV_UID = @OUT_UID,
|
||||
@BYTE_DATA = @BYTE_DATA1,
|
||||
@OUT_DOCID = @OUT_DOCID OUTPUT
|
||||
|
||||
SELECT TOP(1) *
|
||||
FROM [dbo].[TBSIG_ENVELOPE_DOCUMENT]
|
||||
WHERE [GUID] = @OUT_DOCID
|
||||
";
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="base64"></param>
|
||||
/// <param name="envelope_uuid"></param>
|
||||
/// <returns></returns>
|
||||
public static DynamicParameters CreateParmas(string base64, string envelope_uuid)
|
||||
{
|
||||
var parameters = new DynamicParameters();
|
||||
parameters.Add("@Base64", base64);
|
||||
parameters.Add("@OUT_UID", envelope_uuid);
|
||||
return parameters;
|
||||
}
|
||||
}
|
||||
@@ -14,12 +14,11 @@ public class EnvelopeReceiverAddReadSQL : ISQL<Envelope>
|
||||
/// </summary>
|
||||
public string Raw => @"
|
||||
USE [DD_ECM]
|
||||
|
||||
DECLARE @OUT_RECEIVER_ID int
|
||||
|
||||
EXEC [dbo].[PRSIG_API_CREATE_RECEIVER]
|
||||
@ENV_UID = @ENV_UID,
|
||||
@EMAIL_ADRESS = @EMAIL_ADRESS ,
|
||||
@EMAIL_ADRESS = @EMAIL_ADRESS,
|
||||
@SALUTATION = @SALUTATION,
|
||||
@PHONE = @PHONE,
|
||||
@OUT_RECEIVER_ID = @OUT_RECEIVER_ID OUTPUT
|
||||
@@ -29,14 +28,14 @@ public class EnvelopeReceiverAddReadSQL : ISQL<Envelope>
|
||||
WHERE [GUID] = @OUT_RECEIVER_ID;
|
||||
";
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="envelope_uuid"></param>
|
||||
/// <param name="emailAddress"></param>
|
||||
/// <param name="salutation"></param>
|
||||
/// <param name="phone"></param>
|
||||
/// <returns></returns>
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="envelope_uuid"></param>
|
||||
/// <param name="emailAddress"></param>
|
||||
/// <param name="salutation"></param>
|
||||
/// <param name="phone"></param>
|
||||
/// <returns></returns>
|
||||
public static DynamicParameters CreateParameters(string envelope_uuid, string emailAddress, string? salutation = null, string? phone = null)
|
||||
{
|
||||
var parameters = new DynamicParameters();
|
||||
|
||||
@@ -10,6 +10,8 @@ using Microsoft.Extensions.Logging;
|
||||
using EnvelopeGenerator.Extensions;
|
||||
using EnvelopeGenerator.Application.DTOs.Messaging;
|
||||
using EnvelopeGenerator.Application.Contracts.Services;
|
||||
using EnvelopeGenerator.Application.Envelopes;
|
||||
using EnvelopeGenerator.Application.Receivers.Queries.Read;
|
||||
|
||||
namespace EnvelopeGenerator.Application.Services;
|
||||
|
||||
@@ -137,9 +139,25 @@ public class EnvelopeReceiverService : BasicCRUDService<IEnvelopeReceiverReposit
|
||||
: Result.Success(code);
|
||||
}
|
||||
|
||||
public async Task<DataResult<IEnumerable<EnvelopeReceiverDto>>> ReadByUsernameAsync(string username, int? min_status = null, int? max_status = null, params int[] ignore_statuses)
|
||||
public async Task<DataResult<IEnumerable<EnvelopeReceiverDto>>> ReadByUsernameAsync(string username, int? min_status = null, int? max_status = null, EnvelopeQuery? envelopeQuery = null, ReadReceiverQuery? receiverQuery = null, params int[] ignore_statuses)
|
||||
{
|
||||
var er_list = await _repository.ReadByUsernameAsync(username: username, min_status: min_status, max_status: max_status, ignore_statuses: ignore_statuses);
|
||||
|
||||
if(envelopeQuery?.Id is int eId)
|
||||
er_list = er_list.Where(er => er.EnvelopeId == eId);
|
||||
|
||||
if (envelopeQuery?.Uuid is string uuid)
|
||||
er_list = er_list.Where(er => er.Envelope?.Uuid == uuid);
|
||||
|
||||
if (envelopeQuery?.Status is int status)
|
||||
er_list = er_list.Where(er => er.Envelope?.Status == status);
|
||||
|
||||
if(receiverQuery?.Id is int id)
|
||||
er_list = er_list.Where(er => er.Receiver?.Id == id);
|
||||
|
||||
if (receiverQuery?.Signature is string signature)
|
||||
er_list = er_list.Where(er => er.Receiver?.Signature == signature);
|
||||
|
||||
var dto_list = _mapper.Map<IEnumerable<EnvelopeReceiverDto>>(er_list);
|
||||
return Result.Success(dto_list);
|
||||
}
|
||||
|
||||
@@ -28,7 +28,6 @@ namespace EnvelopeGenerator.Domain.Entities
|
||||
[Column("ENVELOPE_UUID", TypeName = "nvarchar(36)")]
|
||||
public required string Uuid { get; init; }
|
||||
|
||||
[Required]
|
||||
[Column("MESSAGE", TypeName = "nvarchar(max)")]
|
||||
public string? Message { get; set; }
|
||||
|
||||
@@ -52,7 +51,7 @@ namespace EnvelopeGenerator.Domain.Entities
|
||||
public int? ContractType { get; set; }
|
||||
|
||||
[Column("LANGUAGE", TypeName = "nvarchar(5)")]
|
||||
public required string Language { get; set; }
|
||||
public string? Language { get; set; }
|
||||
|
||||
[Column("SEND_REMINDER_EMAILS")]
|
||||
public bool? SendReminderEmails { get; set; }
|
||||
|
||||
@@ -5,6 +5,12 @@ using EnvelopeGenerator.Application.EmailTemplates.Commands.Reset;
|
||||
using EnvelopeGenerator.Application.EmailTemplates.Queries.Read;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using EnvelopeGenerator.Application.Contracts.Repositories;
|
||||
using EnvelopeGenerator.Application.DTOs;
|
||||
using MediatR;
|
||||
using System.Threading.Tasks;
|
||||
using DigitalData.UserManager.Application.Services;
|
||||
using EnvelopeGenerator.Application.Exceptions;
|
||||
|
||||
namespace EnvelopeGenerator.GeneratorAPI.Controllers;
|
||||
|
||||
@@ -17,17 +23,27 @@ namespace EnvelopeGenerator.GeneratorAPI.Controllers;
|
||||
[Authorize]
|
||||
public class EmailTemplateController : ControllerBase
|
||||
{
|
||||
private readonly ILogger<EmailTemplateController> _logger;
|
||||
|
||||
private readonly IMapper _mapper;
|
||||
|
||||
private readonly IEmailTemplateRepository _repository;
|
||||
|
||||
private readonly IMediator _mediator;
|
||||
|
||||
/// <summary>
|
||||
/// Initialisiert eine neue Instanz der <see cref="EmailTemplateController"/>-Klasse.
|
||||
/// </summary>
|
||||
/// <param name="mapper">
|
||||
/// <param name="repository">
|
||||
/// Die AutoMapper-Instanz, die zum Zuordnen von Objekten verwendet wird.
|
||||
/// </param>
|
||||
public EmailTemplateController(IMapper mapper)
|
||||
public EmailTemplateController(IMapper mapper, IEmailTemplateRepository repository, ILogger<EmailTemplateController> logger, IMediator mediator)
|
||||
{
|
||||
_mapper = mapper;
|
||||
_repository = repository;
|
||||
_logger = logger;
|
||||
_mediator = mediator;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -45,10 +61,26 @@ public class EmailTemplateController : ControllerBase
|
||||
/// <response code="401">Wenn der Benutzer nicht authentifiziert ist.</response>
|
||||
/// <response code="404">Wenn die gesuchte Abfrage nicht gefunden wird.</response>
|
||||
[HttpGet]
|
||||
public IActionResult Get([FromQuery] ReadEmailTemplateQuery? emailTemplate = null)
|
||||
public async Task<IActionResult> Get([FromQuery] ReadEmailTemplateQuery? emailTemplate = null)
|
||||
{
|
||||
// Implementation logic here
|
||||
return Ok(); // Placeholder for actual implementation
|
||||
try
|
||||
{
|
||||
if (emailTemplate is null || (emailTemplate.Id is null && emailTemplate.Type is null))
|
||||
{
|
||||
var temps = await _repository.ReadAllAsync();
|
||||
return Ok(_mapper.Map<IEnumerable<EmailTemplateDto>>(temps));
|
||||
}
|
||||
else
|
||||
{
|
||||
var temp = await _mediator.Send(emailTemplate);
|
||||
return temp is null ? NotFound() : Ok(temp);
|
||||
}
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex, "{Message}", ex.Message);
|
||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -73,19 +105,32 @@ public class EmailTemplateController : ControllerBase
|
||||
/// <response code="401">Wenn der Benutzer nicht authentifiziert ist.</response>
|
||||
/// <response code="404">Wenn die gesuchte Abfrage nicht gefunden wird.</response>
|
||||
[HttpPut]
|
||||
public IActionResult Update([FromQuery] EmailTemplateQuery email, [FromBody] UpdateEmailTemplateCommand? update = null)
|
||||
public async Task<IActionResult> Update([FromQuery] EmailTemplateQuery email, [FromBody] UpdateEmailTemplateCommand? update = null)
|
||||
{
|
||||
if (update is null)
|
||||
try
|
||||
{
|
||||
var reset = _mapper.Map<ResetEnvelopeTemplateCommand>(email);
|
||||
// Logic for resetting the email template
|
||||
}
|
||||
else
|
||||
{
|
||||
update.EmailTemplateQuery = email;
|
||||
// Logic for updating the email template
|
||||
}
|
||||
if (update is null)
|
||||
{
|
||||
var reset = _mapper.Map<ResetEnvelopeTemplateCommand>(email);
|
||||
await _mediator.Send(new ResetEnvelopeTemplateCommand(email?.Id, email?.Type));
|
||||
return Ok();
|
||||
}
|
||||
else
|
||||
{
|
||||
var reset = _mapper.Map<ResetEnvelopeTemplateCommand>(email);
|
||||
await _mediator.Send(update);
|
||||
return Ok();
|
||||
}
|
||||
|
||||
return Ok(); // Placeholder for actual implementation
|
||||
}
|
||||
catch(NotFoundException)
|
||||
{
|
||||
return BadRequest();
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
_logger.LogError(ex, "An unexpected error occurred. {message}", ex.Message);
|
||||
return new StatusCodeResult(StatusCodes.Status500InternalServerError);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -63,7 +63,19 @@ public class EnvelopeController : ControllerBase
|
||||
{
|
||||
if (User.GetId() is int intId)
|
||||
return await _envelopeService.ReadByUserAsync(intId, min_status: envelope.Status, max_status: envelope.Status).ThenAsync(
|
||||
Success: Ok,
|
||||
Success: envelopes =>
|
||||
{
|
||||
if(envelope.Id is int id)
|
||||
envelopes = envelopes.Where(e => e.Id == id);
|
||||
|
||||
if(envelope.Status is int status)
|
||||
envelopes = envelopes.Where(e => e.Status == status);
|
||||
|
||||
if (envelope.Uuid is string uuid)
|
||||
envelopes = envelopes.Where(e => e.Uuid == uuid);
|
||||
|
||||
return Ok(envelope);
|
||||
},
|
||||
Fail: IActionResult (msg, ntc) =>
|
||||
{
|
||||
_logger.LogNotice(ntc);
|
||||
|
||||
@@ -7,9 +7,13 @@ using EnvelopeGenerator.Application.EnvelopeReceivers.Commands.Create;
|
||||
using EnvelopeGenerator.Application.EnvelopeReceivers.Queries.Read;
|
||||
using EnvelopeGenerator.Application.Envelopes.Queries.ReceiverName;
|
||||
using EnvelopeGenerator.Domain.Entities;
|
||||
using EnvelopeGenerator.GeneratorAPI.Models;
|
||||
using MediatR;
|
||||
using Microsoft.AspNetCore.Authorization;
|
||||
using Microsoft.AspNetCore.Mvc;
|
||||
using Microsoft.Data.SqlClient;
|
||||
using Microsoft.Extensions.Options;
|
||||
using System.Data;
|
||||
using System.Threading.Channels;
|
||||
|
||||
namespace EnvelopeGenerator.GeneratorAPI.Controllers;
|
||||
@@ -37,6 +41,10 @@ public class EnvelopeReceiverController : ControllerBase
|
||||
|
||||
private readonly IEnvelopeReceiverExecutor _erExecutor;
|
||||
|
||||
private readonly IDocumentExecutor _documentExecutor;
|
||||
|
||||
private readonly string _cnnStr;
|
||||
|
||||
/// <summary>
|
||||
/// Konstruktor für den EnvelopeReceiverController.
|
||||
/// </summary>
|
||||
@@ -46,7 +54,7 @@ public class EnvelopeReceiverController : ControllerBase
|
||||
/// <param name="mapper"></param>
|
||||
/// <param name="envelopeExecutor"></param>
|
||||
/// <param name="erExecutor"></param>
|
||||
public EnvelopeReceiverController(ILogger<EnvelopeReceiverController> logger, IEnvelopeReceiverService envelopeReceiverService, IMediator mediator, IMapper mapper, IEnvelopeExecutor envelopeExecutor, IEnvelopeReceiverExecutor erExecutor)
|
||||
public EnvelopeReceiverController(ILogger<EnvelopeReceiverController> logger, IEnvelopeReceiverService envelopeReceiverService, IMediator mediator, IMapper mapper, IEnvelopeExecutor envelopeExecutor, IEnvelopeReceiverExecutor erExecutor, IDocumentExecutor documentExecutor, IOptions<ConnectionString> csOpt)
|
||||
{
|
||||
_logger = logger;
|
||||
_erService = envelopeReceiverService;
|
||||
@@ -54,6 +62,8 @@ public class EnvelopeReceiverController : ControllerBase
|
||||
_mapper = mapper;
|
||||
_envelopeExecutor = envelopeExecutor;
|
||||
_erExecutor = erExecutor;
|
||||
_documentExecutor = documentExecutor;
|
||||
_cnnStr = csOpt.Value.Value;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
@@ -83,7 +93,14 @@ public class EnvelopeReceiverController : ControllerBase
|
||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||
}
|
||||
|
||||
return await _erService.ReadByUsernameAsync(username: username).ThenAsync(
|
||||
return await _erService.ReadByUsernameAsync(
|
||||
username: username,
|
||||
min_status: envelopeReceiver.Status?.Min,
|
||||
max_status:envelopeReceiver.Status?.Max,
|
||||
envelopeQuery: envelopeReceiver.Envelope,
|
||||
receiverQuery: envelopeReceiver.Receiver,
|
||||
ignore_statuses: envelopeReceiver.Status?.Ignore ?? Array.Empty<int>())
|
||||
.ThenAsync(
|
||||
Success: Ok,
|
||||
Fail: IActionResult (msg, ntc) =>
|
||||
{
|
||||
@@ -180,8 +197,11 @@ public class EnvelopeReceiverController : ControllerBase
|
||||
CancellationToken cancel = default;
|
||||
int userId = User.GetId();
|
||||
|
||||
#region Create Envelope
|
||||
var envelope = await _envelopeExecutor.CreateEnvelopeAsync(userId, request.Title, request.Message, request.TFAEnabled, cancel);
|
||||
#endregion
|
||||
|
||||
#region Add receivers
|
||||
List<EnvelopeReceiver> sentRecipients = new();
|
||||
List<ReceiverGetOrCreateCommand> unsentRecipients = new();
|
||||
|
||||
@@ -198,6 +218,104 @@ public class EnvelopeReceiverController : ControllerBase
|
||||
var res = _mapper.Map<CreateEnvelopeReceiverResponse>(envelope);
|
||||
res.UnsentRecipients = unsentRecipients;
|
||||
res.SentRecipients = _mapper.Map<IEnumerable<ReceiverReadDto>>(sentRecipients);
|
||||
#endregion
|
||||
|
||||
#region Add document
|
||||
if(request.Document.DataAsBase64 is null)
|
||||
if (request.Document.DataAsByte is null)
|
||||
return BadRequest("No document data is found");
|
||||
else
|
||||
request.Document.DataAsBase64 = Convert.ToBase64String(request.Document.DataAsByte);
|
||||
else if (request.Document.DataAsByte is not null)
|
||||
return BadRequest("Document data cannot be assigned as both byte data and base64 string.");
|
||||
else if (!IsBase64String(request.Document.DataAsBase64))
|
||||
return BadRequest("Document data is not a base64 string");
|
||||
|
||||
var document = await _documentExecutor.CreateDocumentAsync(request.Document.DataAsBase64, envelope.Uuid, cancel);
|
||||
|
||||
if(document is null)
|
||||
return StatusCode(StatusCodes.Status500InternalServerError, "Document creation is failed.");
|
||||
#endregion
|
||||
|
||||
#region Add document element
|
||||
string sql = @"
|
||||
USE [DD_ECM]
|
||||
|
||||
DECLARE @OUT_SUCCESS bit;
|
||||
|
||||
EXEC [dbo].[PRSIG_API_ADD_DOC_RECEIVER_ELEM]
|
||||
@DOC_ID = @DOC_ID,
|
||||
@RECEIVER_ID = @RECEIVER_ID,
|
||||
@POSITION_X = @POSITION_X,
|
||||
@POSITION_Y = @POSITION_Y,
|
||||
@PAGE = @PAGE,
|
||||
@OUT_SUCCESS = @OUT_SUCCESS OUTPUT;
|
||||
|
||||
SELECT @OUT_SUCCESS as [@OUT_SUCCESS];";
|
||||
|
||||
foreach(var rcv in res.SentRecipients)
|
||||
foreach(var sign in request.Receivers.Where(r => r.EmailAddress == rcv.EmailAddress).FirstOrDefault()?.Signatures ?? Array.Empty<Signature>())
|
||||
{
|
||||
using (SqlConnection conn = new(_cnnStr))
|
||||
{
|
||||
conn.Open();
|
||||
|
||||
using SqlCommand cmd = new SqlCommand(sql, conn);
|
||||
cmd.CommandType = CommandType.Text;
|
||||
|
||||
cmd.Parameters.AddWithValue("@DOC_ID", document.Id);
|
||||
cmd.Parameters.AddWithValue("@RECEIVER_ID", rcv.Id);
|
||||
cmd.Parameters.AddWithValue("@POSITION_X", sign.X.ToString());
|
||||
cmd.Parameters.AddWithValue("@POSITION_Y", sign.Y.ToString());
|
||||
cmd.Parameters.AddWithValue("@PAGE", sign.Page.ToString());
|
||||
|
||||
using SqlDataReader reader = cmd.ExecuteReader();
|
||||
if (reader.Read())
|
||||
{
|
||||
bool outSuccess = reader.GetBoolean(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
#region Create history
|
||||
string connectionString = "Server=YOUR_SERVER;Database=YOUR_DATABASE;Trusted_Connection=True;";
|
||||
|
||||
string sql_hist = @"
|
||||
USE [DD_ECM]
|
||||
|
||||
DECLARE @OUT_SUCCESS bit;
|
||||
|
||||
EXEC [dbo].[PRSIG_API_ADD_HISTORY_STATE]
|
||||
@ENV_UID = @ENV_UID,
|
||||
@STATUS_ID = @STATUS_ID,
|
||||
@USER_ID = @USER_ID,
|
||||
@OUT_SUCCESS = @OUT_SUCCESS OUTPUT;
|
||||
|
||||
SELECT @OUT_SUCCESS as [@OUT_SUCCESS];";
|
||||
|
||||
using (SqlConnection conn = new(connectionString))
|
||||
{
|
||||
conn.Open();
|
||||
|
||||
using (SqlCommand cmd = new SqlCommand(sql_hist, conn))
|
||||
{
|
||||
cmd.CommandType = CommandType.Text;
|
||||
|
||||
cmd.Parameters.AddWithValue("@ENV_UID", envelope.Uuid);
|
||||
cmd.Parameters.AddWithValue("@STATUS_ID", 1003);
|
||||
cmd.Parameters.AddWithValue("@USER_ID", userId);
|
||||
|
||||
using (SqlDataReader reader = cmd.ExecuteReader())
|
||||
{
|
||||
if (reader.Read())
|
||||
{
|
||||
bool outSuccess = reader.GetBoolean(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
#endregion
|
||||
|
||||
return Ok(res);
|
||||
}
|
||||
@@ -207,4 +325,26 @@ public class EnvelopeReceiverController : ControllerBase
|
||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
/// <param name="input"></param>
|
||||
/// <returns></returns>
|
||||
public static bool IsBase64String(string input)
|
||||
{
|
||||
if (string.IsNullOrWhiteSpace(input))
|
||||
return false;
|
||||
|
||||
try
|
||||
{
|
||||
Convert.FromBase64String(input);
|
||||
return true;
|
||||
}
|
||||
catch (FormatException)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -131,6 +131,8 @@ public class HistoryController : ControllerBase
|
||||
[Authorize]
|
||||
public async Task<IActionResult> GetAllAsync([FromQuery] ReadHistoryQuery history)
|
||||
{
|
||||
|
||||
|
||||
bool withReceiver = false;
|
||||
bool withSender = false;
|
||||
|
||||
|
||||
@@ -38,17 +38,24 @@ public class ReceiverController : CRUDControllerBaseWithErrorHandling<IReceiverS
|
||||
[HttpGet]
|
||||
public async Task<IActionResult> Get([FromQuery] ReadReceiverQuery receiver)
|
||||
{
|
||||
if (receiver.EmailAddress is null && receiver.Signature is null)
|
||||
if (receiver.Id is null && receiver.EmailAddress is null && receiver.Signature is null)
|
||||
return await base.GetAll();
|
||||
|
||||
try
|
||||
{
|
||||
if(receiver.Id is int id)
|
||||
return await _service.ReadByIdAsync(id).ThenAsync(
|
||||
Success: Ok,
|
||||
Fail: IActionResult (msg, ntc) =>
|
||||
{
|
||||
return NotFound();
|
||||
});
|
||||
|
||||
return await _service.ReadByAsync(emailAddress: receiver.EmailAddress, signature: receiver.Signature).ThenAsync(
|
||||
Success: Ok,
|
||||
Fail: IActionResult (msg, ntc) =>
|
||||
{
|
||||
_logger.LogNotice(ntc);
|
||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||
return NotFound();
|
||||
});
|
||||
}
|
||||
catch (Exception ex)
|
||||
|
||||
@@ -10,9 +10,9 @@
|
||||
<Authors>Digital Data GmbH</Authors>
|
||||
<Company>Digital Data GmbH</Company>
|
||||
<Product>EnvelopeGenerator.GeneratorAPI</Product>
|
||||
<Version>1.2.0</Version>
|
||||
<FileVersion>1.2.0</FileVersion>
|
||||
<AssemblyVersion>1.2.0</AssemblyVersion>
|
||||
<Version>1.2.1</Version>
|
||||
<FileVersion>1.2.1</FileVersion>
|
||||
<AssemblyVersion>1.2.1</AssemblyVersion>
|
||||
<PackageOutputPath>Copyright © 2025 Digital Data GmbH. All rights reserved.</PackageOutputPath>
|
||||
<DocumentationFile>bin\$(Configuration)\$(TargetFramework)\$(AssemblyName).xml</DocumentationFile>
|
||||
</PropertyGroup>
|
||||
|
||||
12
EnvelopeGenerator.GeneratorAPI/Models/ConnectionString.cs
Normal file
12
EnvelopeGenerator.GeneratorAPI/Models/ConnectionString.cs
Normal file
@@ -0,0 +1,12 @@
|
||||
namespace EnvelopeGenerator.GeneratorAPI.Models;
|
||||
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public class ConnectionString
|
||||
{
|
||||
/// <summary>
|
||||
///
|
||||
/// </summary>
|
||||
public string Value { get; set; } = string.Empty;
|
||||
}
|
||||
@@ -90,6 +90,9 @@ builder.Services.AddSwaggerGen(options =>
|
||||
builder.Services.AddOpenApi();
|
||||
// DbContext
|
||||
var connStr = config.GetConnectionString("Default") ?? throw new InvalidOperationException("There is no default connection string in appsettings.json.");
|
||||
|
||||
builder.Services.Configure<ConnectionString>(cs => cs.Value = connStr);
|
||||
|
||||
builder.Services.AddDbContext<EGDbContext>(options => options.UseSqlServer(connStr));
|
||||
|
||||
builder.Services.AddAuthHubClient(config.GetSection("AuthClientParams"));
|
||||
|
||||
@@ -84,6 +84,7 @@ public static class DIExtensions
|
||||
|
||||
services.AddScoped<IEnvelopeExecutor, EnvelopeExecutor>();
|
||||
services.AddScoped<IEnvelopeReceiverExecutor, EnvelopeReceiverExecutor>();
|
||||
services.AddScoped<IDocumentExecutor, DocumentExecutor>();
|
||||
|
||||
if (sqlExecutorConfiguration is not null || sqlExecutorConfigureOptions is not null)
|
||||
services.AddSQLExecutor(sqlExecutorConfiguration, sqlExecutorConfigureOptions);
|
||||
|
||||
@@ -0,0 +1,28 @@
|
||||
using Dapper;
|
||||
using EnvelopeGenerator.Application.Contracts.SQLExecutor;
|
||||
using EnvelopeGenerator.Application.SQL;
|
||||
using EnvelopeGenerator.Domain.Entities;
|
||||
using Microsoft.Data.SqlClient;
|
||||
using Microsoft.Extensions.DependencyInjection;
|
||||
using Microsoft.Extensions.Options;
|
||||
|
||||
namespace EnvelopeGenerator.Infrastructure.Executor;
|
||||
|
||||
public class DocumentExecutor : SQLExecutor, IDocumentExecutor
|
||||
{
|
||||
public DocumentExecutor(IServiceProvider provider, IOptions<SQLExecutorParams> sqlExecutorParamsOptions) : base(provider, sqlExecutorParamsOptions)
|
||||
{
|
||||
}
|
||||
|
||||
public async Task<EnvelopeDocument> CreateDocumentAsync(string base64, string envelope_uuid, CancellationToken cancellation = default)
|
||||
{
|
||||
using var connection = new SqlConnection(Params.ConnectionString);
|
||||
var sql = Provider.GetRequiredService<DocumentCreateReadSQL>();
|
||||
await connection.OpenAsync(cancellation);
|
||||
var parameters = DocumentCreateReadSQL.CreateParmas(base64, envelope_uuid);
|
||||
var documents = await connection.QueryAsync<EnvelopeDocument>(sql.Raw, parameters);
|
||||
return documents.FirstOrDefault()
|
||||
?? throw new InvalidOperationException($"Document creation failed. Parameters:" +
|
||||
$"base64={base64}, envelope_uuid='{envelope_uuid}'.");
|
||||
}
|
||||
}
|
||||
@@ -14,7 +14,7 @@ public class EnvelopeReceiverExecutor: SQLExecutor, IEnvelopeReceiverExecutor
|
||||
{
|
||||
private readonly IEnvelopeReceiverRepository _erRepository;
|
||||
|
||||
public EnvelopeReceiverExecutor(ILogger<EnvelopeExecutor> logger, IServiceProvider provider, IOptions<SQLExecutorParams> sqlExecutorParamsOptions, IEnvelopeReceiverRepository erRepository) : base(provider, sqlExecutorParamsOptions)
|
||||
public EnvelopeReceiverExecutor(IServiceProvider provider, IOptions<SQLExecutorParams> sqlExecutorParamsOptions, IEnvelopeReceiverRepository erRepository) : base(provider, sqlExecutorParamsOptions)
|
||||
{
|
||||
_erRepository = erRepository;
|
||||
}
|
||||
|
||||
@@ -13,7 +13,7 @@ public class EnvelopeHistoryRepository : CRUDRepository<EnvelopeHistory, long, E
|
||||
|
||||
private IQueryable<EnvelopeHistory> By(int? envelopeId = null, string? userReference = null, int? status = null, bool withSender = false, bool withReceiver = false)
|
||||
{
|
||||
var query = _dbSet.AsQueryable();
|
||||
var query = _dbSet.AsNoTracking();
|
||||
|
||||
if (envelopeId is not null)
|
||||
query = query.Where(eh => eh.EnvelopeId == envelopeId);
|
||||
|
||||
Reference in New Issue
Block a user