using System.Net; using Autofac; using FitConnect.Encryption; using FitConnect.Models; using FitConnect.Services; using FitConnect.Services.Interfaces; using FitConnect.Services.Models.v1.Submission; using Microsoft.Extensions.Logging; using Microsoft.IdentityModel.Tokens; namespace FitConnect; public abstract class FitConnectClient { private readonly string? _privateKeyDecryption; private readonly string? _privateKeySigning; private readonly string? _publicKeyEncryption; private readonly string? _publicKeySignatureVerification; protected readonly bool VerifiedKeysAreMandatory; protected FitConnectClient(FitConnectEnvironment environment, string clientId, string clientSecret, ILogger? logger = null, string? privateKeyDecryption = null, string? privateKeySigning = null, string? publicKeyEncryption = null, string? publicKeySignatureVerification = null ) : this() { _privateKeyDecryption = privateKeyDecryption; _privateKeySigning = privateKeySigning; _publicKeyEncryption = publicKeyEncryption; _publicKeySignatureVerification = publicKeySignatureVerification; OAuthService = new OAuthService(environment.TokenUrl, "V1", clientId, clientSecret, logger); SubmissionService = new SubmissionService(environment.SubmissionUrl[0], OAuthService, publicKeySignatureVerification == null ? null : new JsonWebKey(publicKeySignatureVerification), logger: logger); RouteService = new RouteService(environment.RoutingUrl, logger: logger); CasesService = new CasesService(environment.SubmissionUrl[0], OAuthService, logger: logger); DestinationService = new DestinationService(environment.SubmissionUrl[0], OAuthService, logger: logger); Logger = logger; VerifiedKeysAreMandatory = environment.VerifiedKeysAreMandatory; } protected FitConnectClient(FitConnectEnvironment environment, string clientId, string clientSecret, IContainer container, string? privateKeyDecryption = null, string? privateKeySigning = null, string? publicKeyEncryption = null, string? publicKeySignatureVerification = null ) : this() { _privateKeyDecryption = privateKeyDecryption; _privateKeySigning = privateKeySigning; _publicKeyEncryption = publicKeyEncryption; _publicKeySignatureVerification = publicKeySignatureVerification; OAuthService = container.Resolve<IOAuthService>(); SubmissionService = container.Resolve<ISubmissionService>(); RouteService = container.Resolve<IRouteService>(); CasesService = container.Resolve<ICasesService>(); DestinationService = container.Resolve<IDestinationService>(); Logger = container.Resolve<ILogger>(); } private FitConnectClient() { // Take care of OAuthService if make the constructor public Encryption = new FitEncryption(Logger); } public IOAuthService OAuthService { get; } = null!; // To resolve the warning, is only applicable for the **private** constructor protected ISubmissionService SubmissionService { get; } = null!; protected IRouteService RouteService { get; } = null!; protected IDestinationService DestinationService { get; } = null!; protected ICasesService CasesService { get; } = null!; protected ILogger? Logger { get; } protected FitEncryption Encryption { get; set; } public void SetProxy(WebProxy proxy) { OAuthService.Proxy = proxy; SubmissionService.Proxy = proxy; DestinationService.Proxy = proxy; RouteService.Proxy = proxy; } public WebProxy? GetProxy() { return OAuthService.Proxy; } /// <summary> /// Retrieve the events for the submission /// </summary> /// <param name="caseId"></param> /// <param name="destinationId"></param> /// <param name="skipTest"></param> /// <returns></returns> public List<SecurityEventToken> GetStatusForSubmission(string caseId, string destinationId, bool skipTest = false) { var events = SubmissionService.GetStatusForSubmissionAsync(caseId, destinationId, skipTest) .Result?.Select(e => new SecurityEventToken(e!)).ToList() ?? new List<SecurityEventToken>(); return events; } /// <summary> /// Retrieve the events for the submission /// </summary> /// <param name="submission"></param> /// <param name="skipTest"></param> /// <returns></returns> public List<SecurityEventToken> GetStatusForSubmission(SubmissionForPickupDto submission, bool skipTest = false) { if (submission?.CaseId == null || submission.DestinationId == null) { throw new ArgumentNullException(nameof(submission)); } var events = SubmissionService .GetStatusForSubmissionAsync(submission.CaseId, submission.DestinationId, skipTest) .Result; return events?.Select(e => new SecurityEventToken(e)).ToList() ?? new List<SecurityEventToken>(); } /// <summary> /// Encrypt attachments (Anhänge) /// </summary> /// <param name="publicKey"></param> /// <param name="attachment"></param> /// <returns></returns> public KeyValuePair<string, string> Encrypt(string publicKey, Attachment attachment) { var content = Encryption.Encrypt(attachment.Content ?? Array.Empty<byte>(), publicKey); return new KeyValuePair<string, string>(attachment.Id, content); } /// <summary> /// Encrypt attachments (Anhänge) /// </summary> /// <param name="publicKey">Public key for encryption</param> /// <param name="attachments">List of attachments to encrypt</param> /// <returns></returns> public Dictionary<string, string> Encrypt(string publicKey, IEnumerable<Attachment> attachments) { return attachments.Select(a => Encrypt(publicKey, a)) .ToDictionary(p => p.Key, p => p.Value); } } public static class FitConnectClientExtensions { /// <summary> /// </summary> /// <param name="host"></param> /// <param name="port"></param> /// <param name="username"></param> /// <param name="password"></param> /// <returns></returns> public static T WithProxy<T>(this T caller, string host, int port, string? username = null, string? password = null) where T : FitConnectClient { var proxy = new WebProxy(host, port); if (username != null && password != null) proxy.Credentials = new NetworkCredential(username, password); caller.SetProxy(proxy); return caller; } }