using System;
using System.Security.Cryptography;
using System.Text;
namespace ChronoFlow.Security
{
///
/// Diese Klasse bietet Funktionen zum sicheren Hashen und Überprüfen von Passwörtern.
///
public static class PasswordHasher
{
///
/// Erstellt einen sicheren Hash aus einem Passwort unter Verwendung von PBKDF2.
///
/// Das Klartextpasswort
/// Ein kombinierter Hash-String (Salt + Hash)
public static string HashPassword(string password)
{
using var rng = RandomNumberGenerator.Create();
byte[] salt = new byte[16];
rng.GetBytes(salt);
var pbkdf2 = new Rfc2898DeriveBytes(password, salt, 100_000, HashAlgorithmName.SHA256);
byte[] hash = pbkdf2.GetBytes(32);
// Kombiniere Salt + Hash in einen String (Base64-encodiert)
byte[] hashBytes = new byte[48];
Array.Copy(salt, 0, hashBytes, 0, 16);
Array.Copy(hash, 0, hashBytes, 16, 32);
return Convert.ToBase64String(hashBytes);
}
///
/// Überprüft, ob ein Passwort zu einem gegebenen Hash passt.
///
/// Das eingegebene Klartextpasswort
/// Der gespeicherte kombinierte Hash (Base64, Salt + Hash)
/// True, wenn das Passwort stimmt, sonst false
public static bool VerifyPassword(string password, string storedHash)
{
try
{
byte[] hashBytes = Convert.FromBase64String(storedHash);
byte[] salt = new byte[16];
Array.Copy(hashBytes, 0, salt, 0, 16);
var pbkdf2 = new Rfc2898DeriveBytes(password, salt, 100_000, HashAlgorithmName.SHA256);
byte[] hash = pbkdf2.GetBytes(32);
for (int i = 0; i < 32; i++)
{
if (hashBytes[i + 16] != hash[i])
return false;
}
return true;
}
catch
{
// Falls der gespeicherte Hash beschädigt oder kein Base64 ist
return false;
}
}
}
}