1
0
mirror of https://github.com/chylex/Minecraft-Phantom-Panel.git synced 2024-10-17 12:42:51 +02:00
Minecraft-Phantom-Panel/Server/Phantom.Server.Web.Identity/Authentication/PhantomLoginStore.cs

64 lines
2.0 KiB
C#

using System.Collections.Concurrent;
using System.Diagnostics;
using Microsoft.AspNetCore.Identity;
using Phantom.Common.Logging;
using Phantom.Utils.Runtime;
using ILogger = Serilog.ILogger;
namespace Phantom.Server.Web.Identity.Authentication;
public sealed class PhantomLoginStore {
private static readonly ILogger Logger = PhantomLogger.Create<PhantomLoginStore>();
private static readonly TimeSpan ExpirationTime = TimeSpan.FromMinutes(1);
internal static Func<IServiceProvider, PhantomLoginStore> Create(CancellationToken cancellationToken) {
return provider => new PhantomLoginStore(provider.GetRequiredService<TaskManager>(), cancellationToken);
}
private readonly ConcurrentDictionary<string, LoginEntry> loginEntries = new ();
private readonly CancellationToken cancellationToken;
private PhantomLoginStore(TaskManager taskManager, CancellationToken cancellationToken) {
this.cancellationToken = cancellationToken;
taskManager.Run("Web login entry expiration loop", RunExpirationLoop);
}
private async Task RunExpirationLoop() {
try {
while (true) {
await Task.Delay(ExpirationTime, cancellationToken);
foreach (var (token, entry) in loginEntries) {
if (entry.IsExpired) {
Logger.Debug("Expired login entry for {Username}.", entry.User.UserName);
loginEntries.TryRemove(token, out _);
}
}
}
} finally {
Logger.Information("Expiration loop stopped.");
}
}
internal void Add(string token, IdentityUser user, string password, string returnUrl) {
loginEntries[token] = new LoginEntry(user, password, returnUrl, Stopwatch.StartNew());
}
internal LoginEntry? Pop(string token) {
if (!loginEntries.TryRemove(token, out var entry)) {
return null;
}
if (entry.IsExpired) {
Logger.Debug("Expired login entry for {Username}.", entry.User.UserName);
return null;
}
return entry;
}
internal sealed record LoginEntry(IdentityUser User, string Password, string ReturnUrl, Stopwatch AddedTime) {
public bool IsExpired => AddedTime.Elapsed >= ExpirationTime;
}
}