· 6 years ago · Feb 13, 2020, 09:12 AM
1using KongArthur.Billing.Core;
2using KongArthur.Billpipe.KredinorCallbackAPI.Models;
3using KongArthur.Billpipe.KredinorCallbackAPI.Props;
4using Microsoft.IdentityModel.Tokens;
5using System;
6using System.Collections.Generic;
7using System.IdentityModel.Tokens.Jwt;
8using System.IO;
9using System.Linq;
10using System.Net;
11using System.Net.Http;
12using System.Security.Claims;
13using System.Security.Cryptography;
14using System.Web;
15using System.Web.Http;
16
17namespace KongArthur.Billpipe.KredinorCallbackAPI.Controllers
18{
19 public class APIController : ApiController
20 {
21
22 /**
23 * Every request from Kredinor should go here.
24 * eventType header tells what kind of event it is
25 *
26 * The data is encrypted, and needs to be decrypted.
27 */
28 [HttpPost]
29 public string Post(HttpRequestMessage request)
30 {
31 Logger.WriteLog("Request start", "DEBUG");
32
33 try
34 {
35
36
37
38 MemoryStream ms = new MemoryStream();
39 HttpContext.Current.Request.InputStream.CopyTo(ms);
40
41
42 string encryptionKey = "4czR3L/GGjDjVBE8n4Fr+wQH2DLZKz1YKaQf9Et6WVU=";
43 //HttpRequestMessage request = "incoming request from Kredinor API";
44 string jwtToken = request.Headers.FirstOrDefault(h => h.Key == "x-kredinor-token").Value.First(); // Decrypt and validate JWE x-event-type
45 string eventType = request.Headers.FirstOrDefault(h => h.Key == "x-event-type").Value.First(); // Get event type
46
47 Logger.WriteLog($"Request is {eventType}", "DEBUG");
48 var handler = new JwtSecurityTokenHandler();
49 ClaimsPrincipal token = handler.ValidateToken(
50 jwtToken,
51 new TokenValidationParameters
52 {
53 TokenDecryptionKey = new SymmetricSecurityKey(Convert.FromBase64String(encryptionKey)),
54 IssuerSigningKey = new SymmetricSecurityKey(Convert.FromBase64String(encryptionKey)),
55 ValidateAudience = false,
56 ValidateActor = false,
57 ValidateIssuer = false,
58 ValidateLifetime = false,
59 },
60 out SecurityToken cleanToken);
61 // Fetch AES IV to decrypt payload;
62 Claim iv = token.Claims.FirstOrDefault(c => c.Type == "piv");
63
64 // Use Key and IV to decrypt using AES string decryptedPayload;
65 using (var aes = new AesCryptoServiceProvider())
66 {
67 aes.Key = Convert.FromBase64String(encryptionKey);
68 aes.IV = Convert.FromBase64String(iv.Value);
69 var decryptor = aes.CreateDecryptor(aes.Key, aes.IV);
70 using (var msDecrypt = new MemoryStream(ms.ToArray()))
71 {
72 using (var csDecrypt = new CryptoStream(msDecrypt, decryptor, CryptoStreamMode.Read))
73 {
74 using (var srDecrypt = new StreamReader(csDecrypt))
75 {
76 string decryptedPayload = srDecrypt.ReadToEnd();
77 Logger.WriteLog($"Decrypted data: \n{decryptedPayload}", "DEBUG");
78 try
79 {
80 if (eventType == EventType.Receipt.Value)
81 {
82 ReceiptController.HandleReceipt(new KredinorReceipt(json: decryptedPayload));
83 } else if (eventType == EventType.Status.Value)
84 {
85 StatusController.HandleStatus(new KredinorStatus(json: decryptedPayload));
86 } else if (eventType == EventType.Address.Value)
87 {
88 AddressController.HandleAddress(new KredinorAddress(json: decryptedPayload));
89 }
90
91
92 } catch(Exception e)
93 {
94 Logger.WriteLog($"{e.Message}", "ERROR");
95 }
96
97 }
98 }
99 }
100 }
101 } catch (Exception e)
102 {
103 Logger.WriteLog(e.Message, "ERROR", LoggType.Error, LogLocation.kredinor);
104 return "Something failed";
105
106 }
107
108
109 return "Success";
110
111 }
112 }
113}