Migrate from User to Account domain concept
Renames core domain entities and services from "User" to "Account" Refactors project-wide namespaces, classes, and database tables to use "Account" terminology Updates related components, services, and database schema to reflect new domain naming Standardizes naming conventions across authentication and organization setup features
This commit is contained in:
parent
e5e7c1c19f
commit
88812177a9
29 changed files with 288 additions and 298 deletions
|
|
@ -1,4 +1,4 @@
|
|||
using LightBDD.Framework;
|
||||
using LightBDD.Framework;
|
||||
using LightBDD.Framework.Scenarios;
|
||||
using LightBDD.MsTest3;
|
||||
using PlanTempus.X.Services;
|
||||
|
|
@ -9,29 +9,29 @@ namespace PlanTempus.X.BDD.FeatureFixtures;
|
|||
[FeatureDescription(@"As a new user
|
||||
I want to register with my email
|
||||
So I can start using the system")]
|
||||
public partial class UserRegistrationSpecs : FeatureFixture
|
||||
public partial class AccountRegistrationSpecs : FeatureFixture
|
||||
{
|
||||
protected User _currentUser;
|
||||
protected Account _currentAccount;
|
||||
protected string _currentEmail;
|
||||
protected Exception _registrationError;
|
||||
|
||||
IUserService _userService;
|
||||
IAccountService _accountService;
|
||||
IEmailService _emailService;
|
||||
IOrganizationService _organizationService;
|
||||
|
||||
public async Task Given_no_user_exists_with_email(string email)
|
||||
public async Task Given_no_account_exists_with_email(string email)
|
||||
{
|
||||
// Ensure user doesn't exist with email
|
||||
var user = await _userService.GetUserByEmailAsync(email);
|
||||
user.ShouldBeNull();
|
||||
// Ensure account doesn't exist with email
|
||||
var account = await _accountService.GetAccountByEmailAsync(email);
|
||||
account.ShouldBeNull();
|
||||
_currentEmail = email;
|
||||
}
|
||||
|
||||
public async Task When_I_submit_registration_with_name_and_email(string name, string email)
|
||||
public async Task When_I_submit_registration_with_email_and_password(string email, string password)
|
||||
{
|
||||
try
|
||||
{
|
||||
_currentUser = await _userService.CreateUserAsync(email, name);
|
||||
_currentAccount = await _accountService.CreateAccountAsync(email, password);
|
||||
_currentEmail = email;
|
||||
}
|
||||
catch (Exception ex)
|
||||
|
|
@ -44,7 +44,7 @@ public partial class UserRegistrationSpecs : FeatureFixture
|
|||
{
|
||||
try
|
||||
{
|
||||
_currentUser = await _userService.CreateUserAsync(email, "Test User");
|
||||
_currentAccount = await _accountService.CreateAccountAsync(email, "TestPassword123!");
|
||||
_currentEmail = email;
|
||||
}
|
||||
catch (Exception ex)
|
||||
|
|
@ -53,14 +53,13 @@ public partial class UserRegistrationSpecs : FeatureFixture
|
|||
}
|
||||
}
|
||||
|
||||
public async Task Then_a_new_user_should_be_created_with_email_and_confirmation_status(string email, bool confirmationStatus)
|
||||
public async Task Then_a_new_account_should_be_created_with_email_and_confirmation_status(string email, bool confirmationStatus)
|
||||
{
|
||||
_currentUser.ShouldNotBeNull();
|
||||
_currentUser.Email.ShouldBe(email);
|
||||
_currentUser.EmailConfirmed.ShouldBe(confirmationStatus);
|
||||
_currentAccount.ShouldNotBeNull();
|
||||
_currentAccount.Email.ShouldBe(email);
|
||||
_currentAccount.EmailConfirmed.ShouldBe(confirmationStatus);
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
|
||||
public async Task Then_a_confirmation_email_should_be_sent()
|
||||
|
|
@ -69,18 +68,16 @@ public partial class UserRegistrationSpecs : FeatureFixture
|
|||
emailSent.ShouldBeTrue();
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
|
||||
public async Task Given_a_user_already_exists_with_email(string email)
|
||||
public async Task Given_an_account_already_exists_with_email(string email)
|
||||
{
|
||||
// Create a user first to ensure it exists
|
||||
_currentUser = await _userService.CreateUserAsync(email, "Existing User");
|
||||
_currentUser.ShouldNotBeNull();
|
||||
// Create an account first to ensure it exists
|
||||
_currentAccount = await _accountService.CreateAccountAsync(email, "ExistingPassword123!");
|
||||
_currentAccount.ShouldNotBeNull();
|
||||
_currentEmail = email;
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
|
||||
public async Task Then_registration_should_fail_with_error(string expectedErrorMessage)
|
||||
|
|
@ -89,6 +86,5 @@ public partial class UserRegistrationSpecs : FeatureFixture
|
|||
_registrationError.Message.ShouldBe(expectedErrorMessage);
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
}
|
||||
|
|
@ -5,28 +5,29 @@ using PlanTempus.X.Services;
|
|||
using Shouldly;
|
||||
|
||||
namespace PlanTempus.X.BDD.FeatureFixtures;
|
||||
[TestClass]
|
||||
[FeatureDescription(@"As a system administrator
|
||||
I want to ensure account security is maintained
|
||||
So users' data remains protected")]
|
||||
|
||||
[TestClass]
|
||||
[FeatureDescription(@"As a system administrator
|
||||
I want to ensure account security is maintained
|
||||
So users' data remains protected")]
|
||||
public partial class AccountSecuritySpecs : FeatureFixture
|
||||
{
|
||||
IUserService _userService;
|
||||
IAccountService _accountService;
|
||||
IEmailService _emailService;
|
||||
IOrganizationService _organizationService;
|
||||
IAuthService _authService;
|
||||
|
||||
protected User _currentUser;
|
||||
protected Account _currentAccount;
|
||||
protected DateTime? _lockoutEnd;
|
||||
protected bool _isLocked;
|
||||
protected bool _loginSuccessful;
|
||||
|
||||
public async Task Given_user_exists(string email)
|
||||
public async Task Given_account_exists(string email)
|
||||
{
|
||||
_currentUser = await _userService.GetUserByEmailAsync(email);
|
||||
if (_currentUser == null)
|
||||
_currentAccount = await _accountService.GetAccountByEmailAsync(email);
|
||||
if (_currentAccount == null)
|
||||
{
|
||||
_currentUser = await _userService.CreateUserAsync(email, "Test User");
|
||||
_currentAccount = await _accountService.CreateAccountAsync(email, "TestPassword123!");
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -36,7 +37,7 @@ public partial class AccountSecuritySpecs : FeatureFixture
|
|||
{
|
||||
try
|
||||
{
|
||||
await _authService.AttemptLoginAsync(_currentUser.Email, "WrongPassword");
|
||||
await _authService.AttemptLoginAsync(_currentAccount.Email, "WrongPassword");
|
||||
}
|
||||
catch
|
||||
{
|
||||
|
|
@ -47,29 +48,27 @@ public partial class AccountSecuritySpecs : FeatureFixture
|
|||
|
||||
public async Task Then_the_account_should_be_locked()
|
||||
{
|
||||
_currentUser = _userService.GetUserByEmail(_currentUser.Email);
|
||||
_isLocked = _currentUser.IsLocked;
|
||||
_currentAccount = _accountService.GetAccountByEmail(_currentAccount.Email);
|
||||
_isLocked = _currentAccount.IsLocked;
|
||||
_isLocked.ShouldBeTrue();
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
|
||||
public async Task And_lockout_end_should_be_set()
|
||||
{
|
||||
_lockoutEnd = _currentUser.LockoutEnd;
|
||||
_lockoutEnd = _currentAccount.LockoutEnd;
|
||||
_lockoutEnd.ShouldNotBeNull();
|
||||
_lockoutEnd.Value.ShouldBeGreaterThan(DateTime.UtcNow);
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
|
||||
public async Task And_subsequent_login_attempts_should_fail_until_lockout_end()
|
||||
{
|
||||
try
|
||||
{
|
||||
_loginSuccessful = await _authService.AttemptLoginAsync(_currentUser.Email, _currentUser.Password);
|
||||
_loginSuccessful = await _authService.AttemptLoginAsync(_currentAccount.Email, _currentAccount.Password);
|
||||
}
|
||||
catch
|
||||
{
|
||||
|
|
@ -78,4 +77,4 @@ public partial class AccountSecuritySpecs : FeatureFixture
|
|||
|
||||
_loginSuccessful.ShouldBeFalse();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -5,40 +5,41 @@ using PlanTempus.X.Services;
|
|||
using Shouldly;
|
||||
|
||||
namespace PlanTempus.X.BDD.FeatureFixtures;
|
||||
[TestClass]
|
||||
|
||||
[TestClass]
|
||||
[FeatureDescription(@"As a registered user
|
||||
I want to confirm my email
|
||||
So I can activate my account")]
|
||||
public partial class EmailConfirmationSpecs : FeatureFixture
|
||||
{
|
||||
IUserService _userService;
|
||||
IAccountService _accountService;
|
||||
IEmailService _emailService;
|
||||
IOrganizationService _organizationService;
|
||||
|
||||
protected User _currentUser;
|
||||
protected Account _currentAccount;
|
||||
protected string _currentEmail;
|
||||
protected string _confirmationLink;
|
||||
protected bool _redirectedToWelcome;
|
||||
protected string _errorMessage;
|
||||
|
||||
public async Task Given_a_user_exists_with_unconfirmed_email(string email)
|
||||
public async Task Given_an_account_exists_with_unconfirmed_email(string email)
|
||||
{
|
||||
_currentUser = await _userService.CreateUserAsync(email, "Test User");
|
||||
_currentUser.EmailConfirmed.ShouldBeFalse();
|
||||
_currentAccount = await _accountService.CreateAccountAsync(email, "TestPassword123!");
|
||||
_currentAccount.EmailConfirmed.ShouldBeFalse();
|
||||
_currentEmail = email;
|
||||
}
|
||||
|
||||
public async Task When_I_click_the_valid_confirmation_link_for(string email)
|
||||
{
|
||||
_confirmationLink = await _emailService.GetConfirmationLinkForEmail(email);
|
||||
await _userService.ConfirmEmailAsync(_confirmationLink);
|
||||
await _accountService.ConfirmEmailAsync(_confirmationLink);
|
||||
_redirectedToWelcome = true; // Simulate redirect
|
||||
}
|
||||
|
||||
public async Task Then_the_users_email_confirmed_should_be_true()
|
||||
public async Task Then_the_accounts_email_confirmed_should_be_true()
|
||||
{
|
||||
_currentUser = _userService.GetUserByEmail(_currentEmail);
|
||||
_currentUser.EmailConfirmed.ShouldBeTrue();
|
||||
_currentAccount = _accountService.GetAccountByEmail(_currentEmail);
|
||||
_currentAccount.EmailConfirmed.ShouldBeTrue();
|
||||
}
|
||||
|
||||
public async Task And_I_should_be_redirected_to_the_welcome_page()
|
||||
|
|
@ -50,7 +51,7 @@ public partial class EmailConfirmationSpecs : FeatureFixture
|
|||
{
|
||||
try
|
||||
{
|
||||
await _userService.ConfirmEmailAsync("invalid-confirmation-token");
|
||||
await _accountService.ConfirmEmailAsync("invalid-confirmation-token");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
|
|
@ -65,9 +66,9 @@ public partial class EmailConfirmationSpecs : FeatureFixture
|
|||
|
||||
public async Task And_my_email_remains_unconfirmed()
|
||||
{
|
||||
if (_currentUser != null)
|
||||
if (_currentAccount != null)
|
||||
{
|
||||
_currentUser.EmailConfirmed.ShouldBeFalse();
|
||||
_currentAccount.EmailConfirmed.ShouldBeFalse();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -5,38 +5,39 @@ using PlanTempus.X.Services;
|
|||
using Shouldly;
|
||||
|
||||
namespace PlanTempus.X.BDD.FeatureFixtures;
|
||||
|
||||
[TestClass]
|
||||
[FeatureDescription(@"As a user with confirmed email
|
||||
I want to set up my organization
|
||||
So I can start using the system with my team")]
|
||||
public partial class OrganizationSetupSpecs : FeatureFixture
|
||||
{
|
||||
IUserService _userService;
|
||||
IAccountService _accountService;
|
||||
IEmailService _emailService;
|
||||
IOrganizationService _organizationService;
|
||||
IUserOrganizationService _userOrganizationService;
|
||||
IAccountOrganizationService _accountOrganizationService;
|
||||
ITenantService _tenantService;
|
||||
IAuthService _authService;
|
||||
|
||||
protected User _currentUser;
|
||||
protected Account _currentAccount;
|
||||
protected Organization _organization;
|
||||
protected Exception _setupError;
|
||||
protected List<Organization> _userOrganizations;
|
||||
protected List<Organization> _accountOrganizations;
|
||||
|
||||
public async Task Given_user_has_confirmed_their_email(string email)
|
||||
public async Task Given_account_has_confirmed_their_email(string email)
|
||||
{
|
||||
// Create a user with confirmed email
|
||||
_currentUser = await _userService.CreateUserAsync(email, "Test User");
|
||||
// Create an account with confirmed email
|
||||
_currentAccount = await _accountService.CreateAccountAsync(email, "TestPassword123!");
|
||||
var confirmationLink = await _emailService.GetConfirmationLinkForEmail(email);
|
||||
await _userService.ConfirmEmailAsync(confirmationLink);
|
||||
_currentUser.EmailConfirmed.ShouldBeTrue();
|
||||
await _accountService.ConfirmEmailAsync(confirmationLink);
|
||||
_currentAccount.EmailConfirmed.ShouldBeTrue();
|
||||
}
|
||||
|
||||
public async Task When_user_submit_organization_name_and_valid_password(string orgName, string password)
|
||||
public async Task When_account_submit_organization_name_and_valid_password(string orgName, string password)
|
||||
{
|
||||
try
|
||||
{
|
||||
_organization = await _organizationService.SetupOrganizationAsync(_currentUser.Id, orgName, password);
|
||||
_organization = await _organizationService.SetupOrganizationAsync(_currentAccount.Id, orgName, password);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
|
|
@ -48,18 +49,17 @@ public partial class OrganizationSetupSpecs : FeatureFixture
|
|||
{
|
||||
_organization.ShouldNotBeNull();
|
||||
_organization.Name.ShouldBe("Acme Corp");
|
||||
_organization.CreatedBy.ShouldBe(_currentUser.Id);
|
||||
_organization.CreatedBy.ShouldBe(_currentAccount.Id);
|
||||
|
||||
await Task.CompletedTask;
|
||||
}
|
||||
|
||||
public async Task And_the_user_should_be_linked_to_the_organization_in_user_organizations()
|
||||
public async Task And_the_account_should_be_linked_to_the_organization_in_account_organizations()
|
||||
{
|
||||
var userOrg = _userOrganizationService.GetUserOrganization(_currentUser.Id, _organization.Id);
|
||||
userOrg.ShouldNotBeNull();
|
||||
var accountOrg = _accountOrganizationService.GetAccountOrganization(_currentAccount.Id, _organization.Id);
|
||||
accountOrg.ShouldNotBeNull();
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
|
||||
public async Task And_tenant_tables_should_be_created_for_the_organization()
|
||||
|
|
@ -68,23 +68,21 @@ public partial class OrganizationSetupSpecs : FeatureFixture
|
|||
tenantTablesExist.ShouldBeTrue();
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
|
||||
public async Task And_user_should_be_logged_into_the_system()
|
||||
public async Task And_account_should_be_logged_into_the_system()
|
||||
{
|
||||
var isAuthenticated = _authService.IsUserAuthenticated(_currentUser.Id);
|
||||
var isAuthenticated = _authService.IsAccountAuthenticated(_currentAccount.Id);
|
||||
isAuthenticated.ShouldBeTrue();
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
|
||||
public async Task When_user_submit_organization_name_without_password(string orgName)
|
||||
public async Task When_account_submit_organization_name_without_password(string orgName)
|
||||
{
|
||||
try
|
||||
{
|
||||
await _organizationService.SetupOrganizationAsync(_currentUser.Id, orgName, "");
|
||||
await _organizationService.SetupOrganizationAsync(_currentAccount.Id, orgName, "");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
|
|
@ -98,37 +96,34 @@ public partial class OrganizationSetupSpecs : FeatureFixture
|
|||
_setupError.Message.ShouldBe(expectedErrorMessage);
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
|
||||
public async Task Given_user_has_completed_initial_setup(string email)
|
||||
public async Task Given_account_has_completed_initial_setup(string email)
|
||||
{
|
||||
await Given_user_has_confirmed_their_email(email);
|
||||
await When_user_submit_organization_name_and_valid_password("First Org", "ValidP@ssw0rd");
|
||||
_userOrganizations = new List<Organization> { _organization };
|
||||
await Given_account_has_confirmed_their_email(email);
|
||||
await When_account_submit_organization_name_and_valid_password("First Org", "ValidP@ssw0rd");
|
||||
_accountOrganizations = new List<Organization> { _organization };
|
||||
}
|
||||
|
||||
public async Task When_user_create_a_new_organization(string orgName)
|
||||
public async Task When_account_create_a_new_organization(string orgName)
|
||||
{
|
||||
var newOrg = await _organizationService.CreateOrganizationAsync(_currentUser.Id, orgName);
|
||||
_userOrganizations.Add(newOrg);
|
||||
var newOrg = await _organizationService.CreateOrganizationAsync(_currentAccount.Id, orgName);
|
||||
_accountOrganizations.Add(newOrg);
|
||||
}
|
||||
|
||||
public async Task Then_a_new_organization_entry_should_be_created()
|
||||
{
|
||||
_userOrganizations.Count.ShouldBe(2);
|
||||
_userOrganizations[1].Name.ShouldBe("Second Org");
|
||||
_accountOrganizations.Count.ShouldBe(2);
|
||||
_accountOrganizations[1].Name.ShouldBe("Second Org");
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
|
||||
public async Task And_the_user_should_be_linked_to_both_organizations()
|
||||
public async Task And_the_account_should_be_linked_to_both_organizations()
|
||||
{
|
||||
var userOrgs = _userOrganizationService.GetUserOrganizations(_currentUser.Id);
|
||||
userOrgs.Count.ShouldBe(2);
|
||||
var accountOrgs = _accountOrganizationService.GetAccountOrganizations(_currentAccount.Id);
|
||||
accountOrgs.Count.ShouldBe(2);
|
||||
|
||||
await Task.CompletedTask;
|
||||
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue