From 4637cb5e8360a9fb1a89ac341da7c89a62e28375 Mon Sep 17 00:00:00 2001 From: Doug Ellner Date: Tue, 15 Oct 2019 07:50:16 -0700 Subject: [PATCH 1/7] Fixed Typo CheckMillieSeconds => CheckMilliSeconds --- Examples/AskMessage/Startup.cs | 2 +- Examples/CustomLoginPage/Startup.cs | 2 +- Examples/CustomLoginPageWithHtmlHelpers/Startup.cs | 2 +- Examples/HelpersProvidersAndOtherPaths/Startup.cs | 2 +- Examples/InMemory/Startup.cs | 2 +- Examples/StoringNuts/Startup.cs | 2 +- Examples/WithDatabase/Startup.cs | 2 +- SqrlForNet/SqrlAuthenticationOptions.cs | 4 ++-- SqrlForNet/SqrlCommandWorker.cs | 6 +++--- SqrlForNet/SqrlHtmlHelper.cs | 14 +++++++------- SqrlForNet/SqrlUrlProvider.cs | 2 +- 11 files changed, 20 insertions(+), 20 deletions(-) diff --git a/Examples/AskMessage/Startup.cs b/Examples/AskMessage/Startup.cs index 040a74b..3dfffef 100644 --- a/Examples/AskMessage/Startup.cs +++ b/Examples/AskMessage/Startup.cs @@ -31,7 +31,7 @@ public void ConfigureServices(IServiceCollection services) }) .AddSqrl(options => { - options.CheckMillieSeconds = 1000; + options.CheckMilliSeconds = 1000; options.CreateUser = SqrlCreateUser; options.UserExists = UserExists; options.UpdateUserId = UpdateUserId; diff --git a/Examples/CustomLoginPage/Startup.cs b/Examples/CustomLoginPage/Startup.cs index 4224c6a..4264349 100644 --- a/Examples/CustomLoginPage/Startup.cs +++ b/Examples/CustomLoginPage/Startup.cs @@ -29,7 +29,7 @@ public void ConfigureServices(IServiceCollection services) }) .AddSqrl(options => { - options.CheckMillieSeconds = 1000; + options.CheckMilliSeconds = 1000; options.CreateUser = SqrlCreateUser; options.UserExists = UserExists; options.UpdateUserId = UpdateUserId; diff --git a/Examples/CustomLoginPageWithHtmlHelpers/Startup.cs b/Examples/CustomLoginPageWithHtmlHelpers/Startup.cs index dce54d6..e0122fd 100644 --- a/Examples/CustomLoginPageWithHtmlHelpers/Startup.cs +++ b/Examples/CustomLoginPageWithHtmlHelpers/Startup.cs @@ -31,7 +31,7 @@ public void ConfigureServices(IServiceCollection services) }) .AddSqrl(options => { - options.CheckMillieSeconds = 1000; + options.CheckMilliSeconds = 1000; options.CreateUser = SqrlCreateUser; options.UserExists = UserExists; options.UpdateUserId = UpdateUserId; diff --git a/Examples/HelpersProvidersAndOtherPaths/Startup.cs b/Examples/HelpersProvidersAndOtherPaths/Startup.cs index 9b1074a..5e09191 100644 --- a/Examples/HelpersProvidersAndOtherPaths/Startup.cs +++ b/Examples/HelpersProvidersAndOtherPaths/Startup.cs @@ -31,7 +31,7 @@ public void ConfigureServices(IServiceCollection services) }) .AddSqrl(options => { - options.CheckMillieSeconds = 1000; + options.CheckMilliSeconds = 1000; options.CreateUser = SqrlCreateUser; options.UserExists = UserExists; options.UpdateUserId = UpdateUserId; diff --git a/Examples/InMemory/Startup.cs b/Examples/InMemory/Startup.cs index 4970cc0..a14d2d7 100644 --- a/Examples/InMemory/Startup.cs +++ b/Examples/InMemory/Startup.cs @@ -29,7 +29,7 @@ public void ConfigureServices(IServiceCollection services) }) .AddSqrl(options => { - options.CheckMillieSeconds = 1000; + options.CheckMilliSeconds = 1000; options.CreateUser = SqrlCreateUser; options.UserExists = UserExists; options.UpdateUserId = UpdateUserId; diff --git a/Examples/StoringNuts/Startup.cs b/Examples/StoringNuts/Startup.cs index 2899f0d..d662402 100644 --- a/Examples/StoringNuts/Startup.cs +++ b/Examples/StoringNuts/Startup.cs @@ -29,7 +29,7 @@ public void ConfigureServices(IServiceCollection services) }) .AddSqrl(options => { - options.CheckMillieSeconds = 1000; + options.CheckMilliSeconds = 1000; options.CreateUser = SqrlCreateUser; options.UserExists = UserExists; options.UpdateUserId = UpdateUserId; diff --git a/Examples/WithDatabase/Startup.cs b/Examples/WithDatabase/Startup.cs index 0a50fe4..c7c31ac 100644 --- a/Examples/WithDatabase/Startup.cs +++ b/Examples/WithDatabase/Startup.cs @@ -38,7 +38,7 @@ public void ConfigureServices(IServiceCollection services) }) .AddSqrl(options => { - options.CheckMillieSeconds = 10000; + options.CheckMilliSeconds = 10000; options.CreateUserAsync = new SqrlManager().CreateUser; options.UserExistsAsync = new SqrlManager().UserExists; options.UpdateUserIdAsync = new SqrlManager().UpdateUserId; diff --git a/SqrlForNet/SqrlAuthenticationOptions.cs b/SqrlForNet/SqrlAuthenticationOptions.cs index f6bfbeb..b4c4ea9 100644 --- a/SqrlForNet/SqrlAuthenticationOptions.cs +++ b/SqrlForNet/SqrlAuthenticationOptions.cs @@ -16,7 +16,7 @@ public class SqrlAuthenticationOptions : RemoteAuthenticationOptions public int NutExpiresInSeconds { get; set; } - public int CheckMillieSeconds { get; set; } + public int CheckMilliSeconds { get; set; } public string NameForAnonymous { get; set; } @@ -525,7 +525,7 @@ public SqrlAuthenticationOptions() CallbackPath = "/login-sqrl"; NutExpiresInSeconds = 60; - CheckMillieSeconds = 1000; + CheckMilliSeconds = 1000; NameForAnonymous = "SQRL anonymous user"; Diagnostics = false; diff --git a/SqrlForNet/SqrlCommandWorker.cs b/SqrlForNet/SqrlCommandWorker.cs index 163f23f..cb40627 100644 --- a/SqrlForNet/SqrlCommandWorker.cs +++ b/SqrlForNet/SqrlCommandWorker.cs @@ -622,7 +622,7 @@ private string QrCodePageHtml(string url, string checkUrl, string cancelUrl, str responseMessage.AppendLine("}"); responseMessage.AppendLine(""); responseMessage.AppendLine(""); - responseMessage.AppendLine(""); + responseMessage.AppendLine(""); responseMessage.AppendLine("

SQRL login page

"); responseMessage.AppendLine(""); responseMessage.AppendLine($"Sign in with SQRL"); @@ -692,13 +692,13 @@ internal void CacheHelperValues() _logger.LogTrace("Adding values to cache"); _logger.LogDebug("The CallbackUrl is: {0}", url); - _logger.LogDebug("The CheckMillieSeconds is: {0}", Options.CheckMillieSeconds); + _logger.LogDebug("The CheckMilliSeconds is: {0}", Options.CheckMilliSeconds); _logger.LogDebug("The CheckUrl is: {0}", checkUrl); Request.HttpContext.Items.Add("CallbackUrl", url); Request.HttpContext.Items.Add("QrData", qrCode); - Request.HttpContext.Items.Add("CheckMillieSeconds", Options.CheckMillieSeconds); + Request.HttpContext.Items.Add("CheckMilliSeconds", Options.CheckMilliSeconds); Request.HttpContext.Items.Add("CheckUrl", checkUrl); if (Options.OtherAuthenticationPaths != null && Options.OtherAuthenticationPaths.Any()) { diff --git a/SqrlForNet/SqrlHtmlHelper.cs b/SqrlForNet/SqrlHtmlHelper.cs index 1b4a756..6817b36 100644 --- a/SqrlForNet/SqrlHtmlHelper.cs +++ b/SqrlForNet/SqrlHtmlHelper.cs @@ -24,7 +24,7 @@ public static HtmlString SqrlLink(this IHtmlHelper helper, HttpR public static HtmlString SqrlLink(this IHtmlHelper helper, HttpRequest request, string text, bool poll) { ValidateRequestData(request); - return SqrlLink(helper, request, text, poll, int.Parse(request.HttpContext.Items["CheckMillieSeconds"].ToString())); + return SqrlLink(helper, request, text, poll, int.Parse(request.HttpContext.Items["CheckMilliSeconds"].ToString())); } public static HtmlString SqrlLink(this IHtmlHelper helper, HttpRequest request, string text, bool poll, int pollTime) @@ -86,7 +86,7 @@ public static HtmlString SqrlLinkForPath(this IHtmlHelper helper public static HtmlString SqrlLinkForPath(this IHtmlHelper helper, HttpRequest request, string text, bool poll, string path) { ValidateRequestData(request, path); - return SqrlLinkForPath(helper, request, text, poll, int.Parse(request.HttpContext.Items["CheckMillieSeconds"].ToString()), path); + return SqrlLinkForPath(helper, request, text, poll, int.Parse(request.HttpContext.Items["CheckMilliSeconds"].ToString()), path); } public static HtmlString SqrlLinkForPath(this IHtmlHelper helper, HttpRequest request, string text, bool poll, int pollTime, string path) @@ -145,7 +145,7 @@ public static HtmlString SqrlQrImage(this IHtmlHelper helper, Ht public static HtmlString SqrlQrImage(this IHtmlHelper helper, HttpRequest request, bool poll) { ValidateRequestData(request); - return SqrlQrImage(helper, request, poll, int.Parse(request.HttpContext.Items["CheckMillieSeconds"].ToString())); + return SqrlQrImage(helper, request, poll, int.Parse(request.HttpContext.Items["CheckMilliSeconds"].ToString())); } public static HtmlString SqrlQrImage(this IHtmlHelper helper, HttpRequest request, bool poll, int pollTime) @@ -188,7 +188,7 @@ public static HtmlString SqrlQrImageForPath(this IHtmlHelper hel public static HtmlString SqrlQrImageForPath(this IHtmlHelper helper, HttpRequest request, bool poll, string path) { ValidateRequestData(request, path); - return SqrlQrImageForPath(helper, request, poll, int.Parse(request.HttpContext.Items["CheckMillieSeconds"].ToString()), path); + return SqrlQrImageForPath(helper, request, poll, int.Parse(request.HttpContext.Items["CheckMilliSeconds"].ToString()), path); } public static HtmlString SqrlQrImageForPath(this IHtmlHelper helper, HttpRequest request, bool poll, int pollTime, string path) @@ -237,7 +237,7 @@ public static HtmlString SqrlLinkAndImage(this IHtmlHelper helpe public static HtmlString SqrlLinkAndImage(this IHtmlHelper helper, HttpRequest request, string text, bool poll) { ValidateRequestData(request); - return SqrlLinkAndImage(helper, request, text, poll, int.Parse(request.HttpContext.Items["CheckMillieSeconds"].ToString())); + return SqrlLinkAndImage(helper, request, text, poll, int.Parse(request.HttpContext.Items["CheckMilliSeconds"].ToString())); } public static HtmlString SqrlLinkAndImage(this IHtmlHelper helper, HttpRequest request, string text, bool poll, int pollTime) @@ -259,7 +259,7 @@ public static HtmlString SqrlLinkAndImageForPath(this IHtmlHelper(this IHtmlHelper helper, HttpRequest request, string text, bool poll, string path) { ValidateRequestData(request, path); - return SqrlLinkAndImageForPath(helper, request, text, poll, int.Parse(request.HttpContext.Items["CheckMillieSeconds"].ToString()), path); + return SqrlLinkAndImageForPath(helper, request, text, poll, int.Parse(request.HttpContext.Items["CheckMilliSeconds"].ToString()), path); } public static HtmlString SqrlLinkAndImageForPath(this IHtmlHelper helper, HttpRequest request, string text, bool poll, int pollTime, string path) @@ -283,7 +283,7 @@ private static void ValidateRequestData(HttpRequest request, string path = null) } if (!request.HttpContext.Items.ContainsKey("CallbackUrl") || !request.HttpContext.Items.ContainsKey("QrData") || - !request.HttpContext.Items.ContainsKey("CheckMillieSeconds") || + !request.HttpContext.Items.ContainsKey("CheckMilliSeconds") || !request.HttpContext.Items.ContainsKey("CheckUrl") ) { diff --git a/SqrlForNet/SqrlUrlProvider.cs b/SqrlForNet/SqrlUrlProvider.cs index bdf5526..b1f2912 100644 --- a/SqrlForNet/SqrlUrlProvider.cs +++ b/SqrlForNet/SqrlUrlProvider.cs @@ -39,7 +39,7 @@ public static string SqrlQrData(this HttpResponse response) public static string GetCheckMilliseconds(HttpRequest request) { - return request.HttpContext.Items["CheckMillieSeconds"].ToString(); + return request.HttpContext.Items["CheckMilliSeconds"].ToString(); } public static string SqrlCheckMilliseconds(this HttpRequest request) From 110ec46fd07005ad3a86ab4e5adfbb29c5efd9ef Mon Sep 17 00:00:00 2001 From: Liam Raper Date: Wed, 16 Oct 2019 16:43:16 +0100 Subject: [PATCH 2/7] Changed from Get and Remove methods to GetRemove methods --- Examples/StoringNuts/Startup.cs | 51 +++---- SqrlForNet/SqrlAuthenticationHandler.cs | 5 +- SqrlForNet/SqrlAuthenticationOptions.cs | 176 ++++++++---------------- SqrlForNet/SqrlCommandWorker.cs | 9 +- 4 files changed, 86 insertions(+), 155 deletions(-) diff --git a/Examples/StoringNuts/Startup.cs b/Examples/StoringNuts/Startup.cs index 2899f0d..1d2af13 100644 --- a/Examples/StoringNuts/Startup.cs +++ b/Examples/StoringNuts/Startup.cs @@ -44,15 +44,12 @@ public void ConfigureServices(IServiceCollection services) //These are used to manage nuts options.StoreNut = StoreNut; - options.GetNut = GetNut; - options.RemoveNut = RemoveNut; + options.GetAndRemoveNut = GetAndRemoveNut; options.GetNutIdk = GetNutIdk; - options.CheckNutAuthorized = CheckNutAuthorized; + options.RemoveAuthorizedNut = RemoveAuthorizedNut; options.StoreCpsSessionId = StoreCpsSessionId; - options.GetUserIdByCpsSessionId = GetUserIdByCpsSessionId; - options.RemoveCpsSessionId = RemoveCpsSessionId; - + options.GetUserIdAndRemoveCpsSessionId = GetUserIdAndRemoveCpsSessionId; }); services.AddMvc(); @@ -158,13 +155,15 @@ private Task OnTicketReceived(TicketReceivedContext context) /// private static readonly Dictionary AuthorizedNutList = new Dictionary(); - private NutInfo GetNut(string nut, bool authorized) + private NutInfo GetAndRemoveNut(string nut) { - if (authorized) + if (NutList.ContainsKey(nut)) { - return AuthorizedNutList.ContainsKey(nut) ? AuthorizedNutList[nut] : null; + var info = NutList[nut]; + NutList.Remove(nut); + return info; } - return NutList.ContainsKey(nut) ? NutList[nut] : null; + return null; } private void StoreNut(string nut, NutInfo info, bool authorized) @@ -179,21 +178,15 @@ private void StoreNut(string nut, NutInfo info, bool authorized) } } - private void RemoveNut(string nut, bool authorized) + private bool RemoveAuthorizedNut(string nut) { - if (authorized) + var authorizedNut = AuthorizedNutList.SingleOrDefault(x => x.Key == nut || x.Value.FirstNut == nut); + if (authorizedNut.Key == nut) { AuthorizedNutList.Remove(nut); + return true; } - else - { - NutList.Remove(nut); - } - } - - private bool CheckNutAuthorized(string nut) - { - return AuthorizedNutList.Any(x => x.Key == nut || x.Value.FirstNut == nut); + return false; } private string GetNutIdk(string nut) @@ -209,16 +202,16 @@ private void StoreCpsSessionId(string sessionId, string userId) CpsSessions.Add(sessionId, userId); } - private string GetUserIdByCpsSessionId(string sessionId) + private string GetUserIdAndRemoveCpsSessionId(string sessionId) { - return CpsSessions.ContainsKey(sessionId) ? CpsSessions[sessionId] : null; - } + if (CpsSessions.ContainsKey(sessionId)) + { + var userId = CpsSessions[sessionId]; + CpsSessions.Remove(userId); + return userId; + } - private void RemoveCpsSessionId(string sessionId) - { - CpsSessions.Remove(sessionId); + return null; } - - } } diff --git a/SqrlForNet/SqrlAuthenticationHandler.cs b/SqrlForNet/SqrlAuthenticationHandler.cs index e57002e..8af9fb9 100644 --- a/SqrlForNet/SqrlAuthenticationHandler.cs +++ b/SqrlForNet/SqrlAuthenticationHandler.cs @@ -133,7 +133,6 @@ private Task CheckRequest() }; Logger.LogDebug("The userId is: {0}", userId); Logger.LogDebug("The username is: {0}", username); - Options.RemoveNutInternal(Request.Query["check"], true); var identity = new ClaimsIdentity(claims, Scheme.Name); var principal = new ClaimsPrincipal(identity); @@ -148,7 +147,7 @@ private Task CheckRequest() private Task CheckCpsRequest() { - var result = Options.GetUserIdByCpsSessionIdInternal(Request.Query["cps"]); + var result = Options.GetUserIdAndRemoveCpsSessionIdInternal(Request.Query["cps"]); if (!string.IsNullOrEmpty(result)) { var username = Options.GetUsernameInternal(result, Context); @@ -158,8 +157,6 @@ private Task CheckCpsRequest() new Claim(ClaimTypes.Name, username) }; - Options.RemoveCpsSessionIdInternal(Request.Query["cps"]); - var identity = new ClaimsIdentity(claims, Scheme.Name); var principal = new ClaimsPrincipal(identity); var ticket = new AuthenticationTicket(principal, Scheme.Name); diff --git a/SqrlForNet/SqrlAuthenticationOptions.cs b/SqrlForNet/SqrlAuthenticationOptions.cs index f6bfbeb..bfe6eb2 100644 --- a/SqrlForNet/SqrlAuthenticationOptions.cs +++ b/SqrlForNet/SqrlAuthenticationOptions.cs @@ -168,38 +168,29 @@ internal void RemoveUserInternal(string idk, HttpContext context) } } - public Action RemoveNut; + public Func GetAndRemoveNut; - public Func RemoveNutAsync; + public Func> GetAndRemoveNutAsync; - internal void RemoveNutInternal(string nut, bool authorized) - { - if (RemoveNut != null) - { - RemoveNut.Invoke(nut, authorized); - } - else - { - RemoveNutAsync.Invoke(nut, authorized).Wait(); - } - } - - public Func GetNut; + private KeyValuePair _currentNutInfo; - public Func> GetNutAsync; - - internal NutInfo GetNutInternal(string nut, bool authorized) + internal NutInfo GetAndRemoveNutInternal(string nut) { - if (GetNut != null) + if (_currentNutInfo.Key != nut) { - return GetNut.Invoke(nut, authorized); - } - else - { - var task = GetNutAsync.Invoke(nut, authorized); - task.Wait(); - return task.Result; + if (GetAndRemoveNut != null) + { + _currentNutInfo = new KeyValuePair(nut, GetAndRemoveNut.Invoke(nut)); + } + else + { + var task = GetAndRemoveNutAsync.Invoke(nut); + task.Wait(); + _currentNutInfo = new KeyValuePair(nut, task.Result); + } } + + return _currentNutInfo.Value; } public Action StoreNut; @@ -218,19 +209,19 @@ internal void StoreNutInternal(string nut, NutInfo info, bool authorized) } } - public Func CheckNutAuthorized; + public Func RemoveAuthorizedNut; - public Func> CheckNutAuthorizedAsync; + public Func> RemoveAuthorizedNutAsync; - internal bool CheckNutAuthorizedInternal(string nut) + internal bool RemoveAuthorizedNutInternal(string nut) { - if (CheckNutAuthorized != null) + if (RemoveAuthorizedNut != null) { - return CheckNutAuthorized.Invoke(nut); + return RemoveAuthorizedNut.Invoke(nut); } else { - var task = CheckNutAuthorizedAsync.Invoke(nut); + var task = RemoveAuthorizedNutAsync.Invoke(nut); task.Wait(); return task.Result; } @@ -270,40 +261,24 @@ internal void StoreCpsSessionIdInternal(string code, string idk) } } - public Func GetUserIdByCpsSessionId; + public Func GetUserIdAndRemoveCpsSessionId; - public Func> GetUserIdByCpsSessionIdAsync; + public Func> GetUserIdAndRemoveCpsSessionIdAsync; - internal string GetUserIdByCpsSessionIdInternal(string code) + internal string GetUserIdAndRemoveCpsSessionIdInternal(string code) { - if (GetUserIdByCpsSessionId != null) + if (GetUserIdAndRemoveCpsSessionId != null) { - return GetUserIdByCpsSessionId.Invoke(code); + return GetUserIdAndRemoveCpsSessionId.Invoke(code); } else { - var task = GetUserIdByCpsSessionIdAsync.Invoke(code); + var task = GetUserIdAndRemoveCpsSessionIdAsync.Invoke(code); task.Wait(); return task.Result; } } - public Action RemoveCpsSessionId; - - public Func RemoveCpsSessionIdAsync; - - internal void RemoveCpsSessionIdInternal(string code) - { - if (RemoveCpsSessionId != null) - { - RemoveCpsSessionId.Invoke(code); - } - else - { - RemoveCpsSessionIdAsync.Invoke(code).Wait(); - } - } - public Action SqrlOnlyReceived; public Func SqrlOnlyReceivedAsync; @@ -393,8 +368,7 @@ internal string GetUsernameInternal(string userId, HttpContext context) return NameForAnonymous; } } - - + private static readonly Dictionary NutList = new Dictionary(); private static readonly Dictionary AuthorizedNutList = new Dictionary(); @@ -421,21 +395,19 @@ private void ClearOldNuts() } } - private NutInfo GetNutMethod(string nut, bool authorized) + private NutInfo GetAndRemoveNutMethod(string nut) { ClearOldNuts(); - if (authorized) + lock (NutList) { - lock (AuthorizedNutList) + if (NutList.ContainsKey(nut)) { - return AuthorizedNutList.ContainsKey(nut) ? AuthorizedNutList[nut] : null; + var info = NutList[nut]; + NutList.Remove(nut); + return info; } } - - lock (NutList) - { - return NutList.ContainsKey(nut) ? NutList[nut] : null; - } + return null; } private void StoreNutMethod(string nut, NutInfo info, bool authorized) @@ -457,31 +429,18 @@ private void StoreNutMethod(string nut, NutInfo info, bool authorized) } } - private void RemoveNutMethod(string nut, bool authorized) + private bool RemoveAuthorizedNutMethod(string nut) { ClearOldNuts(); - if (authorized) - { - lock (AuthorizedNutList) - { - AuthorizedNutList.Remove(nut); - } - } - else + lock (AuthorizedNutList) { - lock (NutList) + var authorizedNut = AuthorizedNutList.SingleOrDefault(x => x.Key == nut || x.Value.FirstNut == nut); + if (authorizedNut.Key == nut) { - NutList.Remove(nut); + AuthorizedNutList.Remove(authorizedNut.Key); + return true; } - } - } - - private bool CheckNutAuthorizedMethod(string nut) - { - ClearOldNuts(); - lock (AuthorizedNutList) - { - return AuthorizedNutList.Any(x => x.Key == nut || x.Value.FirstNut == nut); + return false; } } @@ -504,20 +463,16 @@ private void StoreCpsSessionIdMethod(string sessionId, string userId) } } - private string GetUserIdByCpsSessionIdMethod(string sessionId) - { - lock (CpsSessions) - { - return CpsSessions.ContainsKey(sessionId) ? CpsSessions[sessionId] : null; - } - } - - private void RemoveCpsSessionIdMethod(string sessionId) + private string GetUserIdAndRemoveCpsSessionIdMethod(string sessionId) { lock (CpsSessions) { - CpsSessions.Remove(sessionId); + if (CpsSessions.ContainsKey(sessionId)) + { + return CpsSessions[sessionId]; + } } + return null; } public SqrlAuthenticationOptions() @@ -534,16 +489,13 @@ public SqrlAuthenticationOptions() Events = new RemoteAuthenticationEvents(); - RemoveNut = RemoveNutMethod; - GetNut = GetNutMethod; + GetAndRemoveNut = GetAndRemoveNutMethod; StoreNut = StoreNutMethod; - CheckNutAuthorized = CheckNutAuthorizedMethod; + RemoveAuthorizedNut = RemoveAuthorizedNutMethod; GetNutIdk = GetNutIdkMethod; StoreCpsSessionId = StoreCpsSessionIdMethod; - GetUserIdByCpsSessionId = GetUserIdByCpsSessionIdMethod; - RemoveCpsSessionId = RemoveCpsSessionIdMethod; - + GetUserIdAndRemoveCpsSessionId = GetUserIdAndRemoveCpsSessionIdMethod; } public override void Validate() @@ -675,14 +627,9 @@ public override void Validate() throw new ArgumentException($"{nameof(RemoveUser)} and {nameof(RemoveUserAsync)} are both defined you should only define one of them."); } - if (RemoveNut != null && RemoveNutAsync != null) + if (GetAndRemoveNut != null && GetAndRemoveNutAsync != null) { - throw new ArgumentException($"{nameof(RemoveNut)} and {nameof(RemoveNutAsync)} are both defined you should only define one of them."); - } - - if (GetNut != null && GetNutAsync != null) - { - throw new ArgumentException($"{nameof(GetNut)} and {nameof(GetNutAsync)} are both defined you should only define one of them."); + throw new ArgumentException($"{nameof(GetAndRemoveNut)} and {nameof(GetAndRemoveNutAsync)} are both defined you should only define one of them."); } if (StoreNut != null && StoreNutAsync != null) @@ -690,9 +637,9 @@ public override void Validate() throw new ArgumentException($"{nameof(StoreNut)} and {nameof(StoreNutAsync)} are both defined you should only define one of them."); } - if (CheckNutAuthorized != null && CheckNutAuthorizedAsync != null) + if (RemoveAuthorizedNut != null && RemoveAuthorizedNutAsync != null) { - throw new ArgumentException($"{nameof(CheckNutAuthorized)} and {nameof(CheckNutAuthorized)} are both defined you should only define one of them."); + throw new ArgumentException($"{nameof(RemoveAuthorizedNut)} and {nameof(RemoveAuthorizedNut)} are both defined you should only define one of them."); } if (GetNutIdk != null && GetNutIdkAsync != null) @@ -705,14 +652,9 @@ public override void Validate() throw new ArgumentException($"{nameof(StoreCpsSessionId)} and {nameof(StoreCpsSessionIdAsync)} are both defined you should only define one of them."); } - if (GetUserIdByCpsSessionId != null && GetUserIdByCpsSessionIdAsync != null) - { - throw new ArgumentException($"{nameof(GetUserIdByCpsSessionId)} and {nameof(GetUserIdByCpsSessionIdAsync)} are both defined you should only define one of them."); - } - - if (RemoveCpsSessionId != null && RemoveCpsSessionIdAsync != null) + if (GetUserIdAndRemoveCpsSessionId != null && GetUserIdAndRemoveCpsSessionIdAsync != null) { - throw new ArgumentException($"{nameof(RemoveCpsSessionId)} and {nameof(RemoveCpsSessionIdAsync)} are both defined you should only define one of them."); + throw new ArgumentException($"{nameof(GetUserIdAndRemoveCpsSessionId)} and {nameof(GetUserIdAndRemoveCpsSessionIdAsync)} are both defined you should only define one of them."); } if (SqrlOnlyReceived != null && SqrlOnlyReceivedAsync != null) diff --git a/SqrlForNet/SqrlCommandWorker.cs b/SqrlForNet/SqrlCommandWorker.cs index 163f23f..45cf3cd 100644 --- a/SqrlForNet/SqrlCommandWorker.cs +++ b/SqrlForNet/SqrlCommandWorker.cs @@ -113,7 +113,6 @@ public void NutRequest() BadCommand(); } _logger.LogTrace("Removing NUT: {0}", Request.Query["nut"]); - Options.RemoveNutInternal(Request.Query["nut"], false); } private bool IsValidNutRequest() @@ -180,7 +179,7 @@ private NutValidationResult NutStatus() { _logger.LogTrace("Getting status of NUT"); var nut = Request.Query["nut"]; - var nutInfo = Options.GetNutInternal(nut, false); + var nutInfo = Options.GetAndRemoveNutInternal(nut); if (nutInfo == null) { @@ -368,7 +367,7 @@ private bool AuthorizeNut(string nut) var opts = ParseOpts(); if (!opts[OptKey.cps]) { - var nutInfo = Options.GetNutInternal(nut, false); + var nutInfo = Options.GetAndRemoveNutInternal(nut); var authNutInfo = new NutInfo { FirstNut = nutInfo.FirstNut, @@ -747,7 +746,7 @@ public bool CheckPage() { var checkNut = Request.Query["check"]; - var isAuthorized = Options.CheckNutAuthorizedInternal(checkNut); + var isAuthorized = Options.RemoveAuthorizedNutInternal(checkNut); if (!isAuthorized) { var responseMessage = new StringBuilder(); @@ -827,7 +826,7 @@ private NutInfo NewNutInfo() NutInfo currentNut = null; if (Request.Query.ContainsKey("nut")) { - currentNut = Options.GetNutInternal(Request.Query["nut"], false); + currentNut = Options.GetAndRemoveNutInternal(Request.Query["nut"]); } return new NutInfo { From 518ba428c22fbe9233f5977924efe72bd9c995e8 Mon Sep 17 00:00:00 2001 From: Liam Raper Date: Wed, 16 Oct 2019 17:30:51 +0100 Subject: [PATCH 3/7] Added HTTPContext to all hooks and added nut info to database example to test --- Examples/StoringNuts/Startup.cs | 12 +- .../WithDatabase/Database/DatabaseContext.cs | 2 + Examples/WithDatabase/Database/NutInfoData.cs | 16 +++ ...191016162244_AddedNutStoreData.Designer.cs | 107 ++++++++++++++++++ .../20191016162244_AddedNutStoreData.cs | 33 ++++++ .../DatabaseContextModelSnapshot.cs | 26 +++++ Examples/WithDatabase/SqrlManager.cs | 49 +++++++- Examples/WithDatabase/Startup.cs | 4 + Examples/WithDatabase/WithDatabase.csproj | 9 ++ SqrlForNet/Interfaces/AskMessageHooks.cs | 4 +- .../Interfaces/CpsSessionManagementHooks.cs | 4 +- SqrlForNet/Interfaces/INutManagementHooks.cs | 21 ++-- SqrlForNet/SqrlAuthenticationHandler.cs | 4 +- SqrlForNet/SqrlAuthenticationOptions.cs | 72 ++++++------ SqrlForNet/SqrlCommandWorker.cs | 14 +-- 15 files changed, 308 insertions(+), 69 deletions(-) create mode 100644 Examples/WithDatabase/Database/NutInfoData.cs create mode 100644 Examples/WithDatabase/Migrations/20191016162244_AddedNutStoreData.Designer.cs create mode 100644 Examples/WithDatabase/Migrations/20191016162244_AddedNutStoreData.cs diff --git a/Examples/StoringNuts/Startup.cs b/Examples/StoringNuts/Startup.cs index 1d2af13..7cec3ae 100644 --- a/Examples/StoringNuts/Startup.cs +++ b/Examples/StoringNuts/Startup.cs @@ -155,7 +155,7 @@ private Task OnTicketReceived(TicketReceivedContext context) /// private static readonly Dictionary AuthorizedNutList = new Dictionary(); - private NutInfo GetAndRemoveNut(string nut) + private NutInfo GetAndRemoveNut(string nut, HttpContext httpContext) { if (NutList.ContainsKey(nut)) { @@ -166,7 +166,7 @@ private NutInfo GetAndRemoveNut(string nut) return null; } - private void StoreNut(string nut, NutInfo info, bool authorized) + private void StoreNut(string nut, NutInfo info, bool authorized, HttpContext arg4) { if (authorized) { @@ -178,7 +178,7 @@ private void StoreNut(string nut, NutInfo info, bool authorized) } } - private bool RemoveAuthorizedNut(string nut) + private bool RemoveAuthorizedNut(string nut, HttpContext httpContext) { var authorizedNut = AuthorizedNutList.SingleOrDefault(x => x.Key == nut || x.Value.FirstNut == nut); if (authorizedNut.Key == nut) @@ -189,7 +189,7 @@ private bool RemoveAuthorizedNut(string nut) return false; } - private string GetNutIdk(string nut) + private string GetNutIdk(string nut, HttpContext httpContext) { return AuthorizedNutList.Single(x => x.Key == nut || x.Value.FirstNut == nut).Value.Idk; } @@ -197,12 +197,12 @@ private string GetNutIdk(string nut) private static readonly Dictionary CpsSessions = new Dictionary(); - private void StoreCpsSessionId(string sessionId, string userId) + private void StoreCpsSessionId(string sessionId, string userId, HttpContext arg3) { CpsSessions.Add(sessionId, userId); } - private string GetUserIdAndRemoveCpsSessionId(string sessionId) + private string GetUserIdAndRemoveCpsSessionId(string sessionId, HttpContext httpContext) { if (CpsSessions.ContainsKey(sessionId)) { diff --git a/Examples/WithDatabase/Database/DatabaseContext.cs b/Examples/WithDatabase/Database/DatabaseContext.cs index ff21a9f..c72abbe 100644 --- a/Examples/WithDatabase/Database/DatabaseContext.cs +++ b/Examples/WithDatabase/Database/DatabaseContext.cs @@ -12,6 +12,8 @@ public DatabaseContext(DbContextOptions options) : base(options public DbSet SqrlUser { get; set; } public DbSet User { get; set; } + + public DbSet Nuts { get; set; } public void UpdateDatabase() { diff --git a/Examples/WithDatabase/Database/NutInfoData.cs b/Examples/WithDatabase/Database/NutInfoData.cs new file mode 100644 index 0000000..b517fa8 --- /dev/null +++ b/Examples/WithDatabase/Database/NutInfoData.cs @@ -0,0 +1,16 @@ +using System.ComponentModel.DataAnnotations; +using Microsoft.EntityFrameworkCore.Scaffolding.Metadata; +using SqrlForNet; + +namespace WithDatabase.Database +{ + public class NutInfoData : NutInfo + { + + [Key] + public string Nut { get; set; } + + public bool Authorized { get; set; } + + } +} \ No newline at end of file diff --git a/Examples/WithDatabase/Migrations/20191016162244_AddedNutStoreData.Designer.cs b/Examples/WithDatabase/Migrations/20191016162244_AddedNutStoreData.Designer.cs new file mode 100644 index 0000000..ce52d21 --- /dev/null +++ b/Examples/WithDatabase/Migrations/20191016162244_AddedNutStoreData.Designer.cs @@ -0,0 +1,107 @@ +// +using System; +using Microsoft.EntityFrameworkCore; +using Microsoft.EntityFrameworkCore.Infrastructure; +using Microsoft.EntityFrameworkCore.Metadata; +using Microsoft.EntityFrameworkCore.Migrations; +using Microsoft.EntityFrameworkCore.Storage.ValueConversion; +using WithDatabase.Database; + +namespace WithDatabase.Migrations +{ + [DbContext(typeof(DatabaseContext))] + [Migration("20191016162244_AddedNutStoreData")] + partial class AddedNutStoreData + { + protected override void BuildTargetModel(ModelBuilder modelBuilder) + { +#pragma warning disable 612, 618 + modelBuilder + .HasAnnotation("ProductVersion", "3.0.0") + .HasAnnotation("Relational:MaxIdentifierLength", 128) + .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn); + + modelBuilder.Entity("WithDatabase.Database.NutInfoData", b => + { + b.Property("Nut") + .HasColumnType("nvarchar(450)"); + + b.Property("Authorized") + .HasColumnType("bit"); + + b.Property("CreatedDate") + .HasColumnType("datetime2"); + + b.Property("FirstNut") + .HasColumnType("nvarchar(max)"); + + b.Property("Idk") + .HasColumnType("nvarchar(max)"); + + b.Property("IpAddress") + .HasColumnType("nvarchar(max)"); + + b.HasKey("Nut"); + + b.ToTable("Nuts"); + }); + + modelBuilder.Entity("WithDatabase.Database.SqrlUser", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("int") + .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn); + + b.Property("Locked") + .HasColumnType("bit"); + + b.Property("Suk") + .HasColumnType("nvarchar(max)"); + + b.Property("UserId") + .HasColumnType("nvarchar(max)"); + + b.Property("Vuk") + .HasColumnType("nvarchar(max)"); + + b.HasKey("Id"); + + b.ToTable("SqrlUser"); + }); + + modelBuilder.Entity("WithDatabase.Database.User", b => + { + b.Property("Id") + .ValueGeneratedOnAdd() + .HasColumnType("int") + .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn); + + b.Property("Role") + .HasColumnType("nvarchar(max)"); + + b.Property("SqrlUserId") + .HasColumnType("int"); + + b.Property("Username") + .HasColumnType("nvarchar(max)"); + + b.HasKey("Id"); + + b.HasIndex("SqrlUserId"); + + b.ToTable("User"); + }); + + modelBuilder.Entity("WithDatabase.Database.User", b => + { + b.HasOne("WithDatabase.Database.SqrlUser", "SqrlUser") + .WithMany() + .HasForeignKey("SqrlUserId") + .OnDelete(DeleteBehavior.Cascade) + .IsRequired(); + }); +#pragma warning restore 612, 618 + } + } +} diff --git a/Examples/WithDatabase/Migrations/20191016162244_AddedNutStoreData.cs b/Examples/WithDatabase/Migrations/20191016162244_AddedNutStoreData.cs new file mode 100644 index 0000000..c9c42fc --- /dev/null +++ b/Examples/WithDatabase/Migrations/20191016162244_AddedNutStoreData.cs @@ -0,0 +1,33 @@ +using System; +using Microsoft.EntityFrameworkCore.Migrations; + +namespace WithDatabase.Migrations +{ + public partial class AddedNutStoreData : Migration + { + protected override void Up(MigrationBuilder migrationBuilder) + { + migrationBuilder.CreateTable( + name: "Nuts", + columns: table => new + { + Nut = table.Column(nullable: false), + CreatedDate = table.Column(nullable: false), + IpAddress = table.Column(nullable: true), + FirstNut = table.Column(nullable: true), + Idk = table.Column(nullable: true), + Authorized = table.Column(nullable: false) + }, + constraints: table => + { + table.PrimaryKey("PK_Nuts", x => x.Nut); + }); + } + + protected override void Down(MigrationBuilder migrationBuilder) + { + migrationBuilder.DropTable( + name: "Nuts"); + } + } +} diff --git a/Examples/WithDatabase/Migrations/DatabaseContextModelSnapshot.cs b/Examples/WithDatabase/Migrations/DatabaseContextModelSnapshot.cs index af9254d..f080a3a 100644 --- a/Examples/WithDatabase/Migrations/DatabaseContextModelSnapshot.cs +++ b/Examples/WithDatabase/Migrations/DatabaseContextModelSnapshot.cs @@ -1,4 +1,5 @@ // +using System; using Microsoft.EntityFrameworkCore; using Microsoft.EntityFrameworkCore.Infrastructure; using Microsoft.EntityFrameworkCore.Metadata; @@ -18,6 +19,31 @@ protected override void BuildModel(ModelBuilder modelBuilder) .HasAnnotation("Relational:MaxIdentifierLength", 128) .HasAnnotation("SqlServer:ValueGenerationStrategy", SqlServerValueGenerationStrategy.IdentityColumn); + modelBuilder.Entity("WithDatabase.Database.NutInfoData", b => + { + b.Property("Nut") + .HasColumnType("nvarchar(450)"); + + b.Property("Authorized") + .HasColumnType("bit"); + + b.Property("CreatedDate") + .HasColumnType("datetime2"); + + b.Property("FirstNut") + .HasColumnType("nvarchar(max)"); + + b.Property("Idk") + .HasColumnType("nvarchar(max)"); + + b.Property("IpAddress") + .HasColumnType("nvarchar(max)"); + + b.HasKey("Nut"); + + b.ToTable("Nuts"); + }); + modelBuilder.Entity("WithDatabase.Database.SqrlUser", b => { b.Property("Id") diff --git a/Examples/WithDatabase/SqrlManager.cs b/Examples/WithDatabase/SqrlManager.cs index 72ecad8..40faf58 100644 --- a/Examples/WithDatabase/SqrlManager.cs +++ b/Examples/WithDatabase/SqrlManager.cs @@ -1,4 +1,5 @@ -using System.Threading.Tasks; +using System.Linq; +using System.Threading.Tasks; using Microsoft.AspNetCore.Http; using Microsoft.EntityFrameworkCore; using Microsoft.Extensions.DependencyInjection; @@ -8,7 +9,7 @@ namespace WithDatabase { - public class SqrlManager : IUserManagementRequiredHooksAsync, IUserManagementOptionalHooksAsync + public class SqrlManager : IUserManagementRequiredHooksAsync, IUserManagementOptionalHooksAsync, INutManagementHooksAsync { public async Task UserExists(string userId, HttpContext context) @@ -103,5 +104,49 @@ public async Task GetUsername(string userId, HttpContext context) var user = await _database.User.Include(x => x.SqrlUser).SingleAsync(x => x.SqrlUser.UserId == userId); return user.Username; } + + public async Task GetAndRemoveNut(string nut, HttpContext context) + { + var _database = context.RequestServices.GetRequiredService(); + var nutData = await _database.Nuts.FindAsync(nut); + _database.Nuts.Remove(nutData); + await _database.SaveChangesAsync(); + return nutData; + } + + public async Task StoreNut(string nut, NutInfo info, bool authorized, HttpContext context) + { + var _database = context.RequestServices.GetRequiredService(); + await _database.Nuts.AddAsync(new NutInfoData() + { + Nut = nut, + CreatedDate = info.CreatedDate, + FirstNut = info.FirstNut, + Idk = info.Idk, + IpAddress = info.IpAddress + }); + await _database.SaveChangesAsync(); + } + + public async Task RemoveAuthorizedNut(string nut, HttpContext context) + { + var _database = context.RequestServices.GetRequiredService(); + var isAuthorized = await _database.Nuts.Where(x => x.Authorized).AnyAsync(x => x.Nut == nut || x.FirstNut == nut); + if (isAuthorized) + { + var authorizedNut = await _database.Nuts.Where(x => x.Authorized).SingleAsync(x => x.Nut == nut || x.FirstNut == nut); + _database.Nuts.Remove(authorizedNut); + await _database.SaveChangesAsync(); + return true; + } + return false; + } + + public async Task GetNutIdk(string nut, HttpContext context) + { + var _database = context.RequestServices.GetRequiredService(); + var nutInfo = await _database.Nuts.FindAsync(nut); + return nutInfo.Idk; + } } } diff --git a/Examples/WithDatabase/Startup.cs b/Examples/WithDatabase/Startup.cs index 0a50fe4..1b42911 100644 --- a/Examples/WithDatabase/Startup.cs +++ b/Examples/WithDatabase/Startup.cs @@ -48,6 +48,10 @@ public void ConfigureServices(IServiceCollection services) options.GetUserVukAsync = new SqrlManager().GetUserVuk; options.GetUserSukAsync = new SqrlManager().GetUserSuk; options.GetUsernameAsync = new SqrlManager().GetUsername; + options.GetAndRemoveNutAsync = new SqrlManager().GetAndRemoveNut; + options.StoreNutAsync = new SqrlManager().StoreNut; + options.GetNutIdkAsync = new SqrlManager().GetNutIdk; + options.RemoveAuthorizedNutAsync = new SqrlManager().RemoveAuthorizedNut; options.Events.OnTicketReceived += OnTicketReceived; }); var connectionString = Configuration.GetConnectionString("DatabaseContext"); diff --git a/Examples/WithDatabase/WithDatabase.csproj b/Examples/WithDatabase/WithDatabase.csproj index 7c3c3f9..cc796f6 100644 --- a/Examples/WithDatabase/WithDatabase.csproj +++ b/Examples/WithDatabase/WithDatabase.csproj @@ -4,6 +4,15 @@ netcoreapp3.0 + + + + + + + + + diff --git a/SqrlForNet/Interfaces/AskMessageHooks.cs b/SqrlForNet/Interfaces/AskMessageHooks.cs index 88ec8af..51e65ce 100644 --- a/SqrlForNet/Interfaces/AskMessageHooks.cs +++ b/SqrlForNet/Interfaces/AskMessageHooks.cs @@ -3,14 +3,14 @@ namespace SqrlForNet.Interfaces { - public interface AskMessageHooks + public interface IAskMessageHooks { AskMessage GetAskQuestion(HttpRequest request, string nut); bool ProcessAskResponse(HttpRequest request, string nut, int button); } - public interface AskMessageHooksAsync + public interface IAskMessageHooksAsync { Task GetAskQuestion(HttpRequest request, string nut); diff --git a/SqrlForNet/Interfaces/CpsSessionManagementHooks.cs b/SqrlForNet/Interfaces/CpsSessionManagementHooks.cs index dd84146..d2583bc 100644 --- a/SqrlForNet/Interfaces/CpsSessionManagementHooks.cs +++ b/SqrlForNet/Interfaces/CpsSessionManagementHooks.cs @@ -2,7 +2,7 @@ namespace SqrlForNet.Interfaces { - public interface CpsSessionManagementHooks + public interface ICpsSessionManagementHooks { void StoreCpsSessionId(string code, string userId); @@ -12,7 +12,7 @@ public interface CpsSessionManagementHooks } - public interface CpsSessionManagementHooksAsync + public interface ICpsSessionManagementHooksAsync { Task StoreCpsSessionId(string code, string userId); diff --git a/SqrlForNet/Interfaces/INutManagementHooks.cs b/SqrlForNet/Interfaces/INutManagementHooks.cs index 7ae4a7e..5a5c643 100644 --- a/SqrlForNet/Interfaces/INutManagementHooks.cs +++ b/SqrlForNet/Interfaces/INutManagementHooks.cs @@ -1,32 +1,29 @@ using System.Threading.Tasks; +using Microsoft.AspNetCore.Http; namespace SqrlForNet.Interfaces { public interface INutManagementHooks { - NutInfo GetNut(string nut, bool authorized); + NutInfo GetAndRemoveNut(string nut, HttpContext context); - void StoreNut(string nut, NutInfo info, bool authorized); + void StoreNut(string nut, NutInfo info, bool authorized, HttpContext context); - void RemoveNut(string nut, bool authorized); + bool RemoveAuthorizedNut(string nut, HttpContext context); - bool CheckNutAuthorized(string nut); - - string GetNutIdk(string nut); + string GetNutIdk(string nut, HttpContext context); } public interface INutManagementHooksAsync { - Task GetNut(string nut, bool authorized); - - Task StoreNut(string nut, NutInfo info, bool authorized); + Task GetAndRemoveNut(string nut, HttpContext context); - Task RemoveNut(string nut, bool authorized); + Task StoreNut(string nut, NutInfo info, bool authorized, HttpContext context); - Task CheckNutAuthorized(string nut); + Task RemoveAuthorizedNut(string nut, HttpContext context); - Task GetNutIdk(string nut); + Task GetNutIdk(string nut, HttpContext context); } } \ No newline at end of file diff --git a/SqrlForNet/SqrlAuthenticationHandler.cs b/SqrlForNet/SqrlAuthenticationHandler.cs index 8af9fb9..9563749 100644 --- a/SqrlForNet/SqrlAuthenticationHandler.cs +++ b/SqrlForNet/SqrlAuthenticationHandler.cs @@ -125,7 +125,7 @@ private Task CheckRequest() if (result) { Logger.LogTrace("User is authorized and can be logged in"); - var userId = Options.GetNutIdkInternal(Request.Query["check"]); + var userId = Options.GetNutIdkInternal(Request.Query["check"], Context); var username = Options.GetUsernameInternal(userId, Context); var claims = new[] { new Claim(ClaimTypes.NameIdentifier, userId), @@ -147,7 +147,7 @@ private Task CheckRequest() private Task CheckCpsRequest() { - var result = Options.GetUserIdAndRemoveCpsSessionIdInternal(Request.Query["cps"]); + var result = Options.GetUserIdAndRemoveCpsSessionIdInternal(Request.Query["cps"], Context); if (!string.IsNullOrEmpty(result)) { var username = Options.GetUsernameInternal(result, Context); diff --git a/SqrlForNet/SqrlAuthenticationOptions.cs b/SqrlForNet/SqrlAuthenticationOptions.cs index bfe6eb2..9e8745f 100644 --- a/SqrlForNet/SqrlAuthenticationOptions.cs +++ b/SqrlForNet/SqrlAuthenticationOptions.cs @@ -168,23 +168,23 @@ internal void RemoveUserInternal(string idk, HttpContext context) } } - public Func GetAndRemoveNut; + public Func GetAndRemoveNut; - public Func> GetAndRemoveNutAsync; + public Func> GetAndRemoveNutAsync; private KeyValuePair _currentNutInfo; - internal NutInfo GetAndRemoveNutInternal(string nut) + internal NutInfo GetAndRemoveNutInternal(string nut, HttpContext context) { if (_currentNutInfo.Key != nut) { if (GetAndRemoveNut != null) { - _currentNutInfo = new KeyValuePair(nut, GetAndRemoveNut.Invoke(nut)); + _currentNutInfo = new KeyValuePair(nut, GetAndRemoveNut.Invoke(nut, context)); } else { - var task = GetAndRemoveNutAsync.Invoke(nut); + var task = GetAndRemoveNutAsync.Invoke(nut, context); task.Wait(); _currentNutInfo = new KeyValuePair(nut, task.Result); } @@ -193,87 +193,87 @@ internal NutInfo GetAndRemoveNutInternal(string nut) return _currentNutInfo.Value; } - public Action StoreNut; + public Action StoreNut; - public Func StoreNutAsync; + public Func StoreNutAsync; - internal void StoreNutInternal(string nut, NutInfo info, bool authorized) + internal void StoreNutInternal(string nut, NutInfo info, bool authorized, HttpContext context) { if (StoreNut != null) { - StoreNut.Invoke(nut, info, authorized); + StoreNut.Invoke(nut, info, authorized, context); } else { - StoreNutAsync.Invoke(nut, info, authorized).Wait(); + StoreNutAsync.Invoke(nut, info, authorized, context).Wait(); } } - public Func RemoveAuthorizedNut; + public Func RemoveAuthorizedNut; - public Func> RemoveAuthorizedNutAsync; + public Func> RemoveAuthorizedNutAsync; - internal bool RemoveAuthorizedNutInternal(string nut) + internal bool RemoveAuthorizedNutInternal(string nut, HttpContext context) { if (RemoveAuthorizedNut != null) { - return RemoveAuthorizedNut.Invoke(nut); + return RemoveAuthorizedNut.Invoke(nut, context); } else { - var task = RemoveAuthorizedNutAsync.Invoke(nut); + var task = RemoveAuthorizedNutAsync.Invoke(nut, context); task.Wait(); return task.Result; } } - public Func GetNutIdk; + public Func GetNutIdk; - public Func> GetNutIdkAsync; + public Func> GetNutIdkAsync; - internal string GetNutIdkInternal(string nut) + internal string GetNutIdkInternal(string nut, HttpContext context) { if (GetNutIdk != null) { - return GetNutIdk.Invoke(nut); + return GetNutIdk.Invoke(nut, context); } else { - var task = GetNutIdkAsync.Invoke(nut); + var task = GetNutIdkAsync.Invoke(nut, context); task.Wait(); return task.Result; } } - public Action StoreCpsSessionId; + public Action StoreCpsSessionId; - public Func StoreCpsSessionIdAsync; + public Func StoreCpsSessionIdAsync; - internal void StoreCpsSessionIdInternal(string code, string idk) + internal void StoreCpsSessionIdInternal(string code, string idk, HttpContext context) { if (StoreCpsSessionId != null) { - StoreCpsSessionId.Invoke(code, idk); + StoreCpsSessionId.Invoke(code, idk, context); } else { - StoreCpsSessionIdAsync.Invoke(code, idk).Wait(); + StoreCpsSessionIdAsync.Invoke(code, idk, context).Wait(); } } - public Func GetUserIdAndRemoveCpsSessionId; + public Func GetUserIdAndRemoveCpsSessionId; - public Func> GetUserIdAndRemoveCpsSessionIdAsync; + public Func> GetUserIdAndRemoveCpsSessionIdAsync; - internal string GetUserIdAndRemoveCpsSessionIdInternal(string code) + internal string GetUserIdAndRemoveCpsSessionIdInternal(string code, HttpContext context) { if (GetUserIdAndRemoveCpsSessionId != null) { - return GetUserIdAndRemoveCpsSessionId.Invoke(code); + return GetUserIdAndRemoveCpsSessionId.Invoke(code, context); } else { - var task = GetUserIdAndRemoveCpsSessionIdAsync.Invoke(code); + var task = GetUserIdAndRemoveCpsSessionIdAsync.Invoke(code, context); task.Wait(); return task.Result; } @@ -395,7 +395,7 @@ private void ClearOldNuts() } } - private NutInfo GetAndRemoveNutMethod(string nut) + private NutInfo GetAndRemoveNutMethod(string nut, HttpContext httpContext) { ClearOldNuts(); lock (NutList) @@ -410,7 +410,7 @@ private NutInfo GetAndRemoveNutMethod(string nut) return null; } - private void StoreNutMethod(string nut, NutInfo info, bool authorized) + private void StoreNutMethod(string nut, NutInfo info, bool authorized, HttpContext arg4) { ClearOldNuts(); if (authorized) @@ -429,7 +429,7 @@ private void StoreNutMethod(string nut, NutInfo info, bool authorized) } } - private bool RemoveAuthorizedNutMethod(string nut) + private bool RemoveAuthorizedNutMethod(string nut, HttpContext httpContext) { ClearOldNuts(); lock (AuthorizedNutList) @@ -444,7 +444,7 @@ private bool RemoveAuthorizedNutMethod(string nut) } } - private string GetNutIdkMethod(string nut) + private string GetNutIdkMethod(string nut, HttpContext httpContext) { ClearOldNuts(); lock (AuthorizedNutList) @@ -455,7 +455,7 @@ private string GetNutIdkMethod(string nut) private static readonly Dictionary CpsSessions = new Dictionary(); - private void StoreCpsSessionIdMethod(string sessionId, string userId) + private void StoreCpsSessionIdMethod(string sessionId, string userId, HttpContext context) { lock (CpsSessions) { @@ -463,7 +463,7 @@ private void StoreCpsSessionIdMethod(string sessionId, string userId) } } - private string GetUserIdAndRemoveCpsSessionIdMethod(string sessionId) + private string GetUserIdAndRemoveCpsSessionIdMethod(string sessionId, HttpContext context) { lock (CpsSessions) { diff --git a/SqrlForNet/SqrlCommandWorker.cs b/SqrlForNet/SqrlCommandWorker.cs index 45cf3cd..171746c 100644 --- a/SqrlForNet/SqrlCommandWorker.cs +++ b/SqrlForNet/SqrlCommandWorker.cs @@ -179,7 +179,7 @@ private NutValidationResult NutStatus() { _logger.LogTrace("Getting status of NUT"); var nut = Request.Query["nut"]; - var nutInfo = Options.GetAndRemoveNutInternal(nut); + var nutInfo = Options.GetAndRemoveNutInternal(nut, Request.HttpContext); if (nutInfo == null) { @@ -367,7 +367,7 @@ private bool AuthorizeNut(string nut) var opts = ParseOpts(); if (!opts[OptKey.cps]) { - var nutInfo = Options.GetAndRemoveNutInternal(nut); + var nutInfo = Options.GetAndRemoveNutInternal(nut, Request.HttpContext); var authNutInfo = new NutInfo { FirstNut = nutInfo.FirstNut, @@ -375,7 +375,7 @@ private bool AuthorizeNut(string nut) IpAddress = nutInfo.IpAddress, Idk = nutInfo.Idk }; - Options.StoreNutInternal(nut, authNutInfo, true); + Options.StoreNutInternal(nut, authNutInfo, true, Request.HttpContext); return true; } return false; @@ -746,7 +746,7 @@ public bool CheckPage() { var checkNut = Request.Query["check"]; - var isAuthorized = Options.RemoveAuthorizedNutInternal(checkNut); + var isAuthorized = Options.RemoveAuthorizedNutInternal(checkNut, Request.HttpContext); if (!isAuthorized) { var responseMessage = new StringBuilder(); @@ -816,7 +816,7 @@ private void StoreNut(string nut) _logger.LogTrace("Storing NUT"); _logger.LogDebug("The NUT been stored is: {0}", nut); - Options.StoreNutInternal(nut, NewNutInfo(), false); + Options.StoreNutInternal(nut, NewNutInfo(), false, Request.HttpContext); _logger.LogTrace("NUT stored"); } @@ -826,7 +826,7 @@ private NutInfo NewNutInfo() NutInfo currentNut = null; if (Request.Query.ContainsKey("nut")) { - currentNut = Options.GetAndRemoveNutInternal(Request.Query["nut"]); + currentNut = Options.GetAndRemoveNutInternal(Request.Query["nut"], Request.HttpContext); } return new NutInfo { @@ -914,7 +914,7 @@ private string GenerateNut(byte[] key) public string GenerateCpsCode() { var code = Guid.NewGuid().ToString("N"); - Options.StoreCpsSessionIdInternal(code, GetClientParams()["idk"]); + Options.StoreCpsSessionIdInternal(code, GetClientParams()["idk"], Request.HttpContext); return code; } From 80f17c3e969fbca16b798343ba5fdfd622762e16 Mon Sep 17 00:00:00 2001 From: Liam Raper Date: Thu, 17 Oct 2019 09:33:56 +0100 Subject: [PATCH 4/7] Changed some internal veriableds --- .../Chaos.NaCl/Internal/Ed25519Ref10/open.cs | 61 +++---------------- 1 file changed, 10 insertions(+), 51 deletions(-) diff --git a/SqrlForNet/Chaos.NaCl/Internal/Ed25519Ref10/open.cs b/SqrlForNet/Chaos.NaCl/Internal/Ed25519Ref10/open.cs index 01485d0..e1abfde 100644 --- a/SqrlForNet/Chaos.NaCl/Internal/Ed25519Ref10/open.cs +++ b/SqrlForNet/Chaos.NaCl/Internal/Ed25519Ref10/open.cs @@ -4,74 +4,33 @@ namespace SqrlForNet.Chaos.NaCl.Internal.Ed25519Ref10 { internal static partial class Ed25519Operations { - // Original crypto_sign_open, for reference only - /*public static int crypto_sign_open( - byte[] m, out int mlen, - byte[] sm, int smlen, - byte[] pk) - { - byte[] h = new byte[64]; - byte[] checkr = new byte[32]; - GroupElementP3 A; - GroupElementP2 R; - int i; - - mlen = -1; - if (smlen < 64) return -1; - if ((sm[63] & 224) != 0) return -1; - if (GroupOperations.ge_frombytes_negate_vartime(out A, pk, 0) != 0) return -1; - - for (i = 0; i < smlen; ++i) m[i] = sm[i]; - for (i = 0; i < 32; ++i) m[32 + i] = pk[i]; - Sha512BclWrapper.crypto_hash_sha512(h, m, 0, smlen); - ScalarOperations.sc_reduce(h); - - var sm32 = new byte[32]; - Array.Copy(sm, 32, sm32, 0, 32); - GroupOperations.ge_double_scalarmult_vartime(out R, h, ref A, sm32); - GroupOperations.ge_tobytes(checkr, 0, ref R); - if (Helpers.crypto_verify_32(checkr, sm) != 0) - { - for (i = 0; i < smlen; ++i) - m[i] = 0; - return -1; - } - - for (i = 0; i < smlen - 64; ++i) - m[i] = sm[64 + i]; - for (i = smlen - 64; i < smlen; ++i) - m[i] = 0; - mlen = smlen - 64; - return 0; - }*/ - public static bool crypto_sign_verify( - byte[] sig, int sigoffset, - byte[] m, int moffset, int mlen, - byte[] pk, int pkoffset) + byte[] signature, int signatureOffset, + byte[] message, int messageOffset, int messageLength, + byte[] publicKey, int publicKeyOffset) { byte[] h; byte[] checkr = new byte[32]; GroupElementP3 A; GroupElementP2 R; - if ((sig[sigoffset + 63] & 224) != 0) return false; - if (GroupOperations.ge_frombytes_negate_vartime(out A, pk, pkoffset) != 0) + if ((signature[signatureOffset + 63] & 224) != 0) return false; + if (GroupOperations.ge_frombytes_negate_vartime(out A, publicKey, publicKeyOffset) != 0) return false; var hasher = new Sha512(); - hasher.Update(sig, sigoffset, 32); - hasher.Update(pk, pkoffset, 32); - hasher.Update(m, moffset, mlen); + hasher.Update(signature, signatureOffset, 32); + hasher.Update(publicKey, publicKeyOffset, 32); + hasher.Update(message, messageOffset, messageLength); h = hasher.FinalizeHash(); ScalarOperations.sc_reduce(h); var sm32 = new byte[32];//todo: remove allocation - Array.Copy(sig, sigoffset + 32, sm32, 0, 32); + Array.Copy(signature, signatureOffset + 32, sm32, 0, 32); GroupOperations.ge_double_scalarmult_vartime(out R, h, ref A, sm32); GroupOperations.ge_tobytes(checkr, 0, ref R); - var result = CryptoBytes.ConstantTimeEquals(checkr, 0, sig, sigoffset, 32); + var result = CryptoBytes.ConstantTimeEquals(checkr, 0, signature, signatureOffset, 32); CryptoBytes.Wipe(h); CryptoBytes.Wipe(checkr); return result; From 609e589466560fe38d1abb5a1ad08954f919ee67 Mon Sep 17 00:00:00 2001 From: Doug Ellner Date: Thu, 17 Oct 2019 14:46:18 -0700 Subject: [PATCH 5/7] Fix for 500 Error if opt is not specified by client --- SqrlForNet/SqrlCommandWorker.cs | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-) diff --git a/SqrlForNet/SqrlCommandWorker.cs b/SqrlForNet/SqrlCommandWorker.cs index cb40627..5426c63 100644 --- a/SqrlForNet/SqrlCommandWorker.cs +++ b/SqrlForNet/SqrlCommandWorker.cs @@ -889,7 +889,17 @@ private Dictionary ParseOpts() { if (_optionsCache == null) { - var options = GetClientParams()["opt"].Split('~'); + var clientParams = GetClientParams(); + string[] options; + if (clientParams.ContainsKey("opt")) + { + options = clientParams["opt"].Split('~'); + } + else + { + options = new string[0]; + } + _optionsCache = Enum.GetNames(typeof(OptKey)) .ToDictionary( supportedOption => @@ -921,11 +931,11 @@ public string GenerateCpsCode() private void NoneQueryOptionHandling() { - if (GetClientParams().ContainsKey("opt") && ParseOpts()[OptKey.sqrlonly] && (Options.SqrlOnlyReceived != null || Options.SqrlOnlyReceivedAsync != null)) + if (ParseOpts()[OptKey.sqrlonly] && (Options.SqrlOnlyReceived != null || Options.SqrlOnlyReceivedAsync != null)) { Options.SqrlOnlyReceivedInternal(GetClientParams()["idk"], Request.HttpContext); } - if (GetClientParams().ContainsKey("opt") && ParseOpts()[OptKey.hardlock] && (Options.HardlockReceived != null || Options.HardlockReceivedAsync != null)) + if (ParseOpts()[OptKey.hardlock] && (Options.HardlockReceived != null || Options.HardlockReceivedAsync != null)) { Options.HardlockReceivedInternal(GetClientParams()["idk"], Request.HttpContext); } From 360a3e087143af464820a42689f16e502aefa7c1 Mon Sep 17 00:00:00 2001 From: Liam Raper Date: Fri, 18 Oct 2019 09:33:48 +0100 Subject: [PATCH 6/7] Added default for role --- Examples/WithDatabase/Database/User.cs | 5 +---- Examples/WithDatabase/SqrlManager.cs | 1 + Examples/WithDatabase/WithDatabase.csproj | 2 ++ 3 files changed, 4 insertions(+), 4 deletions(-) diff --git a/Examples/WithDatabase/Database/User.cs b/Examples/WithDatabase/Database/User.cs index 3c4bd8e..3a4ff2a 100644 --- a/Examples/WithDatabase/Database/User.cs +++ b/Examples/WithDatabase/Database/User.cs @@ -1,7 +1,4 @@ -using System; -using System.Collections.Generic; -using System.Linq; -using System.Threading.Tasks; +using System.ComponentModel; namespace WithDatabase.Database { diff --git a/Examples/WithDatabase/SqrlManager.cs b/Examples/WithDatabase/SqrlManager.cs index 40faf58..f262a6c 100644 --- a/Examples/WithDatabase/SqrlManager.cs +++ b/Examples/WithDatabase/SqrlManager.cs @@ -77,6 +77,7 @@ public async Task CreateUser(string userId, string suk, string vuk, HttpContext _database.User.Add(new User() { Username = "New user", + Role = "User", SqrlUser = new SqrlUser() { UserId = userId, diff --git a/Examples/WithDatabase/WithDatabase.csproj b/Examples/WithDatabase/WithDatabase.csproj index cc796f6..0dad98f 100644 --- a/Examples/WithDatabase/WithDatabase.csproj +++ b/Examples/WithDatabase/WithDatabase.csproj @@ -11,6 +11,8 @@ + + From 68315f6dd0c09c842ce70922166b9878ac8d0902 Mon Sep 17 00:00:00 2001 From: Liam Raper Date: Fri, 18 Oct 2019 09:36:44 +0100 Subject: [PATCH 7/7] A better way to do default hooks --- SqrlForNet/SqrlAuthenticationOptions.cs | 73 ++++++++++--------------- 1 file changed, 30 insertions(+), 43 deletions(-) diff --git a/SqrlForNet/SqrlAuthenticationOptions.cs b/SqrlForNet/SqrlAuthenticationOptions.cs index 9e8745f..f930fb5 100644 --- a/SqrlForNet/SqrlAuthenticationOptions.cs +++ b/SqrlForNet/SqrlAuthenticationOptions.cs @@ -182,12 +182,16 @@ internal NutInfo GetAndRemoveNutInternal(string nut, HttpContext context) { _currentNutInfo = new KeyValuePair(nut, GetAndRemoveNut.Invoke(nut, context)); } - else + else if (GetAndRemoveNutAsync != null) { var task = GetAndRemoveNutAsync.Invoke(nut, context); task.Wait(); _currentNutInfo = new KeyValuePair(nut, task.Result); } + else + { + _currentNutInfo = new KeyValuePair(nut, GetAndRemoveNutMethod(nut, context)); + } } return _currentNutInfo.Value; @@ -203,10 +207,14 @@ internal void StoreNutInternal(string nut, NutInfo info, bool authorized, HttpCo { StoreNut.Invoke(nut, info, authorized, context); } - else + else if (StoreNutAsync != null) { StoreNutAsync.Invoke(nut, info, authorized, context).Wait(); } + else + { + StoreNutMethod(nut, info, authorized, context); + } } public Func RemoveAuthorizedNut; @@ -219,12 +227,16 @@ internal bool RemoveAuthorizedNutInternal(string nut, HttpContext context) { return RemoveAuthorizedNut.Invoke(nut, context); } - else + else if (RemoveAuthorizedNutAsync != null) { var task = RemoveAuthorizedNutAsync.Invoke(nut, context); task.Wait(); return task.Result; } + else + { + return RemoveAuthorizedNutMethod(nut, context); + } } public Func GetNutIdk; @@ -237,12 +249,16 @@ internal string GetNutIdkInternal(string nut, HttpContext context) { return GetNutIdk.Invoke(nut, context); } - else + else if (GetNutIdkAsync != null) { var task = GetNutIdkAsync.Invoke(nut, context); task.Wait(); return task.Result; } + else + { + return GetNutIdkMethod(nut, context); + } } public Action StoreCpsSessionId; @@ -255,10 +271,14 @@ internal void StoreCpsSessionIdInternal(string code, string idk, HttpContext con { StoreCpsSessionId.Invoke(code, idk, context); } - else + else if (StoreCpsSessionIdAsync != null) { StoreCpsSessionIdAsync.Invoke(code, idk, context).Wait(); } + else + { + StoreCpsSessionIdMethod(code, idk, context); + } } public Func GetUserIdAndRemoveCpsSessionId; @@ -271,12 +291,16 @@ internal string GetUserIdAndRemoveCpsSessionIdInternal(string code, HttpContext { return GetUserIdAndRemoveCpsSessionId.Invoke(code, context); } - else + else if (GetUserIdAndRemoveCpsSessionIdAsync != null) { var task = GetUserIdAndRemoveCpsSessionIdAsync.Invoke(code, context); task.Wait(); return task.Result; } + else + { + return GetUserIdAndRemoveCpsSessionIdMethod(code, context); + } } public Action SqrlOnlyReceived; @@ -489,13 +513,6 @@ public SqrlAuthenticationOptions() Events = new RemoteAuthenticationEvents(); - GetAndRemoveNut = GetAndRemoveNutMethod; - StoreNut = StoreNutMethod; - RemoveAuthorizedNut = RemoveAuthorizedNutMethod; - GetNutIdk = GetNutIdkMethod; - - StoreCpsSessionId = StoreCpsSessionIdMethod; - GetUserIdAndRemoveCpsSessionId = GetUserIdAndRemoveCpsSessionIdMethod; } public override void Validate() @@ -627,36 +644,6 @@ public override void Validate() throw new ArgumentException($"{nameof(RemoveUser)} and {nameof(RemoveUserAsync)} are both defined you should only define one of them."); } - if (GetAndRemoveNut != null && GetAndRemoveNutAsync != null) - { - throw new ArgumentException($"{nameof(GetAndRemoveNut)} and {nameof(GetAndRemoveNutAsync)} are both defined you should only define one of them."); - } - - if (StoreNut != null && StoreNutAsync != null) - { - throw new ArgumentException($"{nameof(StoreNut)} and {nameof(StoreNutAsync)} are both defined you should only define one of them."); - } - - if (RemoveAuthorizedNut != null && RemoveAuthorizedNutAsync != null) - { - throw new ArgumentException($"{nameof(RemoveAuthorizedNut)} and {nameof(RemoveAuthorizedNut)} are both defined you should only define one of them."); - } - - if (GetNutIdk != null && GetNutIdkAsync != null) - { - throw new ArgumentException($"{nameof(GetNutIdk)} and {nameof(GetNutIdkAsync)} are both defined you should only define one of them."); - } - - if (StoreCpsSessionId != null && StoreCpsSessionIdAsync != null) - { - throw new ArgumentException($"{nameof(StoreCpsSessionId)} and {nameof(StoreCpsSessionIdAsync)} are both defined you should only define one of them."); - } - - if (GetUserIdAndRemoveCpsSessionId != null && GetUserIdAndRemoveCpsSessionIdAsync != null) - { - throw new ArgumentException($"{nameof(GetUserIdAndRemoveCpsSessionId)} and {nameof(GetUserIdAndRemoveCpsSessionIdAsync)} are both defined you should only define one of them."); - } - if (SqrlOnlyReceived != null && SqrlOnlyReceivedAsync != null) { throw new ArgumentException($"{nameof(SqrlOnlyReceived)} and {nameof(SqrlOnlyReceivedAsync)} are both defined you should only define one of them.");