2026-01-08 14:14:42 +00:00
|
|
|
namespace Domain.Entities;
|
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
|
|
/// Represents a system user for authentication and authorization.
|
|
|
|
|
/// </summary>
|
|
|
|
|
public class User
|
|
|
|
|
{
|
|
|
|
|
public int Id { get; private set; }
|
|
|
|
|
public string Username { get; private set; } = string.Empty;
|
|
|
|
|
public string PasswordHash { get; private set; } = string.Empty;
|
2026-01-08 15:49:32 +00:00
|
|
|
public string RecoveryCodeHash { get; private set; } = string.Empty;
|
2026-01-08 14:14:42 +00:00
|
|
|
public string Role { get; private set; } = UserRoles.Student;
|
|
|
|
|
public int? StudentId { get; private set; }
|
|
|
|
|
public DateTime CreatedAt { get; private set; }
|
|
|
|
|
public DateTime? LastLoginAt { get; private set; }
|
|
|
|
|
|
|
|
|
|
// Navigation property
|
|
|
|
|
public Student? Student { get; private set; }
|
|
|
|
|
|
|
|
|
|
private User() { }
|
|
|
|
|
|
2026-01-08 15:49:32 +00:00
|
|
|
public static User Create(string username, string passwordHash, string recoveryCodeHash, string role, int? studentId = null)
|
2026-01-08 14:14:42 +00:00
|
|
|
{
|
|
|
|
|
if (string.IsNullOrWhiteSpace(username))
|
|
|
|
|
throw new ArgumentException("Username cannot be empty", nameof(username));
|
|
|
|
|
|
|
|
|
|
if (string.IsNullOrWhiteSpace(passwordHash))
|
|
|
|
|
throw new ArgumentException("Password hash cannot be empty", nameof(passwordHash));
|
|
|
|
|
|
|
|
|
|
if (!UserRoles.IsValid(role))
|
|
|
|
|
throw new ArgumentException($"Invalid role: {role}", nameof(role));
|
|
|
|
|
|
|
|
|
|
return new User
|
|
|
|
|
{
|
|
|
|
|
Username = username.ToLowerInvariant(),
|
|
|
|
|
PasswordHash = passwordHash,
|
2026-01-08 15:49:32 +00:00
|
|
|
RecoveryCodeHash = recoveryCodeHash,
|
2026-01-08 14:14:42 +00:00
|
|
|
Role = role,
|
|
|
|
|
StudentId = studentId,
|
|
|
|
|
CreatedAt = DateTime.UtcNow
|
|
|
|
|
};
|
|
|
|
|
}
|
|
|
|
|
|
2026-01-08 15:49:32 +00:00
|
|
|
public void UpdatePassword(string newPasswordHash)
|
|
|
|
|
{
|
|
|
|
|
if (string.IsNullOrWhiteSpace(newPasswordHash))
|
|
|
|
|
throw new ArgumentException("Password hash cannot be empty", nameof(newPasswordHash));
|
|
|
|
|
PasswordHash = newPasswordHash;
|
|
|
|
|
}
|
|
|
|
|
|
2026-01-08 14:14:42 +00:00
|
|
|
public void UpdateLastLogin()
|
|
|
|
|
{
|
|
|
|
|
LastLoginAt = DateTime.UtcNow;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
public bool IsAdmin => Role == UserRoles.Admin;
|
|
|
|
|
public bool IsStudent => Role == UserRoles.Student;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
/// <summary>
|
|
|
|
|
/// Constants for user roles.
|
|
|
|
|
/// </summary>
|
|
|
|
|
public static class UserRoles
|
|
|
|
|
{
|
|
|
|
|
public const string Admin = "Admin";
|
|
|
|
|
public const string Student = "Student";
|
|
|
|
|
|
|
|
|
|
public static bool IsValid(string role) =>
|
|
|
|
|
role == Admin || role == Student;
|
|
|
|
|
}
|