You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
99 lines
2.8 KiB
99 lines
2.8 KiB
using System.IO;
|
|
using System.Text.Json;
|
|
|
|
namespace Housing.Services;
|
|
|
|
public sealed class LoginHistoryStore
|
|
{
|
|
private const int MaxHistoryCount = 3;
|
|
private readonly string _filePath;
|
|
private readonly LoginHistoryData _data;
|
|
|
|
private LoginHistoryStore(string filePath, LoginHistoryData data)
|
|
{
|
|
_filePath = filePath;
|
|
_data = data;
|
|
}
|
|
|
|
public static LoginHistoryStore Load(string filePath)
|
|
{
|
|
try
|
|
{
|
|
if (!File.Exists(filePath))
|
|
{
|
|
return new LoginHistoryStore(filePath, new LoginHistoryData());
|
|
}
|
|
|
|
var json = File.ReadAllText(filePath);
|
|
var data = JsonSerializer.Deserialize<LoginHistoryData>(json) ?? new LoginHistoryData();
|
|
data.Fields ??= new Dictionary<string, List<string>>();
|
|
return new LoginHistoryStore(filePath, data);
|
|
}
|
|
catch
|
|
{
|
|
return new LoginHistoryStore(filePath, new LoginHistoryData());
|
|
}
|
|
}
|
|
|
|
public IReadOnlyList<string> GetValues(string fieldName)
|
|
{
|
|
return _data.Fields.TryGetValue(fieldName, out var values)
|
|
? values.Where(value => !string.IsNullOrWhiteSpace(value)).Take(MaxHistoryCount).ToArray()
|
|
: Array.Empty<string>();
|
|
}
|
|
|
|
public void Remember(string fieldName, string value)
|
|
{
|
|
if (string.IsNullOrWhiteSpace(value))
|
|
{
|
|
return;
|
|
}
|
|
|
|
if (!_data.Fields.TryGetValue(fieldName, out var values))
|
|
{
|
|
values = new List<string>();
|
|
_data.Fields[fieldName] = values;
|
|
}
|
|
|
|
values.RemoveAll(item => string.Equals(item, value, StringComparison.OrdinalIgnoreCase));
|
|
values.Insert(0, value);
|
|
if (values.Count > MaxHistoryCount)
|
|
{
|
|
values.RemoveRange(MaxHistoryCount, values.Count - MaxHistoryCount);
|
|
}
|
|
}
|
|
|
|
public bool Forget(string fieldName, string value)
|
|
{
|
|
if (string.IsNullOrWhiteSpace(value) ||
|
|
!_data.Fields.TryGetValue(fieldName, out var values))
|
|
{
|
|
return false;
|
|
}
|
|
|
|
var removedCount = values.RemoveAll(item => string.Equals(item, value, StringComparison.OrdinalIgnoreCase));
|
|
if (values.Count == 0)
|
|
{
|
|
_data.Fields.Remove(fieldName);
|
|
}
|
|
|
|
return removedCount > 0;
|
|
}
|
|
|
|
public void Save()
|
|
{
|
|
var directory = Path.GetDirectoryName(_filePath);
|
|
if (!string.IsNullOrWhiteSpace(directory))
|
|
{
|
|
Directory.CreateDirectory(directory);
|
|
}
|
|
|
|
var json = JsonSerializer.Serialize(_data, new JsonSerializerOptions { WriteIndented = true });
|
|
File.WriteAllText(_filePath, json);
|
|
}
|
|
|
|
private sealed class LoginHistoryData
|
|
{
|
|
public Dictionary<string, List<string>> Fields { get; set; } = new(StringComparer.OrdinalIgnoreCase);
|
|
}
|
|
}
|
|
|