diff --git a/Alexa.NET.Security.Functions/Alexa.NET.Security.Functions.csproj b/Alexa.NET.Security.Functions/Alexa.NET.Security.Functions.csproj index cf5989d..a9106dc 100644 --- a/Alexa.NET.Security.Functions/Alexa.NET.Security.Functions.csproj +++ b/Alexa.NET.Security.Functions/Alexa.NET.Security.Functions.csproj @@ -22,7 +22,7 @@ - + diff --git a/Alexa.NET.Security.Functions/AlexaRequestValidationFunctionsExtension.cs b/Alexa.NET.Security.Functions/AlexaRequestValidationFunctionsExtension.cs index f407781..27a9aa6 100644 --- a/Alexa.NET.Security.Functions/AlexaRequestValidationFunctionsExtension.cs +++ b/Alexa.NET.Security.Functions/AlexaRequestValidationFunctionsExtension.cs @@ -3,12 +3,16 @@ using Microsoft.Azure.WebJobs.Extensions.Http; using Microsoft.Extensions.Logging; using System; +using System.Collections.Generic; +using System.Security.Cryptography.X509Certificates; using System.Threading.Tasks; namespace Alexa.NET.Security.Functions { public static class AlexaRequestValidationFunctionsExtension { + private static KeyValuePair certificateCache; + /// /// Validates an incoming request against Amazon security guidelines. /// @@ -83,6 +87,30 @@ private static Uri GetSignatureCertChainUrlFromRequest(HttpRequest httpRequest) return signatureCertChainUrl; } + private static async Task GetCertificate(Uri signatureCertChainUrl) + { + if (signatureCertChainUrl == null) + return null; + + if (certificateCache.Key == null || certificateCache.Key.ToString().ToLowerInvariant() != signatureCertChainUrl.ToString().ToLowerInvariant()) + { + try + { + X509Certificate2 certificate = await RequestVerification.GetCertificate(signatureCertChainUrl); + if (certificate != null) + certificateCache = new KeyValuePair(signatureCertChainUrl, certificate); + + return certificate; + } + catch + { + return null; + } + } + else + return certificateCache.Value; + } + /// /// Gets the Signature value from http request headers. /// @@ -124,7 +152,7 @@ private static bool IsTimestampValid(SkillRequest skillRequest) /// private static async Task IsRequestValid(string signature, Uri signatureCertChainUrl, string body) { - return await RequestVerification.Verify(signature, signatureCertChainUrl, body); + return await RequestVerification.Verify(signature, signatureCertChainUrl, body, GetCertificate); } } } \ No newline at end of file