Compare commits
66 Commits
bugfix/sig
...
fe252b9979
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
fe252b9979 | ||
|
|
f17820e011 | ||
|
|
a21c993cb5 | ||
|
|
dd4afc5ddf | ||
|
|
c220b9e1c8 | ||
|
|
778a498e00 | ||
|
|
48240f2f30 | ||
|
|
e3dfa8dd39 | ||
|
|
6e641395d5 | ||
|
|
fbd09cb570 | ||
|
|
7389909d77 | ||
|
|
ded88383b3 | ||
|
|
1b9b51fbd2 | ||
|
|
afa6dda16f | ||
|
|
994c844f25 | ||
|
|
4551e5dc64 | ||
|
|
ff34e6afab | ||
|
|
a78912260a | ||
|
|
c1e81c546f | ||
|
|
9a950ae37d | ||
|
|
6cec82abd5 | ||
|
|
26616b4cab | ||
|
|
178ec9226d | ||
|
|
0147f525fa | ||
|
|
f0ed6137d1 | ||
|
|
b4ab2c4423 | ||
|
|
5715343651 | ||
|
|
6550be0235 | ||
|
|
99b0dba79f | ||
|
|
2f8d5f1fc8 | ||
|
|
6969f5f93e | ||
|
|
7bbed3890e | ||
|
|
98290c7b28 | ||
|
|
d55006fdda | ||
|
|
b2cc0cb65a | ||
|
|
049827a133 | ||
|
|
b02ab585cb | ||
|
|
c8a5a8627d | ||
|
|
ecf0771f9e | ||
|
|
02c7040b39 | ||
|
|
2cb5d0c0d5 | ||
|
|
9f186afdff | ||
|
|
ec76014ce7 | ||
|
|
e7bc43b339 | ||
|
|
26be8d4565 | ||
|
|
17902c4824 | ||
|
|
396c6014fb | ||
|
|
06175b0c95 | ||
|
|
5375d89d5b | ||
|
|
abd1807b18 | ||
|
|
3f33be452c | ||
|
|
9a4931781a | ||
|
|
b3a2e1559a | ||
|
|
261d1b3db9 | ||
|
|
401d03aac2 | ||
|
|
7871bf72f6 | ||
|
|
7e07afa384 | ||
|
|
251420134a | ||
|
|
701b26289b | ||
|
|
754e3ddc7a | ||
|
|
a0e8cc6989 | ||
|
|
b9f25a0ac4 | ||
|
|
f40ee49977 | ||
|
|
d08e93cbef | ||
|
|
4a48bbb3e2 | ||
|
|
9725e2a729 |
@@ -1,9 +1,11 @@
|
|||||||
using DigitalData.Core.Abstractions;
|
using DigitalData.Core.Abstractions;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
using System.ComponentModel.DataAnnotations.Schema;
|
using System.ComponentModel.DataAnnotations.Schema;
|
||||||
using System.Text.Json.Serialization;
|
using System.Text.Json.Serialization;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs
|
namespace EnvelopeGenerator.Application.DTOs
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record ConfigDto(
|
public record ConfigDto(
|
||||||
string DocumentPath,
|
string DocumentPath,
|
||||||
int SendingProfile,
|
int SendingProfile,
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
using DigitalData.Core.Abstractions;
|
using DigitalData.Core.Abstractions;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs
|
namespace EnvelopeGenerator.Application.DTOs
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record DocumentReceiverElementDto(
|
public record DocumentReceiverElementDto(
|
||||||
int Id,
|
int Id,
|
||||||
int DocumentId,
|
int DocumentId,
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
using DigitalData.Core.Abstractions;
|
using DigitalData.Core.Abstractions;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs
|
namespace EnvelopeGenerator.Application.DTOs
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record DocumentStatusDto(
|
public record DocumentStatusDto(
|
||||||
int Id,
|
int Id,
|
||||||
int EnvelopeId,
|
int EnvelopeId,
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
using DigitalData.Core.Abstractions;
|
using DigitalData.Core.Abstractions;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs
|
namespace EnvelopeGenerator.Application.DTOs
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EmailTemplateDto(
|
public record EmailTemplateDto(
|
||||||
int Id,
|
int Id,
|
||||||
string Name,
|
string Name,
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
using DigitalData.Core.Abstractions;
|
using DigitalData.Core.Abstractions;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs
|
namespace EnvelopeGenerator.Application.DTOs
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeCertificateDto(
|
public record EnvelopeCertificateDto(
|
||||||
int Id,
|
int Id,
|
||||||
int EnvelopeId,
|
int EnvelopeId,
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
using DigitalData.Core.Abstractions;
|
using DigitalData.Core.Abstractions;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs
|
namespace EnvelopeGenerator.Application.DTOs
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeDocumentDto
|
public record EnvelopeDocumentDto
|
||||||
(
|
(
|
||||||
int Id,
|
int Id,
|
||||||
|
|||||||
@@ -2,9 +2,11 @@
|
|||||||
using DigitalData.EmailProfilerDispatcher.Abstraction.Attributes;
|
using DigitalData.EmailProfilerDispatcher.Abstraction.Attributes;
|
||||||
using DigitalData.UserManager.Application.DTOs.User;
|
using DigitalData.UserManager.Application.DTOs.User;
|
||||||
using EnvelopeGenerator.Domain.Entities;
|
using EnvelopeGenerator.Domain.Entities;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs
|
namespace EnvelopeGenerator.Application.DTOs
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeDto() : IUnique<int>
|
public record EnvelopeDto() : IUnique<int>
|
||||||
{
|
{
|
||||||
public int Id { get; set; }
|
public int Id { get; set; }
|
||||||
|
|||||||
@@ -1,5 +1,8 @@
|
|||||||
namespace EnvelopeGenerator.Application.DTOs.EnvelopeHistory
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.DTOs.EnvelopeHistory
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeHistoryCreateDto(
|
public record EnvelopeHistoryCreateDto(
|
||||||
int EnvelopeId,
|
int EnvelopeId,
|
||||||
string UserReference,
|
string UserReference,
|
||||||
|
|||||||
@@ -2,10 +2,12 @@
|
|||||||
using DigitalData.Core.DTO;
|
using DigitalData.Core.DTO;
|
||||||
using DigitalData.UserManager.Application.DTOs.User;
|
using DigitalData.UserManager.Application.DTOs.User;
|
||||||
using EnvelopeGenerator.Application.DTOs.Receiver;
|
using EnvelopeGenerator.Application.DTOs.Receiver;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
using static EnvelopeGenerator.Common.Constants;
|
using static EnvelopeGenerator.Common.Constants;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs.EnvelopeHistory
|
namespace EnvelopeGenerator.Application.DTOs.EnvelopeHistory
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeHistoryDto(
|
public record EnvelopeHistoryDto(
|
||||||
long Id,
|
long Id,
|
||||||
int EnvelopeId,
|
int EnvelopeId,
|
||||||
|
|||||||
@@ -1,8 +1,10 @@
|
|||||||
using DigitalData.Core.Abstractions;
|
using DigitalData.Core.Abstractions;
|
||||||
using DigitalData.EmailProfilerDispatcher.Abstraction.Attributes;
|
using DigitalData.EmailProfilerDispatcher.Abstraction.Attributes;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiver
|
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiver
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeReceiverBasicDto() : IUnique<(int Envelope, int Receiver)>
|
public record EnvelopeReceiverBasicDto() : IUnique<(int Envelope, int Receiver)>
|
||||||
{
|
{
|
||||||
public (int Envelope, int Receiver) Id => (Envelope: EnvelopeId, Receiver: ReceiverId);
|
public (int Envelope, int Receiver) Id => (Envelope: EnvelopeId, Receiver: ReceiverId);
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
using EnvelopeGenerator.Application.DTOs.Receiver;
|
using EnvelopeGenerator.Application.DTOs.Receiver;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiver
|
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiver
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeReceiverDto() : EnvelopeReceiverBasicDto()
|
public record EnvelopeReceiverDto() : EnvelopeReceiverBasicDto()
|
||||||
{
|
{
|
||||||
public EnvelopeDto? Envelope { get; set; }
|
public EnvelopeDto? Envelope { get; set; }
|
||||||
|
|||||||
@@ -1,5 +1,8 @@
|
|||||||
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiver
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiver
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeReceiverSecretDto() : EnvelopeReceiverDto()
|
public record EnvelopeReceiverSecretDto() : EnvelopeReceiverDto()
|
||||||
{
|
{
|
||||||
public string? AccessCode { get; init; }
|
public string? AccessCode { get; init; }
|
||||||
|
|||||||
@@ -1,8 +1,10 @@
|
|||||||
using System.ComponentModel.DataAnnotations;
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
using System.ComponentModel.DataAnnotations;
|
||||||
using System.Text.Json.Serialization;
|
using System.Text.Json.Serialization;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiverReadOnly
|
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiverReadOnly
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeReceiverReadOnlyCreateDto(
|
public record EnvelopeReceiverReadOnlyCreateDto(
|
||||||
DateTime DateValid)
|
DateTime DateValid)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
using EnvelopeGenerator.Application.DTOs.Receiver;
|
using EnvelopeGenerator.Application.DTOs.Receiver;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiverReadOnly
|
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiverReadOnly
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeReceiverReadOnlyDto(
|
public record EnvelopeReceiverReadOnlyDto(
|
||||||
long Id,
|
long Id,
|
||||||
long EnvelopeId,
|
long EnvelopeId,
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
using DigitalData.Core.Abstractions;
|
using DigitalData.Core.Abstractions;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiverReadOnly
|
namespace EnvelopeGenerator.Application.DTOs.EnvelopeReceiverReadOnly
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeReceiverReadOnlyUpdateDto(
|
public record EnvelopeReceiverReadOnlyUpdateDto(
|
||||||
long Id,
|
long Id,
|
||||||
DateTime DateValid,
|
DateTime DateValid,
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
using DigitalData.Core.Abstractions;
|
using DigitalData.Core.Abstractions;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs
|
namespace EnvelopeGenerator.Application.DTOs
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record EnvelopeTypeDto(
|
public record EnvelopeTypeDto(
|
||||||
int Id,
|
int Id,
|
||||||
string Title,
|
string Title,
|
||||||
|
|||||||
@@ -1,4 +1,7 @@
|
|||||||
namespace EnvelopeGenerator.Application.DTOs.Messaging
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.DTOs.Messaging
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public class GtxMessagingResponse : Dictionary<string, object?> { }
|
public class GtxMessagingResponse : Dictionary<string, object?> { }
|
||||||
}
|
}
|
||||||
@@ -1,5 +1,8 @@
|
|||||||
namespace EnvelopeGenerator.Application.DTOs.Messaging
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.DTOs.Messaging
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record SmsResponse
|
public record SmsResponse
|
||||||
{
|
{
|
||||||
public required bool Ok { get; init; }
|
public required bool Ok { get; init; }
|
||||||
|
|||||||
@@ -1,9 +1,11 @@
|
|||||||
using System.ComponentModel.DataAnnotations;
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
using System.ComponentModel.DataAnnotations;
|
||||||
using System.Security.Cryptography;
|
using System.Security.Cryptography;
|
||||||
using System.Text;
|
using System.Text;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs.Receiver
|
namespace EnvelopeGenerator.Application.DTOs.Receiver
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record ReceiverCreateDto([EmailAddress] string EmailAddress, string? TotpSecretkey = null)
|
public record ReceiverCreateDto([EmailAddress] string EmailAddress, string? TotpSecretkey = null)
|
||||||
{
|
{
|
||||||
public string Signature => sha256HexOfMail.Value;
|
public string Signature => sha256HexOfMail.Value;
|
||||||
|
|||||||
@@ -2,10 +2,12 @@
|
|||||||
using DigitalData.Core.DTO;
|
using DigitalData.Core.DTO;
|
||||||
using DigitalData.EmailProfilerDispatcher.Abstraction.Attributes;
|
using DigitalData.EmailProfilerDispatcher.Abstraction.Attributes;
|
||||||
using EnvelopeGenerator.Application.DTOs.EnvelopeReceiver;
|
using EnvelopeGenerator.Application.DTOs.EnvelopeReceiver;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
using System.Text.Json.Serialization;
|
using System.Text.Json.Serialization;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs.Receiver;
|
namespace EnvelopeGenerator.Application.DTOs.Receiver;
|
||||||
|
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record ReceiverReadDto(
|
public record ReceiverReadDto(
|
||||||
int Id,
|
int Id,
|
||||||
string EmailAddress,
|
string EmailAddress,
|
||||||
|
|||||||
@@ -1,5 +1,7 @@
|
|||||||
using DigitalData.Core.Abstractions;
|
using DigitalData.Core.Abstractions;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs.Receiver;
|
namespace EnvelopeGenerator.Application.DTOs.Receiver;
|
||||||
|
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record ReceiverUpdateDto(int Id, string? TotpSecretkey = null, DateTime? TfaRegDeadline = null) : IUnique<int>;
|
public record ReceiverUpdateDto(int Id, string? TotpSecretkey = null, DateTime? TfaRegDeadline = null) : IUnique<int>;
|
||||||
@@ -1,7 +1,9 @@
|
|||||||
using DigitalData.Core.Abstractions;
|
using DigitalData.Core.Abstractions;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.Application.DTOs
|
namespace EnvelopeGenerator.Application.DTOs
|
||||||
{
|
{
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
public record UserReceiverDto(
|
public record UserReceiverDto(
|
||||||
int Id,
|
int Id,
|
||||||
int UserId,
|
int UserId,
|
||||||
|
|||||||
@@ -0,0 +1,22 @@
|
|||||||
|
using EnvelopeGenerator.Common;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.EmailTemplates.Commands.Reset;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Ein Befehl zum Zurücksetzen einer E-Mail-Vorlage auf die Standardwerte.
|
||||||
|
/// Erbt von <see cref="EmailTemplateQuery"/> und ermöglicht die Angabe einer optionalen ID und eines Typs der E-Mail-Vorlage.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Id">Die optionale ID der E-Mail-Vorlage, die zurückgesetzt werden soll.</param>
|
||||||
|
/// <param name="Type">Der Typ der E-Mail-Vorlage, z. B. <see cref="Constants.EmailTemplateType"/> (optional). Beispiele:
|
||||||
|
/// 0 - DocumentReceived: Benachrichtigung über den Empfang eines Dokuments.
|
||||||
|
/// 1 - DocumentSigned: Benachrichtigung über die Unterzeichnung eines Dokuments.
|
||||||
|
/// 2 - DocumentDeleted: Benachrichtigung über das Löschen eines Dokuments.
|
||||||
|
/// 3 - DocumentCompleted: Benachrichtigung über den Abschluss eines Dokuments.
|
||||||
|
/// 4 - DocumentAccessCodeReceived: Benachrichtigung über den Erhalt eines Zugangscodes.
|
||||||
|
/// 5 - DocumentShared: Benachrichtigung über das Teilen eines Dokuments.
|
||||||
|
/// 6 - TotpSecret: Benachrichtigung über ein TOTP-Geheimnis.
|
||||||
|
/// 7 - DocumentRejected_ADM (Für den Absender): Mail an den Absender, wenn das Dokument abgelehnt wird.
|
||||||
|
/// 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);
|
||||||
@@ -0,0 +1,22 @@
|
|||||||
|
using System.Text.Json.Serialization;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.EmailTemplates.Commands.Update;
|
||||||
|
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Befehl zum Aktualisieren einer E-Mail-Vorlage.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Body">
|
||||||
|
/// (Optional)Der neue Inhalt des E-Mail-Textkörpers. Wenn null, bleibt der vorhandene Inhalt unverändert.
|
||||||
|
/// </param>
|
||||||
|
/// <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)
|
||||||
|
{
|
||||||
|
/// <param>
|
||||||
|
/// Die Abfrage, die die E-Mail-Vorlage darstellt, die aktualisiert werden soll.
|
||||||
|
/// </param>
|
||||||
|
[JsonIgnore]
|
||||||
|
public EmailTemplateQuery? EmailTemplateQuery { get; set; }
|
||||||
|
}
|
||||||
@@ -0,0 +1,24 @@
|
|||||||
|
using EnvelopeGenerator.Common;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.EmailTemplates;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Repräsentiert eine Abfrage für E-Mail-Vorlagen, die für Absender und Empfänger von Umschlägen verwendet werden.
|
||||||
|
/// Die Standardkultur ist "de-DE".
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Id">Die eindeutige Kennung der E-Mail-Vorlage (optional).</param>
|
||||||
|
/// <param name="Type">Der Typ der E-Mail-Vorlage, z. B. <see cref="Constants.EmailTemplateType"/> (optional). Beispiele:
|
||||||
|
/// 0 - DocumentReceived: Benachrichtigung über den Empfang eines Dokuments.
|
||||||
|
/// 1 - DocumentSigned: Benachrichtigung über die Unterzeichnung eines Dokuments.
|
||||||
|
/// 2 - DocumentDeleted: Benachrichtigung über das Löschen eines Dokuments.
|
||||||
|
/// 3 - DocumentCompleted: Benachrichtigung über den Abschluss eines Dokuments.
|
||||||
|
/// 4 - DocumentAccessCodeReceived: Benachrichtigung über den Erhalt eines Zugangscodes.
|
||||||
|
/// 5 - DocumentShared: Benachrichtigung über das Teilen eines Dokuments.
|
||||||
|
/// 6 - TotpSecret: Benachrichtigung über ein TOTP-Geheimnis.
|
||||||
|
/// 7 - DocumentRejected_ADM (Für den Absender): Mail an den Absender, wenn das Dokument abgelehnt wird.
|
||||||
|
/// 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 EmailTemplateQuery(int? Id = null, Constants.EmailTemplateType? Type = null)
|
||||||
|
{
|
||||||
|
}
|
||||||
@@ -0,0 +1,10 @@
|
|||||||
|
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
|
||||||
|
{
|
||||||
|
}
|
||||||
@@ -0,0 +1,20 @@
|
|||||||
|
namespace EnvelopeGenerator.Application.EmailTemplates.Queries.Read;
|
||||||
|
|
||||||
|
/// <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)
|
||||||
|
{
|
||||||
|
}
|
||||||
@@ -1,9 +1,11 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net7.0</TargetFramework>
|
<TargetFrameworks>net7.0;net8.0;net9.0</TargetFrameworks>
|
||||||
<ImplicitUsings>enable</ImplicitUsings>
|
<ImplicitUsings>enable</ImplicitUsings>
|
||||||
<Nullable>enable</Nullable>
|
<Nullable>enable</Nullable>
|
||||||
|
<GenerateDocumentationFile>true</GenerateDocumentationFile>
|
||||||
|
<DocumentationFile>bin\$(Configuration)\$(TargetFramework)\$(AssemblyName).xml</DocumentationFile>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
@@ -17,6 +19,7 @@
|
|||||||
<PackageReference Include="DigitalData.Core.Client" Version="2.0.3" />
|
<PackageReference Include="DigitalData.Core.Client" Version="2.0.3" />
|
||||||
<PackageReference Include="DigitalData.Core.DTO" Version="2.0.0" />
|
<PackageReference Include="DigitalData.Core.DTO" Version="2.0.0" />
|
||||||
<PackageReference Include="DigitalData.EmailProfilerDispatcher" Version="2.0.0" />
|
<PackageReference Include="DigitalData.EmailProfilerDispatcher" Version="2.0.0" />
|
||||||
|
<PackageReference Include="MediatR" Version="11.1.0" />
|
||||||
<PackageReference Include="Microsoft.AspNetCore.Authentication.JwtBearer" Version="7.0.18" />
|
<PackageReference Include="Microsoft.AspNetCore.Authentication.JwtBearer" Version="7.0.18" />
|
||||||
<PackageReference Include="Otp.NET" Version="1.4.0" />
|
<PackageReference Include="Otp.NET" Version="1.4.0" />
|
||||||
<PackageReference Include="QRCoder" Version="1.6.0" />
|
<PackageReference Include="QRCoder" Version="1.6.0" />
|
||||||
|
|||||||
@@ -0,0 +1,59 @@
|
|||||||
|
using MediatR;
|
||||||
|
using System.ComponentModel.DataAnnotations;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.EnvelopeReceivers.Commands.Create;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Befehl zur Erstellung eines Umschlags.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Title">Der Titel des Umschlags. Dies ist ein Pflichtfeld.</param>
|
||||||
|
/// <param name="Message">Die Nachricht, die im Umschlag enthalten sein soll. Dies ist ein Pflichtfeld.</param>
|
||||||
|
/// <param name="Document">Das mit dem Umschlag verknüpfte Dokument. Dies ist ein Pflichtfeld.</param>
|
||||||
|
/// <param name="Receivers">Eine Sammlung von Empfängern, die den Umschlag erhalten. Dies ist ein Pflichtfeld.</param>
|
||||||
|
/// <param name="TFAEnabled">Gibt an, ob die Zwei-Faktor-Authentifizierung für den Umschlag aktiviert ist. Standardmäßig false.</param>
|
||||||
|
public record CreateEnvelopeReceiverCommand(
|
||||||
|
[Required] string Title,
|
||||||
|
[Required] string Message,
|
||||||
|
[Required] DocumentCreateCommand Document,
|
||||||
|
[Required] IEnumerable<ReceiverGetOrCreateCommand> Receivers,
|
||||||
|
bool TFAEnabled = false
|
||||||
|
) : IRequest;
|
||||||
|
|
||||||
|
#region DTOs
|
||||||
|
/// <summary>
|
||||||
|
/// Signaturposition auf einem Dokument.
|
||||||
|
/// </summary>
|
||||||
|
/// <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);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// DTO für Empfänger, die erstellt oder abgerufen werden sollen.
|
||||||
|
/// Wenn nicht, wird sie erstellt und mit einer Signatur versehen.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Signatures">Unterschriften auf Dokumenten.</param>
|
||||||
|
/// <param name="Salution">Der Name, mit dem der Empfänger angesprochen werden soll. Bei Null oder keinem Wert wird der zuletzt verwendete Name verwendet.</param>
|
||||||
|
/// <param name="PhoneNumber">Sollte mit Vorwahl geschrieben werden</param>
|
||||||
|
public record ReceiverGetOrCreateCommand([Required] IEnumerable<Signature> Signatures, string? Salution = null, string? PhoneNumber = null)
|
||||||
|
{
|
||||||
|
private string _emailAddress = string.Empty;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// E-Mail-Adresse des Empfängers.
|
||||||
|
/// </summary>
|
||||||
|
[Required]
|
||||||
|
public required string EmailAddress { get => _emailAddress.ToLower(); init => _emailAddress = _emailAddress.ToLower(); }
|
||||||
|
};
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// DTO zum Erstellen eines Dokuments.
|
||||||
|
/// </summary>
|
||||||
|
/// <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);
|
||||||
|
#endregion
|
||||||
@@ -0,0 +1,47 @@
|
|||||||
|
using EnvelopeGenerator.Application.Histories;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.EnvelopeReceivers;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Stellt eine Abfrage für einen Envelope-Empfänger dar.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Status">Der Status der Abfrage, optional.</param>
|
||||||
|
public record EnvelopeReceiverQuery(EnvelopeStatusQuery? Status = null);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Repräsentiert den Status eines Umschlags und dessen Beziehung zum Empfänger. (vgl. auch <see cref="Common.Constants.EnvelopeStatus"/>
|
||||||
|
/// Invalid (0): Ungültiger Status.
|
||||||
|
/// EnvelopeCreated (1001): Der Umschlag wurde erstellt.
|
||||||
|
/// EnvelopeSaved (1002): Der Umschlag wurde gespeichert.
|
||||||
|
/// EnvelopeQueued (1003): Der Umschlag wurde zur Verarbeitung eingeplant.
|
||||||
|
/// EnvelopeSent (1004): Der Umschlag wurde versendet. (Nicht verwendet)
|
||||||
|
/// EnvelopePartlySigned (1005): Der Umschlag wurde teilweise unterschrieben.
|
||||||
|
/// EnvelopeCompletelySigned (1006): Der Umschlag wurde vollständig unterschrieben.
|
||||||
|
/// EnvelopeReportCreated (1007): Ein Abschlussbericht wurde für den Umschlag erstellt.
|
||||||
|
/// EnvelopeArchived (1008): Der Umschlag wurde archiviert.
|
||||||
|
/// EnvelopeDeleted (1009): Der Umschlag wurde gelöscht.
|
||||||
|
/// AccessCodeRequested (2001): Der Zugriffscode wurde angefordert.
|
||||||
|
/// AccessCodeCorrect (2002): Der Zugriffscode war korrekt.
|
||||||
|
/// AccessCodeIncorrect (2003): Der Zugriffscode war falsch.
|
||||||
|
/// DocumentOpened (2004): Das Dokument wurde geöffnet.
|
||||||
|
/// DocumentSigned (2005): Ein Dokument wurde unterschrieben.
|
||||||
|
/// SignatureConfirmed (2006): Die Signatur wurde bestätigt.
|
||||||
|
/// DocumentRejected (2007): Ein Dokument wurde abgelehnt.
|
||||||
|
/// EnvelopeShared (2008): Der Umschlag wurde geteilt.
|
||||||
|
/// EnvelopeViewed (2009): Der Umschlag wurde angesehen.
|
||||||
|
/// DocumentForwarded (4001): Das Dokument wurde weitergeleitet.
|
||||||
|
/// MessageInvitationSent (3001): Einladung wurde gesendet (vom Trigger verwendet).
|
||||||
|
/// MessageAccessCodeSent (3002): Zugriffscode wurde gesendet.
|
||||||
|
/// MessageConfirmationSent (3003): Bestätigungsnachricht wurde gesendet.
|
||||||
|
/// MessageDeletionSent (3004): Löschbenachrichtigung wurde gesendet.
|
||||||
|
/// MessageCompletionSent (3005): Abschlussbenachrichtigung wurde gesendet.
|
||||||
|
/// <param name="Min">Der minimale Statuswert, der berücksichtigt werden soll.</param>
|
||||||
|
/// <param name="Max">Der maximale Statuswert, der berücksichtigt werden soll.</param>
|
||||||
|
/// <param name="Ignore">Eine Liste von Statuswerten, die ignoriert werden sollen.</param>
|
||||||
|
/// </summary>
|
||||||
|
public record EnvelopeStatusQuery(
|
||||||
|
int? Min = null,
|
||||||
|
int? Max = null,
|
||||||
|
int[]? Ignore = null)
|
||||||
|
{
|
||||||
|
}
|
||||||
@@ -0,0 +1,30 @@
|
|||||||
|
using EnvelopeGenerator.Application.Histories;
|
||||||
|
using EnvelopeGenerator.Application.Envelopes.Queries.Read;
|
||||||
|
using EnvelopeGenerator.Application.Receivers.Queries.Read;
|
||||||
|
using MediatR;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.EnvelopeReceivers.Queries.Read;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Repräsentiert eine Abfrage zum Lesen eines Envelope-Empfängers.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// Diese Abfrage kombiniert Informationen über einen Umschlag (<see cref="ReadEnvelopeQuery"/>)
|
||||||
|
/// und einen Empfänger (<see cref="ReadReceiverQuery"/>), um eine vollständige Antwort
|
||||||
|
/// (<see cref="ReadEnvelopeReceiverResponse"/>) zu generieren.
|
||||||
|
/// Die Antwort enthält Details wie den Status, die Zuordnung zwischen Umschlag und Empfänger
|
||||||
|
/// sowie zusätzliche Metadaten.
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="Status">Umschlag oder Empfängerstatus.</param>
|
||||||
|
public record ReadEnvelopeReceiverQuery(EnvelopeStatusQuery? Status = null) : EnvelopeReceiverQuery(Status), IRequest<ReadEnvelopeReceiverResponse>
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Der Umschlag, der mit dem Empfänger verknüpft ist.
|
||||||
|
/// </summary>
|
||||||
|
public ReadEnvelopeQuery? Envelope { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Der Empfänger, der mit dem Umschlag verknüpft ist.
|
||||||
|
/// </summary>
|
||||||
|
public ReadReceiverQuery? Receiver { get; init; }
|
||||||
|
};
|
||||||
@@ -0,0 +1,94 @@
|
|||||||
|
using DigitalData.EmailProfilerDispatcher.Abstraction.Attributes;
|
||||||
|
using EnvelopeGenerator.Application.Envelopes.Queries.Read;
|
||||||
|
using EnvelopeGenerator.Application.Receivers.Queries.Read;
|
||||||
|
using System.ComponentModel.DataAnnotations;
|
||||||
|
using System.ComponentModel.DataAnnotations.Schema;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.EnvelopeReceivers.Queries.Read;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Repräsentiert die Antwort für das Lesen eines Envelope-Empfängers.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// Diese Klasse enthält Informationen über einen spezifischen Empfänger eines Umschlags (Envelope).
|
||||||
|
/// Sie verknüpft die Empfängerinformationen mit den zugehörigen Umschlagsdaten und bietet zusätzliche Metadaten.
|
||||||
|
/// </remarks>
|
||||||
|
/// <param name="UserId">Die eindeutige Kennung des Benutzers, der den Empfänger erstellt hat.</param>
|
||||||
|
/// <param name="Status">Der Status des Empfängers als numerischer Wert.</param>
|
||||||
|
public record ReadEnvelopeReceiverResponse(int UserId, int Status)
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Gibt die zusammengesetzte Kennung des Empfängers zurück, bestehend aus der Umschlags-ID und der Empfänger-ID.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// Diese Eigenschaft kombiniert die eindeutige Kennung des Umschlags (EnvelopeId) und die des Empfängers (ReceiverId)
|
||||||
|
/// zu einer einzigen, leicht zugänglichen Struktur.
|
||||||
|
/// </remarks>
|
||||||
|
[NotMapped]
|
||||||
|
public (int Envelope, int Receiver) Id => (Envelope: EnvelopeId, Receiver: ReceiverId);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Die eindeutige Kennung des zugehörigen Umschlags.
|
||||||
|
/// </summary>
|
||||||
|
[Required]
|
||||||
|
public int EnvelopeId { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Die eindeutige Kennung des Empfängers.
|
||||||
|
/// </summary>
|
||||||
|
[Required]
|
||||||
|
public int ReceiverId { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Die Reihenfolge des Empfängers innerhalb des Umschlags.
|
||||||
|
/// </summary>
|
||||||
|
public int Sequence { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Der Name des Empfängers. Kann als Platzhalter verwendet werden.
|
||||||
|
/// </summary>
|
||||||
|
[TemplatePlaceholder("[NAME_RECEIVER]")]
|
||||||
|
public string? Name { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Die Berufsbezeichnung des Empfängers.
|
||||||
|
/// </summary>
|
||||||
|
public string? JobTitle { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Der Firmenname des Empfängers.
|
||||||
|
/// </summary>
|
||||||
|
public string? CompanyName { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Eine private Nachricht, die mit dem Empfänger verknüpft ist.
|
||||||
|
/// </summary>
|
||||||
|
public string? PrivateMessage { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Das Datum und die Uhrzeit, wann der Empfänger hinzugefügt wurde.
|
||||||
|
/// </summary>
|
||||||
|
public DateTime AddedWhen { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Das Datum und die Uhrzeit, wann der Empfänger zuletzt geändert wurde (falls vorhanden).
|
||||||
|
/// </summary>
|
||||||
|
public DateTime? ChangedWhen { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gibt an, ob der Empfänger eine Telefonnummer hat.
|
||||||
|
/// </summary>
|
||||||
|
public bool HasPhoneNumber { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Die zugehörigen Umschlagsdaten.
|
||||||
|
/// </summary>
|
||||||
|
[Required]
|
||||||
|
public required ReadEnvelopeResponse Envelope { get; init; }
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Die Liste der Empfängerinformationen.
|
||||||
|
/// </summary>
|
||||||
|
[Required]
|
||||||
|
public IEnumerable<ReadReceiverResponse> Receiver { get; init; } = new List<ReadReceiverResponse>();
|
||||||
|
}
|
||||||
16
EnvelopeGenerator.Application/Envelopes/EnvelopeQuery.cs
Normal file
16
EnvelopeGenerator.Application/Envelopes/EnvelopeQuery.cs
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
using MediatR;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.Envelopes;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Repräsentiert eine Abfrage für Umschläge.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Id">Die eindeutige Kennung des Umschlags.</param>
|
||||||
|
/// <param name="Status">Der Status des Umschlags.</param>
|
||||||
|
/// <param name="Uuid">Die universell eindeutige Kennung des Umschlags.</param>
|
||||||
|
public record EnvelopeQuery(
|
||||||
|
int? Id = null,
|
||||||
|
int? Status = null,
|
||||||
|
string? Uuid = null) : IRequest
|
||||||
|
{
|
||||||
|
};
|
||||||
@@ -0,0 +1,8 @@
|
|||||||
|
namespace EnvelopeGenerator.Application.Envelopes.Queries.Read;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Stellt eine Abfrage zum Lesen von Briefumschlägen dar.
|
||||||
|
/// </summary>
|
||||||
|
public record ReadEnvelopeQuery : EnvelopeQuery
|
||||||
|
{
|
||||||
|
}
|
||||||
@@ -0,0 +1,36 @@
|
|||||||
|
using EnvelopeGenerator.Common;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.Envelopes.Queries.Read;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Repräsentiert die Antwort für das Lesen eines Umschlags.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Id">Die eindeutige Kennung des Umschlags.</param>
|
||||||
|
/// <param name="UserId">Die Kennung des Benutzers, der den Umschlag erstellt hat.</param>
|
||||||
|
/// <param name="Status">Der Status des Umschlags als numerischer Wert.</param>
|
||||||
|
/// <param name="Uuid">Die universelle eindeutige Kennung (UUID) des Umschlags.</param>
|
||||||
|
/// <param name="Message">Eine optionale Nachricht, die mit dem Umschlag verknüpft ist.</param>
|
||||||
|
/// <param name="AddedWhen">Das Datum und die Uhrzeit, wann der Umschlag hinzugefügt wurde.</param>
|
||||||
|
/// <param name="ChangedWhen">Das Datum und die Uhrzeit, wann der Umschlag zuletzt geändert wurde (falls vorhanden).</param>
|
||||||
|
/// <param name="Title">Ein optionaler Titel des Umschlags.</param>
|
||||||
|
/// <param name="Language">Die Sprache, die mit dem Umschlag verknüpft ist.</param>
|
||||||
|
/// <param name="TFAEnabled">Gibt an, ob die Zwei-Faktor-Authentifizierung (TFA) aktiviert ist.</param>
|
||||||
|
/// <param name="User">Das Benutzerobjekt, das mit dem Umschlag verknüpft ist.</param>
|
||||||
|
public record ReadEnvelopeResponse(
|
||||||
|
int Id,
|
||||||
|
int UserId,
|
||||||
|
int Status,
|
||||||
|
string Uuid,
|
||||||
|
string? Message,
|
||||||
|
DateTime AddedWhen,
|
||||||
|
DateTime? ChangedWhen,
|
||||||
|
string? Title,
|
||||||
|
string Language,
|
||||||
|
bool TFAEnabled,
|
||||||
|
DigitalData.UserManager.Domain.Entities.User User)
|
||||||
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Gibt den Namen des Status zurück, der dem numerischen Statuswert entspricht.
|
||||||
|
/// </summary>
|
||||||
|
public string StatusName => ((Constants.EnvelopeStatus)Status).ToString();
|
||||||
|
}
|
||||||
@@ -0,0 +1,13 @@
|
|||||||
|
using EnvelopeGenerator.Application.Receivers.Queries.Read;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.Envelopes.Queries.ReceiverName;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Eine Abfrage, um die zuletzt verwendete Anrede eines Empfängers zu ermitteln,
|
||||||
|
/// damit diese für zukünftige Umschläge wiederverwendet werden kann.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Envelope">Der Umschlag, für den die Anrede des Empfängers ermittelt werden soll.</param>
|
||||||
|
/// <param name="OnlyLast">Gibt an, ob nur die zuletzt verwendete Anrede zurückgegeben werden soll.</param>
|
||||||
|
public record ReadReceiverNameQuery(EnvelopeQuery? Envelope = null, bool OnlyLast = true) : ReadReceiverQuery
|
||||||
|
{
|
||||||
|
}
|
||||||
@@ -0,0 +1,20 @@
|
|||||||
|
using EnvelopeGenerator.Application.Envelopes.Queries.Read;
|
||||||
|
using EnvelopeGenerator.Application.Receivers.Queries.Read;
|
||||||
|
using EnvelopeGenerator.Common;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.Application.Histories.Queries.Read;
|
||||||
|
|
||||||
|
/// <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,
|
||||||
|
Constants.ReferenceType? Related = null,
|
||||||
|
bool? OnlyLast = true);
|
||||||
@@ -0,0 +1,10 @@
|
|||||||
|
namespace EnvelopeGenerator.Application.Receivers.Queries.Read;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Stellt eine Abfrage dar, um die Details eines Empfängers zu lesen.
|
||||||
|
/// Diese Abfrage erbt von <see cref="ReceiverQuery"/> und wird verwendet,
|
||||||
|
/// um spezifische Informationen über einen Empfänger abzurufen.
|
||||||
|
/// </summary>
|
||||||
|
public record ReadReceiverQuery : ReceiverQuery
|
||||||
|
{
|
||||||
|
}
|
||||||
@@ -0,0 +1,12 @@
|
|||||||
|
namespace EnvelopeGenerator.Application.Receivers.Queries.Read;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Repräsentiert die Antwort auf eine Abfrage, um einen Empfänger zu lesen.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Id">Die eindeutige Identifikationsnummer des Empfängers.</param>
|
||||||
|
/// <param name="EmailAddress">Die E-Mail-Adresse des Empfängers.</param>
|
||||||
|
/// <param name="AddedWhen">Das Datum und die Uhrzeit, wann der Empfänger hinzugefügt wurde.</param>
|
||||||
|
/// <param name="Signature">Die Signatur des Empfängers.</param>
|
||||||
|
public record ReadReceiverResponse(int Id, string EmailAddress, DateTime AddedWhen, string Signature)
|
||||||
|
{
|
||||||
|
}
|
||||||
9
EnvelopeGenerator.Application/Receivers/ReceiverQuery.cs
Normal file
9
EnvelopeGenerator.Application/Receivers/ReceiverQuery.cs
Normal file
@@ -0,0 +1,9 @@
|
|||||||
|
namespace EnvelopeGenerator.Application.Receivers;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Empfänger des Umschlags
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Id">ID des Empfängers</param>
|
||||||
|
/// <param name="EmailAddress">E-Mail Adresse des Empfängers</param>
|
||||||
|
/// <param name="Signature">Eindeutige Signatur des Empfängers</param>
|
||||||
|
public record ReceiverQuery(int? Id = null, string? EmailAddress = null, string? Signature = null);
|
||||||
@@ -32,7 +32,7 @@
|
|||||||
|
|
||||||
'TODO: standardize in xwiki
|
'TODO: standardize in xwiki
|
||||||
Public Enum ReferenceType
|
Public Enum ReferenceType
|
||||||
Receiver
|
Receiver = 0
|
||||||
Sender
|
Sender
|
||||||
System
|
System
|
||||||
Unknown
|
Unknown
|
||||||
@@ -94,13 +94,16 @@
|
|||||||
End Enum
|
End Enum
|
||||||
|
|
||||||
Public Enum EmailTemplateType
|
Public Enum EmailTemplateType
|
||||||
DocumentReceived
|
DocumentReceived = 0
|
||||||
DocumentSigned
|
DocumentSigned
|
||||||
DocumentDeleted
|
DocumentDeleted
|
||||||
DocumentCompleted
|
DocumentCompleted
|
||||||
DocumentAccessCodeReceived
|
DocumentAccessCodeReceived
|
||||||
DocumentShared
|
DocumentShared
|
||||||
TotpSecret
|
TotpSecret
|
||||||
|
DocumentRejected_ADM
|
||||||
|
DocumentRejected_REC
|
||||||
|
DocumentRejected_REC_2
|
||||||
End Enum
|
End Enum
|
||||||
|
|
||||||
Public Enum EncodeType
|
Public Enum EncodeType
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net7.0</TargetFramework>
|
<TargetFrameworks>net7.0;net8.0;net9.0</TargetFrameworks>
|
||||||
<ImplicitUsings>enable</ImplicitUsings>
|
<ImplicitUsings>enable</ImplicitUsings>
|
||||||
<Nullable>enable</Nullable>
|
<Nullable>enable</Nullable>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|||||||
13
EnvelopeGenerator.GeneratorAPI/.config/dotnet-tools.json
Normal file
13
EnvelopeGenerator.GeneratorAPI/.config/dotnet-tools.json
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
{
|
||||||
|
"version": 1,
|
||||||
|
"isRoot": true,
|
||||||
|
"tools": {
|
||||||
|
"dotnet-ef": {
|
||||||
|
"version": "9.0.3",
|
||||||
|
"commands": [
|
||||||
|
"dotnet-ef"
|
||||||
|
],
|
||||||
|
"rollForward": false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -7,17 +7,27 @@ using Microsoft.AspNetCore.Mvc;
|
|||||||
using System.Security.Claims;
|
using System.Security.Claims;
|
||||||
using DigitalData.UserManager.Application.DTOs.Auth;
|
using DigitalData.UserManager.Application.DTOs.Auth;
|
||||||
using Microsoft.AspNetCore.Authorization;
|
using Microsoft.AspNetCore.Authorization;
|
||||||
|
using EnvelopeGenerator.GeneratorAPI.Models;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
||||||
{
|
{
|
||||||
|
/// <summary>
|
||||||
|
/// Controller verantwortlich für die Benutzer-Authentifizierung, einschließlich Anmelden, Abmelden und Überprüfung des Authentifizierungsstatus.
|
||||||
|
/// </summary>
|
||||||
[Route("api/[controller]")]
|
[Route("api/[controller]")]
|
||||||
[ApiController]
|
[ApiController]
|
||||||
public class AuthController : ControllerBase
|
public partial class AuthController : ControllerBase
|
||||||
{
|
{
|
||||||
private readonly ILogger<AuthController> _logger;
|
private readonly ILogger<AuthController> _logger;
|
||||||
private readonly IUserService _userService;
|
private readonly IUserService _userService;
|
||||||
private readonly IDirectorySearchService _dirSearchService;
|
private readonly IDirectorySearchService _dirSearchService;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Initializes a new instance of the <see cref="AuthController"/> class.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="logger">The logger instance.</param>
|
||||||
|
/// <param name="userService">The user service instance.</param>
|
||||||
|
/// <param name="dirSearchService">The directory search service instance.</param>
|
||||||
public AuthController(ILogger<AuthController> logger, IUserService userService, IDirectorySearchService dirSearchService)
|
public AuthController(ILogger<AuthController> logger, IUserService userService, IDirectorySearchService dirSearchService)
|
||||||
{
|
{
|
||||||
_logger = logger;
|
_logger = logger;
|
||||||
@@ -25,10 +35,37 @@ namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
|||||||
_dirSearchService = dirSearchService;
|
_dirSearchService = dirSearchService;
|
||||||
}
|
}
|
||||||
|
|
||||||
//TODO: When a user group is created for signFlow, add a process to check if the user is in this group (like "PM_USER")
|
/// <summary>
|
||||||
|
/// Authentifiziert einen Benutzer und generiert ein JWT-Token. Wenn 'cookie' wahr ist, wird das Token als HTTP-Only-Cookie zurückgegeben.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="login">Benutzeranmeldedaten (Benutzername und Passwort).</param>
|
||||||
|
/// <param name="cookie">Wenn wahr, wird das JWT-Token auch als HTTP-Only-Cookie gesendet.</param>
|
||||||
|
/// <returns>
|
||||||
|
/// Gibt eine HTTP 200 oder 401.
|
||||||
|
/// </returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// Sample request:
|
||||||
|
///
|
||||||
|
/// POST /api/auth?cookie=true
|
||||||
|
/// {
|
||||||
|
/// "username": "MaxMustermann",
|
||||||
|
/// "password": "Geheim123!"
|
||||||
|
/// }
|
||||||
|
///
|
||||||
|
/// POST /api/auth?cookie=true
|
||||||
|
/// {
|
||||||
|
/// "id": "1",
|
||||||
|
/// "password": "Geheim123!"
|
||||||
|
/// }
|
||||||
|
///
|
||||||
|
/// </remarks>
|
||||||
|
/// <response code="200">Erfolgreiche Anmeldung. Gibt das JWT-Token im Antwortkörper oder als Cookie zurück, wenn 'cookie' wahr ist.</response>
|
||||||
|
/// <response code="401">Unbefugt. Ungültiger Benutzername oder Passwort.</response>
|
||||||
|
[ProducesResponseType(typeof(string), StatusCodes.Status200OK, "text/javascript")]
|
||||||
|
[ProducesResponseType(typeof(void), StatusCodes.Status401Unauthorized)]
|
||||||
[AllowAnonymous]
|
[AllowAnonymous]
|
||||||
[HttpPost("login")]
|
[HttpPost]
|
||||||
public async Task<IActionResult> Login([FromBody] LogInDto login)
|
public async Task<IActionResult> Login([FromBody] Login login, [FromQuery] bool cookie = false)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
@@ -48,13 +85,13 @@ namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
|||||||
|
|
||||||
// Create claims
|
// Create claims
|
||||||
var claims = new List<Claim>
|
var claims = new List<Claim>
|
||||||
{
|
{
|
||||||
new (ClaimTypes.NameIdentifier, user.Id.ToString()),
|
new (ClaimTypes.NameIdentifier, user.Id.ToString()),
|
||||||
new (ClaimTypes.Name, user.Username),
|
new (ClaimTypes.Name, user.Username),
|
||||||
new (ClaimTypes.Surname, user.Name!),
|
new (ClaimTypes.Surname, user.Name!),
|
||||||
new (ClaimTypes.GivenName, user.Prename!),
|
new (ClaimTypes.GivenName, user.Prename!),
|
||||||
new (ClaimTypes.Email, user.Email!),
|
new (ClaimTypes.Email, user.Email!),
|
||||||
};
|
};
|
||||||
|
|
||||||
// Create claimsIdentity
|
// Create claimsIdentity
|
||||||
var claimsIdentity = new ClaimsIdentity(claims, CookieAuthenticationDefaults.AuthenticationScheme);
|
var claimsIdentity = new ClaimsIdentity(claims, CookieAuthenticationDefaults.AuthenticationScheme);
|
||||||
@@ -75,13 +112,58 @@ namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
|||||||
|
|
||||||
return Ok();
|
return Ok();
|
||||||
}
|
}
|
||||||
catch(Exception ex)
|
catch (Exception ex)
|
||||||
{
|
{
|
||||||
_logger.LogError(ex, "Unexpected error occurred.\n{ErrorMessage}", ex.Message);
|
_logger.LogError(ex, "Unexpected error occurred.\n{ErrorMessage}", ex.Message);
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Authentifiziert einen Benutzer und generiert ein JWT-Token. Das Token wird als HTTP-only-Cookie zurückgegeben.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="login">Benutzeranmeldedaten (Benutzername und Passwort).</param>
|
||||||
|
/// <returns>
|
||||||
|
/// Gibt eine HTTP 200 oder 401.
|
||||||
|
/// </returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// Sample request:
|
||||||
|
///
|
||||||
|
/// POST /api/auth/form
|
||||||
|
/// {
|
||||||
|
/// "username": "MaxMustermann",
|
||||||
|
/// "password": "Geheim123!"
|
||||||
|
/// }
|
||||||
|
///
|
||||||
|
/// </remarks>
|
||||||
|
/// <response code="200">Erfolgreiche Anmeldung. Gibt das JWT-Token im Antwortkörper oder als Cookie zurück, wenn 'cookie' wahr ist.</response>
|
||||||
|
/// <response code="401">Unbefugt. Ungültiger Benutzername oder Passwort.</response>
|
||||||
|
[ProducesResponseType(typeof(string), StatusCodes.Status200OK, "text/javascript")]
|
||||||
|
[ProducesResponseType(typeof(void), StatusCodes.Status401Unauthorized)]
|
||||||
|
[AllowAnonymous]
|
||||||
|
[HttpPost]
|
||||||
|
[Route("form")]
|
||||||
|
public async Task<IActionResult> Login([FromForm] Login login)
|
||||||
|
{
|
||||||
|
return await Login(login, true);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Entfernt das Authentifizierungs-Cookie des Benutzers (AuthCookie)
|
||||||
|
/// </summary>
|
||||||
|
/// <returns>
|
||||||
|
/// Gibt eine HTTP 200 oder 401.
|
||||||
|
/// </returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// Sample request:
|
||||||
|
///
|
||||||
|
/// POST /api/auth/logout
|
||||||
|
///
|
||||||
|
/// </remarks>
|
||||||
|
/// <response code="200">Erfolgreich gelöscht, wenn der Benutzer ein berechtigtes Cookie hat.</response>
|
||||||
|
/// <response code="401">Wenn es kein zugelassenes Cookie gibt, wird „nicht zugelassen“ zurückgegeben.</response>
|
||||||
|
[ProducesResponseType(typeof(string), StatusCodes.Status200OK, "text/javascript")]
|
||||||
|
[ProducesResponseType(typeof(void), StatusCodes.Status401Unauthorized)]
|
||||||
[Authorize]
|
[Authorize]
|
||||||
[HttpPost("logout")]
|
[HttpPost("logout")]
|
||||||
public async Task<IActionResult> Logout()
|
public async Task<IActionResult> Logout()
|
||||||
@@ -98,8 +180,22 @@ namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
[AllowAnonymous]
|
/// <summary>
|
||||||
[HttpGet("check")]
|
/// Prüft, ob der Benutzer ein autorisiertes Token hat.
|
||||||
public IActionResult IsAuthenticated() => Ok(User.Identity?.IsAuthenticated ?? false);
|
/// </summary>
|
||||||
|
/// <returns>Wenn ein autorisiertes Token vorhanden ist HTTP 200 asynchron 401</returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// Sample request:
|
||||||
|
///
|
||||||
|
/// GET /api/auth
|
||||||
|
///
|
||||||
|
/// </remarks>
|
||||||
|
/// <response code="200">Wenn es einen autorisierten Cookie gibt.</response>
|
||||||
|
/// <response code="401">Wenn kein Cookie vorhanden ist oder nicht autorisierte.</response>
|
||||||
|
[ProducesResponseType(typeof(string), StatusCodes.Status200OK, "text/javascript")]
|
||||||
|
[ProducesResponseType(typeof(void), StatusCodes.Status401Unauthorized)]
|
||||||
|
[Authorize]
|
||||||
|
[HttpGet]
|
||||||
|
public IActionResult IsAuthenticated() => Ok();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -0,0 +1,91 @@
|
|||||||
|
using AutoMapper;
|
||||||
|
using EnvelopeGenerator.Application.EmailTemplates;
|
||||||
|
using EnvelopeGenerator.Application.EmailTemplates.Commands.Update;
|
||||||
|
using EnvelopeGenerator.Application.EmailTemplates.Commands.Reset;
|
||||||
|
using EnvelopeGenerator.Application.EmailTemplates.Queries.Read;
|
||||||
|
using Microsoft.AspNetCore.Authorization;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.GeneratorAPI.Controllers;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Controller for managing email templates.
|
||||||
|
/// Steuerung zur Verwaltung von E-Mail-Vorlagen.
|
||||||
|
/// </summary>
|
||||||
|
[Route("api/[controller]")]
|
||||||
|
[ApiController]
|
||||||
|
[Authorize]
|
||||||
|
public class EmailTemplateController : ControllerBase
|
||||||
|
{
|
||||||
|
private readonly IMapper _mapper;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Initialisiert eine neue Instanz der <see cref="EmailTemplateController"/>-Klasse.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="mapper">
|
||||||
|
/// Die AutoMapper-Instanz, die zum Zuordnen von Objekten verwendet wird.
|
||||||
|
/// </param>
|
||||||
|
public EmailTemplateController(IMapper mapper)
|
||||||
|
{
|
||||||
|
_mapper = mapper;
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Ruft E-Mail-Vorlagen basierend auf der angegebenen Abfrage ab.
|
||||||
|
/// Gibt alles zurück, wenn keine Id- oder Typ-Informationen eingegeben wurden.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="emailTemplate">Die Abfrageparameter zum Abrufen von E-Mail-Vorlagen.</param>
|
||||||
|
/// <returns>Gibt HTTP-Antwort zurück</returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// Sample request:
|
||||||
|
/// GET /api/EmailTemplate?emailTemplateId=123
|
||||||
|
/// </remarks>
|
||||||
|
/// <response code="200">Wenn die E-Mail-Vorlagen erfolgreich abgerufen werden.</response>
|
||||||
|
/// <response code="400">Wenn die Abfrageparameter ungültig sind.</response>
|
||||||
|
/// <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)
|
||||||
|
{
|
||||||
|
// Implementation logic here
|
||||||
|
return Ok(); // Placeholder for actual implementation
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Updates an email template or resets it if no update command is provided.
|
||||||
|
/// Aktualisiert eine E-Mail-Vorlage oder setzt sie zurück, wenn kein Aktualisierungsbefehl angegeben ist.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="email">Die E-Mail-Vorlagenabfrage.</param>
|
||||||
|
/// <param name="update">Der Aktualisierungsbefehl für die E-Mail-Vorlage.
|
||||||
|
/// Wird auf Standardwert aktualisiert, wenn die Anfrage ohne http-Body gesendet wird.
|
||||||
|
/// </param>
|
||||||
|
/// <returns>Gibt HTTP-Antwort zurück</returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// Sample request:
|
||||||
|
/// PUT /api/EmailTemplate
|
||||||
|
/// {
|
||||||
|
/// "emailTemplateId": 123,
|
||||||
|
/// "newContent": "Updated content"
|
||||||
|
/// }
|
||||||
|
/// </remarks>
|
||||||
|
/// <response code="200">Wenn die E-Mail-Vorlage erfolgreich aktualisiert oder zurückgesetzt wird.</response>
|
||||||
|
/// <response code="400">Wenn die Abfrage ohne einen String gesendet wird.</response>
|
||||||
|
/// <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)
|
||||||
|
{
|
||||||
|
if (update is null)
|
||||||
|
{
|
||||||
|
var reset = _mapper.Map<ResetEnvelopeTemplateCommand>(email);
|
||||||
|
// Logic for resetting the email template
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
update.EmailTemplateQuery = email;
|
||||||
|
// Logic for updating the email template
|
||||||
|
}
|
||||||
|
|
||||||
|
return Ok(); // Placeholder for actual implementation
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -1,52 +1,78 @@
|
|||||||
using DigitalData.Core.DTO;
|
using DigitalData.Core.DTO;
|
||||||
using EnvelopeGenerator.Application.Contracts.Services;
|
using EnvelopeGenerator.Application.Contracts.Services;
|
||||||
|
using EnvelopeGenerator.Application.Envelopes.Queries.Read;
|
||||||
using Microsoft.AspNetCore.Authorization;
|
using Microsoft.AspNetCore.Authorization;
|
||||||
using Microsoft.AspNetCore.Mvc;
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
namespace EnvelopeGenerator.GeneratorAPI.Controllers;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Dieser Controller stellt Endpunkte für die Verwaltung von Umschlägen bereit.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// Die API ermöglicht das Abrufen und Verwalten von Umschlägen basierend auf Benutzerinformationen und Statusfiltern.
|
||||||
|
///
|
||||||
|
/// Mögliche Antworten:
|
||||||
|
/// - 200 OK: Die Anfrage war erfolgreich, und die angeforderten Daten werden zurückgegeben.
|
||||||
|
/// - 400 Bad Request: Die Anfrage war fehlerhaft oder unvollständig.
|
||||||
|
/// - 401 Unauthorized: Der Benutzer ist nicht authentifiziert.
|
||||||
|
/// - 403 Forbidden: Der Benutzer hat keine Berechtigung, auf die Ressource zuzugreifen.
|
||||||
|
/// - 404 Not Found: Die angeforderte Ressource wurde nicht gefunden.
|
||||||
|
/// - 500 Internal Server Error: Ein unerwarteter Fehler ist aufgetreten.
|
||||||
|
/// </remarks>
|
||||||
|
[Route("api/[controller]")]
|
||||||
|
[ApiController]
|
||||||
|
[Authorize]
|
||||||
|
public class EnvelopeController : ControllerBase
|
||||||
{
|
{
|
||||||
[Route("api/[controller]")]
|
private readonly ILogger<EnvelopeController> _logger;
|
||||||
[ApiController]
|
private readonly IEnvelopeService _envelopeService;
|
||||||
[Authorize]
|
|
||||||
public class EnvelopeController : ControllerBase
|
/// <summary>
|
||||||
|
/// Erstellt eine neue Instanz des EnvelopeControllers.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="logger">Der Logger, der für das Protokollieren von Informationen verwendet wird.</param>
|
||||||
|
/// <param name="envelopeService">Der Dienst, der für die Verarbeitung von Umschlägen zuständig ist.</param>
|
||||||
|
public EnvelopeController(ILogger<EnvelopeController> logger, IEnvelopeService envelopeService)
|
||||||
{
|
{
|
||||||
private readonly ILogger<EnvelopeController> _logger;
|
_logger = logger;
|
||||||
private readonly IEnvelopeService _envelopeService;
|
_envelopeService = envelopeService;
|
||||||
|
}
|
||||||
|
|
||||||
public EnvelopeController(ILogger<EnvelopeController> logger, IEnvelopeService envelopeService)
|
/// <summary>
|
||||||
|
/// Ruft eine Liste von Umschlägen basierend auf dem Benutzer und den angegebenen Statusfiltern ab.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="envelope"></param>
|
||||||
|
/// <returns>Eine IActionResult-Instanz, die die abgerufenen Umschläge oder einen Fehlerstatus enthält.</returns>
|
||||||
|
/// <response code="200">Die Anfrage war erfolgreich, und die Umschläge werden zurückgegeben.</response>
|
||||||
|
/// <response code="400">Die Anfrage war fehlerhaft oder unvollständig.</response>
|
||||||
|
/// <response code="401">Der Benutzer ist nicht authentifiziert.</response>
|
||||||
|
/// <response code="403">Der Benutzer hat keine Berechtigung, auf die Ressource zuzugreifen.</response>
|
||||||
|
/// <response code="500">Ein unerwarteter Fehler ist aufgetreten.</response>
|
||||||
|
[Authorize]
|
||||||
|
[HttpGet]
|
||||||
|
public async Task<IActionResult> GetAsync([FromQuery] ReadEnvelopeQuery envelope)
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
_logger = logger;
|
if (User.GetId() is int intId)
|
||||||
_envelopeService = envelopeService;
|
return await _envelopeService.ReadByUserAsync(intId, min_status: envelope.Status, max_status: envelope.Status).ThenAsync(
|
||||||
}
|
Success: Ok,
|
||||||
|
Fail: IActionResult (msg, ntc) =>
|
||||||
[Authorize]
|
{
|
||||||
[HttpGet]
|
_logger.LogNotice(ntc);
|
||||||
public async Task<IActionResult> GetCurrentAsync(
|
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||||
[FromQuery] int? min_status = null,
|
});
|
||||||
[FromQuery] int? max_status = null,
|
else
|
||||||
[FromQuery] params int[] ignore_statuses)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
{
|
||||||
if (User.GetId() is int intId)
|
_logger.LogError("Trotz erfolgreicher Autorisierung wurde die Benutzer-ID nicht als Ganzzahl erkannt. Dies könnte auf eine fehlerhafte Erstellung der Anspruchsliste zurückzuführen sein.");
|
||||||
return await _envelopeService.ReadByUserAsync(intId, min_status: min_status, max_status: max_status, ignore_statuses: ignore_statuses).ThenAsync(
|
|
||||||
Success: Ok,
|
|
||||||
Fail: IActionResult (msg, ntc) =>
|
|
||||||
{
|
|
||||||
_logger.LogNotice(ntc);
|
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
|
||||||
});
|
|
||||||
else
|
|
||||||
{
|
|
||||||
_logger.LogError("Despite successful authorization, the 'api/envelope' route encountered an issue: the user ID is not recognized as an integer. This may be due to the removal of the ID during the creation of the claims list.");
|
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "{Message}", ex.Message);
|
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
_logger.LogError(ex, "{Message}", ex.Message);
|
||||||
|
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,98 +1,165 @@
|
|||||||
using DigitalData.Core.DTO;
|
using DigitalData.Core.DTO;
|
||||||
using EnvelopeGenerator.Application.Contracts.Services;
|
using EnvelopeGenerator.Application.Contracts.Services;
|
||||||
using EnvelopeGenerator.Common.My.Resources;
|
using EnvelopeGenerator.Application.EnvelopeReceivers.Commands.Create;
|
||||||
|
using EnvelopeGenerator.Application.EnvelopeReceivers.Queries.Read;
|
||||||
|
using EnvelopeGenerator.Application.Envelopes.Queries.ReceiverName;
|
||||||
|
using MediatR;
|
||||||
using Microsoft.AspNetCore.Authorization;
|
using Microsoft.AspNetCore.Authorization;
|
||||||
using Microsoft.AspNetCore.Mvc;
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
namespace EnvelopeGenerator.GeneratorAPI.Controllers;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Controller für die Verwaltung von Umschlagempfängern.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// Dieser Controller bietet Endpunkte für das Abrufen und Verwalten von Umschlagempfängerdaten.
|
||||||
|
/// </remarks>
|
||||||
|
[Route("api/[controller]")]
|
||||||
|
[Authorize]
|
||||||
|
[ApiController]
|
||||||
|
public class EnvelopeReceiverController : ControllerBase
|
||||||
{
|
{
|
||||||
[Route("api/[controller]")]
|
private readonly ILogger<EnvelopeReceiverController> _logger;
|
||||||
[Authorize]
|
|
||||||
[ApiController]
|
private readonly IEnvelopeReceiverService _erService;
|
||||||
public class EnvelopeReceiverController : ControllerBase
|
|
||||||
|
private readonly IMediator _mediator;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Konstruktor für den EnvelopeReceiverController.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="logger">Logger-Instanz zur Protokollierung von Informationen und Fehlern.</param>
|
||||||
|
/// <param name="envelopeReceiverService">Service zur Verwaltung von Umschlagempfängern.</param>
|
||||||
|
/// <param name="mediator">Mediator-Instanz zur Verarbeitung von Befehlen und Abfragen.</param>
|
||||||
|
public EnvelopeReceiverController(ILogger<EnvelopeReceiverController> logger, IEnvelopeReceiverService envelopeReceiverService, IMediator mediator)
|
||||||
{
|
{
|
||||||
private readonly ILogger<EnvelopeReceiverController> _logger;
|
_logger = logger;
|
||||||
private readonly IEnvelopeReceiverService _erService;
|
_erService = envelopeReceiverService;
|
||||||
|
_mediator = mediator;
|
||||||
|
}
|
||||||
|
|
||||||
public EnvelopeReceiverController(ILogger<EnvelopeReceiverController> logger, IEnvelopeReceiverService envelopeReceiverService)
|
/// <summary>
|
||||||
|
/// Ruft eine Liste von Umschlagempfängern basierend auf den angegebenen Abfrageparametern ab.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="envelopeReceiver">Die Abfrageparameter für die Filterung von Umschlagempfängern.</param>
|
||||||
|
/// <returns>Eine HTTP-Antwort mit der Liste der gefundenen Umschlagempfänger oder einem Fehlerstatus.</returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// Dieser Endpunkt ermöglicht es, Umschlagempfänger basierend auf dem Benutzernamen und optionalen Statusfiltern abzurufen.
|
||||||
|
/// Wenn der Benutzername nicht ermittelt werden kann, wird ein Serverfehler zurückgegeben.
|
||||||
|
/// </remarks>
|
||||||
|
/// <response code="200">Die Liste der Umschlagempfänger wurde erfolgreich abgerufen.</response>
|
||||||
|
/// <response code="401">Wenn kein autorisierter Token vorhanden ist</response>
|
||||||
|
/// <response code="500">Ein unerwarteter Fehler ist aufgetreten.</response>
|
||||||
|
[Authorize]
|
||||||
|
[HttpGet]
|
||||||
|
public async Task<IActionResult> GetEnvelopeReceiver([FromQuery] ReadEnvelopeReceiverQuery envelopeReceiver)
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
_logger = logger;
|
var username = User.GetUsername();
|
||||||
_erService = envelopeReceiverService;
|
|
||||||
}
|
|
||||||
|
|
||||||
[HttpGet]
|
if (username is null)
|
||||||
public async Task<IActionResult> GetEnvelopeReceiver([FromQuery] int? min_status = null, [FromQuery] int? max_status = null, [FromQuery] int[]? ignore_status = null)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
{
|
||||||
var username = User.GetUsername();
|
_logger.LogError(@"Envelope Receiver dto cannot be sent because username claim is null. Potential authentication and authorization error. The value of other claims are [id: {id}], [username: {username}], [name: {name}], [prename: {prename}], [email: {email}].",
|
||||||
|
User.GetId(), User.GetUsername(), User.GetName(), User.GetPrename(), User.GetEmail());
|
||||||
if (username is null)
|
|
||||||
{
|
|
||||||
_logger.LogError(@"Envelope Receiver dto cannot be sent because username claim is null. Potential authentication and authorization error. The value of other claims are [id: {id}], [username: {username}], [name: {name}], [prename: {prename}], [email: {email}].",
|
|
||||||
User.GetId(), User.GetUsername(), User.GetName(), User.GetPrename(), User.GetEmail());
|
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
|
||||||
}
|
|
||||||
|
|
||||||
ignore_status ??= Array.Empty<int>();
|
|
||||||
|
|
||||||
return await _erService.ReadByUsernameAsync(username: username, min_status: min_status, max_status: max_status, ignore_statuses: ignore_status).ThenAsync(
|
|
||||||
Success: Ok,
|
|
||||||
Fail: IActionResult (msg, ntc) =>
|
|
||||||
{
|
|
||||||
_logger.LogNotice(ntc);
|
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError, msg);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
catch(Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "An unexpected error occurred. {message}", ex.Message);
|
|
||||||
return new StatusCodeResult(StatusCodes.Status500InternalServerError);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
[HttpGet("receiver-name/{mail}")]
|
|
||||||
public async Task<IActionResult> GetReceiverName([FromRoute] string mail)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
return await _erService.ReadLastUsedReceiverNameByMail(mail).ThenAsync(
|
|
||||||
Success: res => res is null ? Ok(string.Empty) : Ok(res),
|
|
||||||
Fail: IActionResult (msg, ntc) =>
|
|
||||||
{
|
|
||||||
if (ntc.HasFlag(Flag.NotFound))
|
|
||||||
return NotFound();
|
|
||||||
|
|
||||||
_logger.LogNotice(ntc);
|
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
catch(Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "{message}", ex.Message);
|
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
[HttpGet("secret")]
|
return await _erService.ReadByUsernameAsync(username: username).ThenAsync(
|
||||||
[Authorize]
|
|
||||||
public async Task<IActionResult> GetSecretAsync([FromQuery] string uuid)
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
return await _erService.ReadWithSecretByUuidAsync(uuid: uuid).ThenAsync(
|
|
||||||
Success: Ok,
|
Success: Ok,
|
||||||
Fail: IActionResult (msg, ntc) =>
|
Fail: IActionResult (msg, ntc) =>
|
||||||
{
|
{
|
||||||
_logger.LogNotice(ntc);
|
_logger.LogNotice(ntc);
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
return StatusCode(StatusCodes.Status500InternalServerError, msg);
|
||||||
});
|
});
|
||||||
}
|
}
|
||||||
catch (Exception ex)
|
catch (Exception ex)
|
||||||
{
|
{
|
||||||
_logger.LogError(ex, "{message}", ex.Message);
|
_logger.LogError(ex, "An unexpected error occurred. {message}", ex.Message);
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
return new StatusCodeResult(StatusCodes.Status500InternalServerError);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Ruft den Namen des zuletzt verwendeten Empfängers basierend auf der angegebenen E-Mail-Adresse ab.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="receiverName">Die Abfrage, die die E-Mail-Adresse des Empfängers enthält.</param>
|
||||||
|
/// <returns>Eine HTTP-Antwort mit dem Namen des Empfängers oder einem Fehlerstatus.</returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// Dieser Endpunkt ermöglicht es, den Namen des zuletzt verwendeten Empfängers basierend auf der E-Mail-Adresse abzurufen.
|
||||||
|
/// </remarks>
|
||||||
|
/// <response code="200">Der Name des Empfängers wurde erfolgreich abgerufen.</response>
|
||||||
|
/// <response code="401">Wenn kein autorisierter Token vorhanden ist</response>
|
||||||
|
/// <response code="404">Kein Empfänger gefunden.</response>
|
||||||
|
/// <response code="500">Ein unerwarteter Fehler ist aufgetreten.</response>
|
||||||
|
[Authorize]
|
||||||
|
[HttpGet("salute")]
|
||||||
|
public async Task<IActionResult> GetReceiverName([FromQuery] ReadReceiverNameQuery receiverName)
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
return await _erService.ReadLastUsedReceiverNameByMail(receiverName.EmailAddress).ThenAsync(
|
||||||
|
Success: res => res is null ? Ok(string.Empty) : Ok(res),
|
||||||
|
Fail: IActionResult (msg, ntc) =>
|
||||||
|
{
|
||||||
|
if (ntc.HasFlag(Flag.NotFound))
|
||||||
|
return NotFound();
|
||||||
|
|
||||||
|
_logger.LogNotice(ntc);
|
||||||
|
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
_logger.LogError(ex, "{message}", ex.Message);
|
||||||
|
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Datenübertragungsobjekt mit Informationen zu Umschlägen, Empfängern und Unterschriften.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="createEnvelopeQuery"></param>
|
||||||
|
/// <param name="cancellationToken">Token to cancel the operation</param>
|
||||||
|
/// <returns>HTTP-Antwort</returns>
|
||||||
|
/// <remarks>
|
||||||
|
/// Sample request:
|
||||||
|
///
|
||||||
|
/// POST /api/envelope
|
||||||
|
/// {
|
||||||
|
/// "title": "Vertragsdokument",
|
||||||
|
/// "message": "Bitte unterschreiben Sie dieses Dokument.",
|
||||||
|
/// "document": {
|
||||||
|
/// "dataAsBase64": "dGVzdC1iYXNlNjQtZGF0YQ=="
|
||||||
|
/// },
|
||||||
|
/// "receivers": [
|
||||||
|
/// {
|
||||||
|
/// "emailAddress": "example@example.com",
|
||||||
|
/// "signatures": [
|
||||||
|
/// {
|
||||||
|
/// "x": 100,
|
||||||
|
/// "y": 200,
|
||||||
|
/// "page": 1
|
||||||
|
/// }
|
||||||
|
/// ],
|
||||||
|
/// "name": "Max Mustermann",
|
||||||
|
/// "phoneNumber": "+49123456789"
|
||||||
|
/// }
|
||||||
|
/// ],
|
||||||
|
/// "tfaEnabled": false
|
||||||
|
/// }
|
||||||
|
///
|
||||||
|
/// </remarks>
|
||||||
|
/// <response code="202">Envelope-Erstellung und Sendeprozessbefehl erfolgreich</response>
|
||||||
|
/// <response code="400">Wenn ein Fehler im HTTP-Body auftritt</response>
|
||||||
|
/// <response code="401">Wenn kein autorisierter Token vorhanden ist</response>
|
||||||
|
/// <response code="500">Es handelt sich um einen unerwarteten Fehler. Die Protokolle sollten überprüft werden.</response>
|
||||||
|
[Authorize]
|
||||||
|
[HttpPost]
|
||||||
|
public async Task<IActionResult> CreateAsync([FromBody] CreateEnvelopeReceiverCommand createEnvelopeQuery, CancellationToken cancellationToken)
|
||||||
|
{
|
||||||
|
await _mediator.Send(createEnvelopeQuery, cancellationToken);
|
||||||
|
return Accepted();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
@@ -1,43 +1,40 @@
|
|||||||
using DigitalData.Core.DTO;
|
using DigitalData.Core.DTO;
|
||||||
using EnvelopeGenerator.Application.Contracts.Services;
|
using EnvelopeGenerator.Application.Contracts.Services;
|
||||||
using Microsoft.AspNetCore.Http;
|
|
||||||
using Microsoft.AspNetCore.Mvc;
|
using Microsoft.AspNetCore.Mvc;
|
||||||
using System.Net.Mail;
|
|
||||||
using System.Security.Cryptography.Xml;
|
|
||||||
|
|
||||||
namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
namespace EnvelopeGenerator.GeneratorAPI.Controllers;
|
||||||
|
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
|
[Route("api/[controller]")]
|
||||||
|
[ApiController]
|
||||||
|
public class EnvelopeTypeController : ControllerBase
|
||||||
{
|
{
|
||||||
[Route("api/[controller]")]
|
private readonly ILogger<EnvelopeTypeController> _logger;
|
||||||
[ApiController]
|
private readonly IEnvelopeTypeService _service;
|
||||||
public class EnvelopeTypeController : ControllerBase
|
|
||||||
|
public EnvelopeTypeController(ILogger<EnvelopeTypeController> logger, IEnvelopeTypeService service)
|
||||||
{
|
{
|
||||||
private readonly ILogger<EnvelopeTypeController> _logger;
|
_logger = logger;
|
||||||
private readonly IEnvelopeTypeService _service;
|
_service = service;
|
||||||
|
}
|
||||||
|
|
||||||
public EnvelopeTypeController(ILogger<EnvelopeTypeController> logger, IEnvelopeTypeService service)
|
[HttpGet]
|
||||||
|
public async Task<IActionResult> GetAllAsync()
|
||||||
|
{
|
||||||
|
try
|
||||||
{
|
{
|
||||||
_logger = logger;
|
return await _service.ReadAllAsync().ThenAsync(
|
||||||
_service = service;
|
Success: Ok,
|
||||||
|
Fail: IActionResult (msg, ntc) =>
|
||||||
|
{
|
||||||
|
_logger.LogNotice(ntc);
|
||||||
|
return ntc.HasFlag(Flag.NotFound) ? NotFound() : StatusCode(StatusCodes.Status500InternalServerError);
|
||||||
|
});
|
||||||
}
|
}
|
||||||
|
catch (Exception ex)
|
||||||
[HttpGet]
|
|
||||||
public async Task<IActionResult> GetAllAsync()
|
|
||||||
{
|
{
|
||||||
try
|
_logger.LogError(ex, "{Message}", ex.Message);
|
||||||
{
|
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||||
return await _service.ReadAllAsync().ThenAsync(
|
|
||||||
Success: Ok,
|
|
||||||
Fail: IActionResult (msg, ntc) =>
|
|
||||||
{
|
|
||||||
_logger.LogNotice(ntc);
|
|
||||||
return ntc.HasFlag(Flag.NotFound) ? NotFound() : StatusCode(StatusCodes.Status500InternalServerError);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
catch (Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "{Message}", ex.Message);
|
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -1,73 +1,155 @@
|
|||||||
using EnvelopeGenerator.Application.Contracts.Services;
|
using DigitalData.EmailProfilerDispatcher.Abstraction.Entities;
|
||||||
|
using EnvelopeGenerator.Application.Contracts.Services;
|
||||||
|
using EnvelopeGenerator.Application.Histories.Queries.Read;
|
||||||
using Microsoft.AspNetCore.Authorization;
|
using Microsoft.AspNetCore.Authorization;
|
||||||
using Microsoft.AspNetCore.Mvc;
|
using Microsoft.AspNetCore.Mvc;
|
||||||
using System;
|
|
||||||
using static EnvelopeGenerator.Common.Constants;
|
using static EnvelopeGenerator.Common.Constants;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
|
||||||
|
namespace EnvelopeGenerator.GeneratorAPI.Controllers;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Dieser Controller stellt Endpunkte für den Zugriff auf die Umschlaghistorie bereit.
|
||||||
|
/// </summary>
|
||||||
|
[Route("api/[controller]")]
|
||||||
|
[ApiController]
|
||||||
|
[Authorize]
|
||||||
|
public class HistoryController : ControllerBase
|
||||||
{
|
{
|
||||||
[Route("api/[controller]")]
|
private readonly ILogger<HistoryController> _logger;
|
||||||
[ApiController]
|
|
||||||
[Authorize]
|
private readonly IEnvelopeHistoryService _service;
|
||||||
public class HistoryController : ControllerBase
|
|
||||||
|
/// <summary>
|
||||||
|
/// Konstruktor für den HistoryController.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="logger">Der Logger, der für das Protokollieren von Informationen verwendet wird.</param>
|
||||||
|
/// <param name="service">Der Dienst, der für die Verarbeitung der Umschlaghistorie verantwortlich ist.</param>
|
||||||
|
public HistoryController(ILogger<HistoryController> logger, IEnvelopeHistoryService service)
|
||||||
{
|
{
|
||||||
private readonly ILogger<HistoryController> _logger;
|
_logger = logger;
|
||||||
|
_service = service;
|
||||||
|
}
|
||||||
|
|
||||||
private readonly IEnvelopeHistoryService _service;
|
/// <summary>
|
||||||
|
/// Gibt alle möglichen Verweise auf alle möglichen Status in einem Verlaufsdatensatz zurück. (z. B. DocumentSigned bezieht sich auf Receiver.)
|
||||||
|
/// Dies wird hinzugefügt, damit Client-Anwendungen sich selbst auf dem neuesten Stand halten können.
|
||||||
|
/// 0 - Receiver:
|
||||||
|
/// Historische Datensätze, die sich auf den Status des Absenders beziehen. Sie haben Statuscodes, die mit 1* beginnen.
|
||||||
|
/// 1 - Sender:
|
||||||
|
/// Historische Datensätze über den Status der Empfänger. Diese haben Statuscodes, die mit 2* beginnen.
|
||||||
|
/// 2 - System:
|
||||||
|
/// Historische Datensätze, die sich auf den allgemeinen Zustand des Umschlags beziehen. Diese haben Statuscodes, die mit 3* beginnen.
|
||||||
|
/// 3 - Unknown:
|
||||||
|
/// Ein unbekannter Datensatz weist auf einen möglichen Mangel oder eine Unstimmigkeit im Aktualisierungsprozess der Anwendung hin.
|
||||||
|
/// </summary>
|
||||||
|
/// <returns></returns>
|
||||||
|
/// <response code="200"></response>
|
||||||
|
[HttpGet("related")]
|
||||||
|
[Authorize]
|
||||||
|
public IActionResult GetReferenceTypes()
|
||||||
|
{
|
||||||
|
// Enum zu Schlüssel-Wert-Paar
|
||||||
|
var referenceTypes = Enum.GetValues(typeof(ReferenceType))
|
||||||
|
.Cast<ReferenceType>()
|
||||||
|
.ToDictionary(rt =>
|
||||||
|
{
|
||||||
|
var key = rt.ToString();
|
||||||
|
var keyAsCamelCase = char.ToLower(key[0]) + key[1..];
|
||||||
|
return keyAsCamelCase;
|
||||||
|
}, rt => (int)rt);
|
||||||
|
|
||||||
public HistoryController(ILogger<HistoryController> logger, IEnvelopeHistoryService service)
|
return Ok(referenceTypes);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Gibt alle möglichen Status in einem Verlaufsdatensatz zurück.
|
||||||
|
/// Dies wird hinzugefügt, damit Client-Anwendungen sich selbst auf dem neuesten Stand halten können.
|
||||||
|
/// 0: Invalid
|
||||||
|
/// 1001: EnvelopeCreated
|
||||||
|
/// 1002: EnvelopeSaved
|
||||||
|
/// 1003: EnvelopeQueued
|
||||||
|
/// 1004: EnvelopeSent (Nicht verwendet)
|
||||||
|
/// 1005: EnvelopePartlySigned
|
||||||
|
/// 1006: EnvelopeCompletelySigned
|
||||||
|
/// 1007: EnvelopeReportCreated
|
||||||
|
/// 1008: EnvelopeArchived
|
||||||
|
/// 1009: EnvelopeDeleted
|
||||||
|
/// 2001: AccessCodeRequested
|
||||||
|
/// 2002: AccessCodeCorrect
|
||||||
|
/// 2003: AccessCodeIncorrect
|
||||||
|
/// 2004: DocumentOpened
|
||||||
|
/// 2005: DocumentSigned
|
||||||
|
/// 4001: DocumentForwarded
|
||||||
|
/// 2006: SignatureConfirmed
|
||||||
|
/// 2007: DocumentRejected
|
||||||
|
/// 2008: EnvelopeShared
|
||||||
|
/// 2009: EnvelopeViewed
|
||||||
|
/// 3001: MessageInvitationSent (Wird von Trigger verwendet)
|
||||||
|
/// 3002: MessageAccessCodeSent
|
||||||
|
/// 3003: MessageConfirmationSent
|
||||||
|
/// 3004: MessageDeletionSent
|
||||||
|
/// 3005: MessageCompletionSent
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="related">
|
||||||
|
/// Abfrageparameter, der angibt, auf welche Referenz sich der Status bezieht.
|
||||||
|
/// 0 - Sender: Historische Datensätze, die sich auf den Status des Absenders beziehen. Sie haben Statuscodes, die mit 1* beginnen.
|
||||||
|
/// 1 - Receiver: Historische Datensätze über den Status der Empfänger. Diese haben Statuscodes, die mit 2* beginnen.
|
||||||
|
/// 2 - System: Diese werden durch Datenbank-Trigger aktualisiert und sind in den Tabellen EnvelopeHistory und EmailOut zu finden.Sie arbeiten
|
||||||
|
/// integriert mit der Anwendung EmailProfiler, um E-Mails zu versenden und haben die Codes, die mit 3* beginnen.
|
||||||
|
/// </param>
|
||||||
|
/// <returns>Gibt die HTTP-Antwort zurück.</returns>
|
||||||
|
/// <response code="200"></response>
|
||||||
|
[HttpGet("status")]
|
||||||
|
[Authorize]
|
||||||
|
public IActionResult GetEnvelopeStatus([FromQuery] ReferenceType? related = null)
|
||||||
|
{
|
||||||
|
// Enum zu Schlüssel-Wert-Paar
|
||||||
|
var referenceTypes = Enum.GetValues(typeof(EnvelopeStatus))
|
||||||
|
.Cast<EnvelopeStatus>()
|
||||||
|
.ToDictionary(rt =>
|
||||||
|
{
|
||||||
|
var key = rt.ToString();
|
||||||
|
var keyAsCamelCase = char.ToLower(key[0]) + key[1..];
|
||||||
|
return keyAsCamelCase;
|
||||||
|
}, rt => (int)rt);
|
||||||
|
|
||||||
|
return Ok(referenceTypes);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Ruft die gesamte Umschlaghistorie basierend auf den angegebenen Abfrageparametern ab.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="history">Die Abfrageparameter, die die Filterkriterien für die Umschlaghistorie definieren.</param>
|
||||||
|
/// <returns>Eine Liste von Historieneinträgen, die den angegebenen Kriterien entsprechen, oder nur der letzte Eintrag.</returns>
|
||||||
|
/// <response code="200">Die Anfrage war erfolgreich, und die Umschlaghistorie wird zurückgegeben.</response>
|
||||||
|
/// <response code="400">Die Anfrage war ungültig oder unvollständig.</response>
|
||||||
|
/// <response code="401">Der Benutzer ist nicht authentifiziert.</response>
|
||||||
|
/// <response code="403">Der Benutzer hat keine Berechtigung, auf die Ressource zuzugreifen.</response>
|
||||||
|
/// <response code="500">Ein unerwarteter Fehler ist aufgetreten.</response>
|
||||||
|
[HttpGet]
|
||||||
|
[Authorize]
|
||||||
|
public async Task<IActionResult> GetAllAsync([FromQuery] ReadHistoryQuery history)
|
||||||
|
{
|
||||||
|
bool withReceiver = false;
|
||||||
|
bool withSender = false;
|
||||||
|
|
||||||
|
switch (history.Related)
|
||||||
{
|
{
|
||||||
_logger = logger;
|
case ReferenceType.Receiver:
|
||||||
_service = service;
|
withReceiver = true;
|
||||||
|
break;
|
||||||
|
case ReferenceType.Sender:
|
||||||
|
withSender = true;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
[HttpGet("reference-type")]
|
var histories = await _service.ReadAsync(
|
||||||
[Authorize]
|
envelopeId: history.EnvelopeId,
|
||||||
public IActionResult GetReferenceTypes()
|
referenceType: history.Related,
|
||||||
{
|
withSender: withSender,
|
||||||
// Enum to Key-Value pair
|
withReceiver: withReceiver);
|
||||||
var referenceTypes = Enum.GetValues(typeof(ReferenceType))
|
|
||||||
.Cast<ReferenceType>()
|
|
||||||
.ToDictionary(rt =>
|
|
||||||
{
|
|
||||||
var key = rt.ToString();
|
|
||||||
var keyAsCamelCase = char.ToLower(key[0]) + key[1..];
|
|
||||||
return keyAsCamelCase;
|
|
||||||
}, rt => (int)rt);
|
|
||||||
|
|
||||||
return Ok(referenceTypes);
|
return Ok(histories);
|
||||||
}
|
|
||||||
|
|
||||||
[HttpGet]
|
|
||||||
[Authorize]
|
|
||||||
public async Task<IActionResult> GetAllAsync([FromQuery] int? envelopeId = null, [FromQuery] string? userReference = null, [FromQuery] int? referenceType = null, [FromQuery] bool withSender = false, [FromQuery] bool withReceiver = false)
|
|
||||||
{
|
|
||||||
ReferenceType? refTypEnum = null;
|
|
||||||
|
|
||||||
if (referenceType is int refTypInt)
|
|
||||||
if (Enum.IsDefined(typeof(ReferenceType), refTypInt))
|
|
||||||
refTypEnum = (ReferenceType)refTypInt;
|
|
||||||
else
|
|
||||||
throw new ArgumentException($"The provided referenceType '{referenceType}' is not valid. It must correspond to a valid value in the {nameof(ReferenceType)} enum.");
|
|
||||||
|
|
||||||
switch(referenceType)
|
|
||||||
{
|
|
||||||
case (int)ReferenceType.Receiver:
|
|
||||||
withReceiver = true;
|
|
||||||
break;
|
|
||||||
case (int)ReferenceType.Sender:
|
|
||||||
withSender = true;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
var histories = await _service.ReadAsync(
|
|
||||||
envelopeId: envelopeId,
|
|
||||||
userReference: userReference,
|
|
||||||
referenceType: refTypEnum,
|
|
||||||
withSender: withSender,
|
|
||||||
withReceiver: withReceiver);
|
|
||||||
|
|
||||||
return Ok(histories);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -6,85 +6,115 @@ using Microsoft.AspNetCore.Mvc;
|
|||||||
using Microsoft.Extensions.Caching.Memory;
|
using Microsoft.Extensions.Caching.Memory;
|
||||||
using Microsoft.Extensions.Localization;
|
using Microsoft.Extensions.Localization;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
namespace EnvelopeGenerator.GeneratorAPI.Controllers;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Controller für die Verwaltung der Lokalisierung und Spracheinstellungen.
|
||||||
|
/// </summary>
|
||||||
|
[ApiExplorerSettings(IgnoreApi = true)]
|
||||||
|
[Route("api/[controller]")]
|
||||||
|
[ApiController]
|
||||||
|
public class LocalizationController : ControllerBase
|
||||||
{
|
{
|
||||||
[Route("api/[controller]")]
|
private static readonly Guid L_KEY = Guid.NewGuid();
|
||||||
[ApiController]
|
|
||||||
public class LocalizationController : ControllerBase
|
private readonly ILogger<LocalizationController> _logger;
|
||||||
|
private readonly IStringLocalizer<Model> _mLocalizer;
|
||||||
|
private readonly IStringLocalizer<Resource> _localizer;
|
||||||
|
private readonly IMemoryCache _cache;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Konstruktor für den <see cref="LocalizationController"/>.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="logger">Logger für die Protokollierung.</param>
|
||||||
|
/// <param name="localizer">Lokalisierungsdienst für Ressourcen.</param>
|
||||||
|
/// <param name="memoryCache">Speicher-Cache für die Zwischenspeicherung von Daten.</param>
|
||||||
|
/// <param name="_modelLocalizer">Lokalisierungsdienst für Modelle.</param>
|
||||||
|
public LocalizationController(
|
||||||
|
ILogger<LocalizationController> logger,
|
||||||
|
IStringLocalizer<Resource> localizer,
|
||||||
|
IMemoryCache memoryCache,
|
||||||
|
IStringLocalizer<Model> _modelLocalizer)
|
||||||
{
|
{
|
||||||
private static readonly Guid L_KEY = Guid.NewGuid();
|
_logger = logger;
|
||||||
|
_localizer = localizer;
|
||||||
|
_cache = memoryCache;
|
||||||
|
_mLocalizer = _modelLocalizer;
|
||||||
|
}
|
||||||
|
|
||||||
private readonly ILogger<LocalizationController> _logger;
|
/// <summary>
|
||||||
private readonly IStringLocalizer<Model> _mLocalizer;
|
/// Ruft alle lokalisierten Daten ab.
|
||||||
private readonly IStringLocalizer<Resource> _localizer;
|
/// </summary>
|
||||||
private readonly IMemoryCache _cache;
|
/// <returns>Eine Liste aller lokalisierten Daten.</returns>
|
||||||
|
[HttpGet]
|
||||||
|
public IActionResult GetAll() => Ok(_cache.GetOrCreate(Language ?? string.Empty + L_KEY, _ => _mLocalizer.ToDictionary()));
|
||||||
|
|
||||||
public LocalizationController(
|
/// <summary>
|
||||||
ILogger<LocalizationController> logger,
|
/// Ruft die aktuelle Sprache ab.
|
||||||
IStringLocalizer<Resource> localizer,
|
/// </summary>
|
||||||
IMemoryCache memoryCache,
|
/// <returns>Die aktuelle Sprache oder ein NotFound-Ergebnis, wenn keine Sprache gesetzt ist.</returns>
|
||||||
IStringLocalizer<Model> _modelLocalizer)
|
[HttpGet("lang")]
|
||||||
|
public IActionResult GetLanguage() => Language is null ? NotFound() : Ok(Language);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Setzt die Sprache.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="language">Die zu setzende Sprache.</param>
|
||||||
|
/// <returns>Ein Ok-Ergebnis, wenn die Sprache erfolgreich gesetzt wurde, oder ein BadRequest-Ergebnis, wenn die Eingabe ungültig ist.</returns>
|
||||||
|
[HttpPost("lang")]
|
||||||
|
public IActionResult SetLanguage([FromQuery] string language)
|
||||||
|
{
|
||||||
|
if (string.IsNullOrEmpty(language))
|
||||||
|
return BadRequest();
|
||||||
|
|
||||||
|
Language = language;
|
||||||
|
return Ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Löscht die aktuelle Sprache.
|
||||||
|
/// </summary>
|
||||||
|
/// <returns>Ein Ok-Ergebnis, wenn die Sprache erfolgreich gelöscht wurde.</returns>
|
||||||
|
[HttpDelete("lang")]
|
||||||
|
public IActionResult DeleteLanguage()
|
||||||
|
{
|
||||||
|
Language = null;
|
||||||
|
return Ok();
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Eigenschaft für die Verwaltung der aktuellen Sprache über Cookies.
|
||||||
|
/// </summary>
|
||||||
|
private string? Language
|
||||||
|
{
|
||||||
|
get
|
||||||
{
|
{
|
||||||
_logger = logger;
|
var cookieValue = Request.Cookies[CookieRequestCultureProvider.DefaultCookieName];
|
||||||
_localizer = localizer;
|
|
||||||
_cache = memoryCache;
|
if (string.IsNullOrEmpty(cookieValue))
|
||||||
_mLocalizer = _modelLocalizer;
|
return null;
|
||||||
|
|
||||||
|
var culture = CookieRequestCultureProvider.ParseCookieValue(cookieValue)?.Cultures[0];
|
||||||
|
return culture?.Value ?? null;
|
||||||
}
|
}
|
||||||
|
set
|
||||||
[HttpGet]
|
|
||||||
public IActionResult GetAll() => Ok(_cache.GetOrCreate(Language ?? string.Empty + L_KEY, _ => _mLocalizer.ToDictionary()));
|
|
||||||
|
|
||||||
[HttpGet("lang")]
|
|
||||||
public IActionResult GetLanguage() => Language is null ? NotFound() : Ok(Language);
|
|
||||||
|
|
||||||
[HttpPost("lang")]
|
|
||||||
public IActionResult SetLanguage([FromQuery] string language)
|
|
||||||
{
|
{
|
||||||
if (string.IsNullOrEmpty(language))
|
if (value is null)
|
||||||
return BadRequest();
|
Response.Cookies.Delete(CookieRequestCultureProvider.DefaultCookieName);
|
||||||
|
else
|
||||||
Language = language;
|
|
||||||
return Ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
[HttpDelete("lang")]
|
|
||||||
public IActionResult DeleteLanguage()
|
|
||||||
{
|
|
||||||
Language = null;
|
|
||||||
return Ok();
|
|
||||||
}
|
|
||||||
|
|
||||||
private string? Language
|
|
||||||
{
|
|
||||||
get
|
|
||||||
{
|
{
|
||||||
var cookieValue = Request.Cookies[CookieRequestCultureProvider.DefaultCookieName];
|
var cookieOptions = new CookieOptions()
|
||||||
|
|
||||||
if (string.IsNullOrEmpty(cookieValue))
|
|
||||||
return null;
|
|
||||||
|
|
||||||
var culture = CookieRequestCultureProvider.ParseCookieValue(cookieValue)?.Cultures[0];
|
|
||||||
return culture?.Value ?? null;
|
|
||||||
}
|
|
||||||
set
|
|
||||||
{
|
|
||||||
if (value is null)
|
|
||||||
Response.Cookies.Delete(CookieRequestCultureProvider.DefaultCookieName);
|
|
||||||
else
|
|
||||||
{
|
{
|
||||||
var cookieOptions = new CookieOptions()
|
Expires = DateTimeOffset.UtcNow.AddYears(1),
|
||||||
{
|
Secure = false,
|
||||||
Expires = DateTimeOffset.UtcNow.AddYears(1),
|
SameSite = SameSiteMode.Strict,
|
||||||
Secure = false,
|
HttpOnly = true
|
||||||
SameSite = SameSiteMode.Strict,
|
};
|
||||||
HttpOnly = true
|
|
||||||
};
|
|
||||||
|
|
||||||
Response.Cookies.Append(
|
Response.Cookies.Append(
|
||||||
CookieRequestCultureProvider.DefaultCookieName,
|
CookieRequestCultureProvider.DefaultCookieName,
|
||||||
CookieRequestCultureProvider.MakeCookieValue(new RequestCulture(value)),
|
CookieRequestCultureProvider.MakeCookieValue(new RequestCulture(value)),
|
||||||
cookieOptions);
|
cookieOptions);
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,88 +2,97 @@
|
|||||||
using DigitalData.Core.DTO;
|
using DigitalData.Core.DTO;
|
||||||
using EnvelopeGenerator.Application.Contracts.Services;
|
using EnvelopeGenerator.Application.Contracts.Services;
|
||||||
using EnvelopeGenerator.Application.DTOs.Receiver;
|
using EnvelopeGenerator.Application.DTOs.Receiver;
|
||||||
|
using EnvelopeGenerator.Application.Receivers.Queries.Read;
|
||||||
using EnvelopeGenerator.Domain.Entities;
|
using EnvelopeGenerator.Domain.Entities;
|
||||||
using Microsoft.AspNetCore.Authorization;
|
using Microsoft.AspNetCore.Authorization;
|
||||||
using Microsoft.AspNetCore.Mvc;
|
using Microsoft.AspNetCore.Mvc;
|
||||||
|
|
||||||
namespace EnvelopeGenerator.GeneratorAPI.Controllers
|
namespace EnvelopeGenerator.GeneratorAPI.Controllers;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Controller für die Verwaltung von Empfängern.
|
||||||
|
/// </summary>
|
||||||
|
/// <remarks>
|
||||||
|
/// Dieser Controller bietet Endpunkte für CRUD-Operationen (Erstellen, Lesen, Aktualisieren, Löschen)
|
||||||
|
/// sowie zusätzliche Funktionen wie das Abrufen von Empfängern basierend auf E-Mail-Adresse oder Signatur.
|
||||||
|
/// </remarks>
|
||||||
|
[Route("api/[controller]")]
|
||||||
|
[ApiController]
|
||||||
|
[Authorize]
|
||||||
|
public class ReceiverController : CRUDControllerBaseWithErrorHandling<IReceiverService, ReceiverCreateDto, ReceiverReadDto, ReceiverUpdateDto, Receiver, int>
|
||||||
{
|
{
|
||||||
[Route("api/[controller]")]
|
/// <summary>
|
||||||
[ApiController]
|
/// Initialisiert eine neue Instanz des <see cref="ReceiverController"/>-Controllers.
|
||||||
[Authorize]
|
/// </summary>
|
||||||
public class ReceiverController : CRUDControllerBaseWithErrorHandling<IReceiverService, ReceiverCreateDto, ReceiverReadDto, ReceiverUpdateDto, Receiver, int>
|
/// <param name="logger">Der Logger für die Protokollierung.</param>
|
||||||
|
/// <param name="service">Der Dienst für Empfängeroperationen.</param>
|
||||||
|
public ReceiverController(ILogger<ReceiverController> logger, IReceiverService service) : base(logger, service)
|
||||||
{
|
{
|
||||||
public ReceiverController(ILogger<ReceiverController> logger, IReceiverService service) : base(logger, service)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
[HttpGet]
|
|
||||||
public async Task<IActionResult> Get([FromQuery] string? emailAddress = null, [FromQuery] string? signature = null)
|
|
||||||
{
|
|
||||||
if (emailAddress is null && signature is null)
|
|
||||||
return await base.GetAll();
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
return await _service.ReadByAsync(emailAddress: emailAddress, signature: signature).ThenAsync(
|
|
||||||
Success: Ok,
|
|
||||||
Fail: IActionResult (msg, ntc) =>
|
|
||||||
{
|
|
||||||
_logger.LogNotice(ntc);
|
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
catch(Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "{Message}", ex.Message);
|
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
[HttpPost]
|
|
||||||
public async override Task<IActionResult> Create(ReceiverCreateDto createDto)
|
|
||||||
{
|
|
||||||
if (!ModelState.IsValid)
|
|
||||||
return BadRequest(ModelState);
|
|
||||||
|
|
||||||
return await base.Create(createDto);
|
|
||||||
}
|
|
||||||
|
|
||||||
[HttpDelete]
|
|
||||||
public async Task<IActionResult> Delete([FromQuery] int? id = null, [FromQuery]string? emailAddress = null, [FromQuery] string? signature = null)
|
|
||||||
{
|
|
||||||
if(id is int id_int)
|
|
||||||
return await base.Delete(id_int);
|
|
||||||
|
|
||||||
try
|
|
||||||
{
|
|
||||||
if (emailAddress is not null || signature is not null)
|
|
||||||
return await _service.DeleteByAsync(emailAddress: emailAddress, signature: signature).ThenAsync(
|
|
||||||
Success: Ok,
|
|
||||||
Fail: IActionResult (msg, ntc) =>
|
|
||||||
{
|
|
||||||
_logger.LogNotice(ntc);
|
|
||||||
return StatusCode(StatusCodes.Status500InternalServerError);
|
|
||||||
});
|
|
||||||
}
|
|
||||||
catch(Exception ex)
|
|
||||||
{
|
|
||||||
_logger.LogError(ex, "{Message}", ex.Message);
|
|
||||||
return StatusCode(500);
|
|
||||||
}
|
|
||||||
|
|
||||||
return BadRequest();
|
|
||||||
}
|
|
||||||
|
|
||||||
#region REMOVED ENDPOINTS
|
|
||||||
[NonAction]
|
|
||||||
public override Task<IActionResult> GetAll() => base.GetAll();
|
|
||||||
|
|
||||||
[NonAction]
|
|
||||||
public override Task<IActionResult> Delete([FromRoute] int id) => base.Delete(id);
|
|
||||||
|
|
||||||
[NonAction]
|
|
||||||
public override Task<IActionResult> Update(ReceiverUpdateDto updateDto) => base.Update(updateDto);
|
|
||||||
#endregion
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Ruft eine Liste von Empfängern ab, basierend auf den angegebenen Abfrageparametern.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="receiver">Die Abfrageparameter, einschließlich E-Mail-Adresse und Signatur.</param>
|
||||||
|
/// <returns>Eine Liste von Empfängern oder ein Fehlerstatus.</returns>
|
||||||
|
[HttpGet]
|
||||||
|
public async Task<IActionResult> Get([FromQuery] ReadReceiverQuery receiver)
|
||||||
|
{
|
||||||
|
if (receiver.EmailAddress is null && receiver.Signature is null)
|
||||||
|
return await base.GetAll();
|
||||||
|
|
||||||
|
try
|
||||||
|
{
|
||||||
|
return await _service.ReadByAsync(emailAddress: receiver.EmailAddress, signature: receiver.Signature).ThenAsync(
|
||||||
|
Success: Ok,
|
||||||
|
Fail: IActionResult (msg, ntc) =>
|
||||||
|
{
|
||||||
|
_logger.LogNotice(ntc);
|
||||||
|
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
catch (Exception ex)
|
||||||
|
{
|
||||||
|
_logger.LogError(ex, "{Message}", ex.Message);
|
||||||
|
return StatusCode(StatusCodes.Status500InternalServerError);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#region REMOVED ENDPOINTS
|
||||||
|
/// <summary>
|
||||||
|
/// Diese Methode ist deaktiviert und wird nicht verwendet.
|
||||||
|
/// </summary>
|
||||||
|
[NonAction]
|
||||||
|
public override Task<IActionResult> GetAll() => base.GetAll();
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Diese Methode ist deaktiviert und wird nicht verwendet.
|
||||||
|
/// </summary>
|
||||||
|
[NonAction]
|
||||||
|
public override Task<IActionResult> Delete([FromRoute] int id) => base.Delete(id);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Diese Methode ist deaktiviert und wird nicht verwendet.
|
||||||
|
/// </summary>
|
||||||
|
[NonAction]
|
||||||
|
public override Task<IActionResult> Update(ReceiverUpdateDto updateDto) => base.Update(updateDto);
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Diese Methode ist deaktiviert und wird nicht verwendet.
|
||||||
|
/// </summary>
|
||||||
|
[NonAction]
|
||||||
|
public override Task<IActionResult> Create(ReceiverCreateDto createDto)
|
||||||
|
{
|
||||||
|
return base.Create(createDto);
|
||||||
|
}
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Diese Methode ist deaktiviert und wird nicht verwendet.
|
||||||
|
/// </summary>
|
||||||
|
[NonAction]
|
||||||
|
public override Task<IActionResult> GetById([FromRoute] int id)
|
||||||
|
{
|
||||||
|
return base.GetById(id);
|
||||||
|
}
|
||||||
|
#endregion
|
||||||
}
|
}
|
||||||
@@ -1,16 +1,29 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk.Web">
|
<Project Sdk="Microsoft.NET.Sdk.Web">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net7.0</TargetFramework>
|
<TargetFrameworks>net9.0</TargetFrameworks>
|
||||||
<Nullable>enable</Nullable>
|
<Nullable>enable</Nullable>
|
||||||
<ImplicitUsings>enable</ImplicitUsings>
|
<ImplicitUsings>enable</ImplicitUsings>
|
||||||
|
<GenerateDocumentationFile>true</GenerateDocumentationFile>
|
||||||
|
<PackageId>EnvelopeGenerator.GeneratorAPI</PackageId>
|
||||||
|
<Title></Title>
|
||||||
|
<Authors>Digital Data GmbH</Authors>
|
||||||
|
<Company>Digital Data GmbH</Company>
|
||||||
|
<Product>EnvelopeGenerator.GeneratorAPI</Product>
|
||||||
|
<Version>1.1.0</Version>
|
||||||
|
<FileVersion>1.1.0</FileVersion>
|
||||||
|
<AssemblyVersion>1.1.0</AssemblyVersion>
|
||||||
|
<PackageOutputPath>Copyright © 2025 Digital Data GmbH. All rights reserved.</PackageOutputPath>
|
||||||
|
<DocumentationFile>bin\$(Configuration)\$(TargetFramework)\$(AssemblyName).xml</DocumentationFile>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
|
<PackageReference Include="AspNetCore.Scalar" Version="1.1.8" />
|
||||||
<PackageReference Include="DigitalData.Core.Abstractions" Version="2.2.1" />
|
<PackageReference Include="DigitalData.Core.Abstractions" Version="2.2.1" />
|
||||||
<PackageReference Include="DigitalData.Core.API" Version="2.0.0" />
|
<PackageReference Include="DigitalData.Core.API" Version="2.0.0" />
|
||||||
<PackageReference Include="Microsoft.AspNetCore.OpenApi" Version="7.0.15" />
|
<PackageReference Include="Microsoft.AspNetCore.OpenApi" Version="9.0.3" />
|
||||||
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.5.0" />
|
<PackageReference Include="Scalar.AspNetCore" Version="2.1.4" />
|
||||||
|
<PackageReference Include="Swashbuckle.AspNetCore" Version="8.1.0" />
|
||||||
<PackageReference Include="System.DirectoryServices" Version="7.0.1" />
|
<PackageReference Include="System.DirectoryServices" Version="7.0.1" />
|
||||||
<PackageReference Include="System.DirectoryServices.AccountManagement" Version="7.0.1" />
|
<PackageReference Include="System.DirectoryServices.AccountManagement" Version="7.0.1" />
|
||||||
<PackageReference Include="System.DirectoryServices.Protocols" Version="7.0.1" />
|
<PackageReference Include="System.DirectoryServices.Protocols" Version="7.0.1" />
|
||||||
|
|||||||
13
EnvelopeGenerator.GeneratorAPI/Models/Login.cs
Normal file
13
EnvelopeGenerator.GeneratorAPI/Models/Login.cs
Normal file
@@ -0,0 +1,13 @@
|
|||||||
|
using System.ComponentModel.DataAnnotations;
|
||||||
|
|
||||||
|
namespace EnvelopeGenerator.GeneratorAPI.Models;
|
||||||
|
|
||||||
|
/// <summary>
|
||||||
|
/// Repräsentiert ein Login-Modell mit erforderlichem Passwort und optionaler ID und Benutzername.
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="Password">Das erforderliche Passwort für das Login.</param>
|
||||||
|
/// <param name="Id">Die optionale ID des Benutzers.</param>
|
||||||
|
/// <param name="Username">Der optionale Benutzername.</param>
|
||||||
|
public record Login([Required] string Password, int? Id = null, string? Username = null)
|
||||||
|
{
|
||||||
|
}
|
||||||
@@ -7,6 +7,9 @@ using Microsoft.AspNetCore.Authentication.Cookies;
|
|||||||
using Microsoft.AspNetCore.Localization;
|
using Microsoft.AspNetCore.Localization;
|
||||||
using Microsoft.EntityFrameworkCore;
|
using Microsoft.EntityFrameworkCore;
|
||||||
using System.Globalization;
|
using System.Globalization;
|
||||||
|
using Scalar.AspNetCore;
|
||||||
|
using Microsoft.OpenApi.Models;
|
||||||
|
using System.Reflection;
|
||||||
|
|
||||||
var builder = WebApplication.CreateBuilder(args);
|
var builder = WebApplication.CreateBuilder(args);
|
||||||
|
|
||||||
@@ -31,8 +34,53 @@ builder.Services.AddCors(options =>
|
|||||||
|
|
||||||
// Swagger
|
// Swagger
|
||||||
builder.Services.AddEndpointsApiExplorer();
|
builder.Services.AddEndpointsApiExplorer();
|
||||||
builder.Services.AddSwaggerGen();
|
builder.Services.AddSwaggerGen(options =>
|
||||||
|
{
|
||||||
|
options.SwaggerDoc("v1", new OpenApiInfo
|
||||||
|
{
|
||||||
|
Version = "v1",
|
||||||
|
Title = "signFLOW Absender-API",
|
||||||
|
Description = "Eine API zur Verwaltung der Erstellung, des Versands und der Nachverfolgung von Umschlägen in der signFLOW-Anwendung.",
|
||||||
|
Contact = new OpenApiContact
|
||||||
|
{
|
||||||
|
Name = "Digital Data GmbH",
|
||||||
|
Url = new Uri("https://digitaldata.works/digitale-signatur#kontakt"),
|
||||||
|
Email = "info-flow@digitaldata.works"
|
||||||
|
},
|
||||||
|
});
|
||||||
|
|
||||||
|
options.AddSecurityDefinition("Bearer", new OpenApiSecurityScheme
|
||||||
|
{
|
||||||
|
Name = "Authorization",
|
||||||
|
Type = SecuritySchemeType.Http,
|
||||||
|
Scheme = "Bearer",
|
||||||
|
BearerFormat = "JWT",
|
||||||
|
In = ParameterLocation.Header,
|
||||||
|
Description = "JWT-Autorisierungs-Header unter Verwendung des Bearer-Schemas.",
|
||||||
|
});
|
||||||
|
|
||||||
|
options.AddSecurityRequirement(new OpenApiSecurityRequirement
|
||||||
|
{
|
||||||
|
{
|
||||||
|
new OpenApiSecurityScheme
|
||||||
|
{
|
||||||
|
Reference = new OpenApiReference
|
||||||
|
{
|
||||||
|
Type = ReferenceType.SecurityScheme,
|
||||||
|
Id = "Bearer"
|
||||||
|
}
|
||||||
|
},
|
||||||
|
new string[] {}
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
var xmlFiles = Directory.GetFiles(AppContext.BaseDirectory, "*.xml");
|
||||||
|
foreach (var xmlFile in xmlFiles)
|
||||||
|
{
|
||||||
|
options.IncludeXmlComments(xmlFile);
|
||||||
|
}
|
||||||
|
});
|
||||||
|
builder.Services.AddOpenApi();
|
||||||
// DbContext
|
// DbContext
|
||||||
var connStr = config.GetConnectionString("Default") ?? throw new InvalidOperationException("There is no default connection string in appsettings.json.");
|
var connStr = config.GetConnectionString("Default") ?? throw new InvalidOperationException("There is no default connection string in appsettings.json.");
|
||||||
builder.Services.AddDbContext<EGDbContext>(options => options.UseSqlServer(connStr));
|
builder.Services.AddDbContext<EGDbContext>(options => options.UseSqlServer(connStr));
|
||||||
@@ -60,15 +108,20 @@ builder.Services.AddDirectorySearchService();
|
|||||||
builder.Services.AddCookieBasedLocalizer() ;
|
builder.Services.AddCookieBasedLocalizer() ;
|
||||||
|
|
||||||
// Envelope generator serives
|
// Envelope generator serives
|
||||||
builder.Services.AddEnvelopeGenerator(config);
|
builder.Services
|
||||||
|
.AddEnvelopeGeneratorRepositories()
|
||||||
|
.AddEnvelopeGeneratorServices(config);
|
||||||
|
|
||||||
var app = builder.Build();
|
var app = builder.Build();
|
||||||
|
|
||||||
|
app.MapOpenApi();
|
||||||
|
|
||||||
// Configure the HTTP request pipeline.
|
// Configure the HTTP request pipeline.
|
||||||
if (app.Environment.IsDevelopment())
|
if (app.Environment.IsDevelopment() || (app.IsDevOrDiP() && config.GetValue<bool>("UseSwagger")))
|
||||||
{
|
{
|
||||||
app.UseSwagger();
|
app.UseSwagger();
|
||||||
app.UseSwaggerUI();
|
app.UseSwaggerUI();
|
||||||
|
app.MapScalarApiReference();
|
||||||
}
|
}
|
||||||
|
|
||||||
// Set CORS policy
|
// Set CORS policy
|
||||||
|
|||||||
@@ -1,4 +1,6 @@
|
|||||||
{
|
{
|
||||||
|
"UseSwagger": true,
|
||||||
|
"DiPMode": true,
|
||||||
"Logging": {
|
"Logging": {
|
||||||
"LogLevel": {
|
"LogLevel": {
|
||||||
"Default": "Information",
|
"Default": "Information",
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
<Project Sdk="Microsoft.NET.Sdk">
|
<Project Sdk="Microsoft.NET.Sdk">
|
||||||
|
|
||||||
<PropertyGroup>
|
<PropertyGroup>
|
||||||
<TargetFramework>net7.0</TargetFramework>
|
<TargetFrameworks>net7.0;net8.0;net9.0</TargetFrameworks>
|
||||||
<ImplicitUsings>enable</ImplicitUsings>
|
<ImplicitUsings>enable</ImplicitUsings>
|
||||||
<Nullable>enable</Nullable>
|
<Nullable>enable</Nullable>
|
||||||
</PropertyGroup>
|
</PropertyGroup>
|
||||||
|
|||||||
Reference in New Issue
Block a user