Skip to content

Commit

Permalink
feat: implement authentication handling and view navigation
Browse files Browse the repository at this point in the history
Signed-off-by: Russell Camo <[email protected]>
  • Loading branch information
russkyc committed Aug 28, 2023
1 parent f4894a8 commit 5535e60
Show file tree
Hide file tree
Showing 29 changed files with 379 additions and 83 deletions.
12 changes: 12 additions & 0 deletions GroomWise.Application/Enums/NavigationPage.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// Copyright (C) 2023 Russell Camo (Russkyc).- All Rights Reserved
//
// Unauthorized copying or redistribution of all files, in source and binary forms via any medium
// without written, signed consent from the author is strictly prohibited.

namespace GroomWise.Application.Enums;

public enum NavigationPage
{
Login,
Main
}
6 changes: 6 additions & 0 deletions GroomWise.Application/GroomWise.Application.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,12 @@
<ItemGroup>
<ProjectReference Include="..\GroomWise.Infrastructure\GroomWise.Infrastructure.csproj" />







</ItemGroup>


Expand Down
40 changes: 36 additions & 4 deletions GroomWise.Application/ViewModels/AppViewModel.cs
Original file line number Diff line number Diff line change
@@ -1,11 +1,43 @@
// Copyright (C) 2023 Russell Camo (Russkyc).- All Rights Reserved
//
//
// Unauthorized copying or redistribution of all files, in source and binary forms via any medium
// without written, signed consent from the author is strictly prohibited.

using GroomWise.Application.Enums;
using GroomWise.Domain.Interfaces;
using GroomWise.Infrastructure.Authentication.Enums;
using GroomWise.Infrastructure.Authentication.Interfaces;
using GroomWise.Infrastructure.Navigation;
using MvvmGen;

namespace GroomWise.Application.ViewModels;

public class AppViewModel
[Inject(typeof(IAuthenticationService))]
[Inject(typeof(IDialogFactory))]
[ViewModel]
[ViewModelGenerateInterface]
public partial class AppViewModel
{

}
[Command]
private async Task Logout()
{
await Task.Run(async () =>
{
var dialogResult = DialogFactory.Create(
"GroomWise",
"Are you sure you want to log out?"
);
if (dialogResult == true)
{
var result = AuthenticationService.Logout();
await Task.Delay(500);
if (result.Equals(AuthenticationStatus.NotAuthenticated))
{
NavigationService.Instance?.Navigate(NavigationPage.Login);
}
}
});
}
}
12 changes: 10 additions & 2 deletions GroomWise.Application/ViewModels/LoginViewModel.cs
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,12 @@
// Unauthorized copying or redistribution of all files, in source and binary forms via any medium
// without written, signed consent from the author is strictly prohibited.

using GroomWise.Application.Enums;
using GroomWise.Application.Observables;
using GroomWise.Domain.Enums;
using GroomWise.Infrastructure.Authentication.Enums;
using GroomWise.Infrastructure.Authentication.Interfaces;
using GroomWise.Infrastructure.Navigation;
using MvvmGen;
using Swordfish.NET.Collections;

Expand Down Expand Up @@ -37,7 +39,7 @@ public partial class LoginViewModel
[Command]
private async Task Login()
{
await Task.Run(() =>
await Task.Run(async () =>
{
var result = AuthenticationService.Login(Username, Password);
Expand Down Expand Up @@ -78,7 +80,13 @@ private async Task Login()
Description = "Login successful."
}
);
Task.Delay(500);
Username = string.Empty;
Password = string.Empty;
await Task.Delay(1000);
Notifications.RemoveLast();
NavigationService.Instance?.Navigate(NavigationPage.Main);
});
}

Expand Down
7 changes: 3 additions & 4 deletions GroomWise.Domain/Entities/Account.cs
Original file line number Diff line number Diff line change
Expand Up @@ -3,16 +3,15 @@
// Unauthorized copying or redistribution of all files, in source and binary forms via any medium
// without written, signed consent from the author is strictly prohibited.

using GroomWise.Domain.Entities;
using GroomWise.Domain.Interfaces;
using LiteDB;

namespace GroomWise.Domain.Entities;
using Role = GroomWise.Domain.Enums.Role;

public class Account : IEntity
{
public Guid Id { get; set; }
public string? Username { get; set; }
public string? Password { get; set; }

public Employee Employee { get; set; }

Check warning on line 15 in GroomWise.Domain/Entities/Account.cs

View workflow job for this annotation

GitHub Actions / build (Debug)

Non-nullable property 'Employee' must contain a non-null value when exiting constructor. Consider declaring the property as nullable.

Check warning on line 15 in GroomWise.Domain/Entities/Account.cs

View workflow job for this annotation

GitHub Actions / build (Release)

Non-nullable property 'Employee' must contain a non-null value when exiting constructor. Consider declaring the property as nullable.
public IList<Role> Roles { get; set; } = new List<Role>();
}
3 changes: 0 additions & 3 deletions GroomWise.Domain/Entities/Employee.cs
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,4 @@ public record Employee : IEntity

[BsonRef("appointments")]
public IList<Appointment>? Appointments { get; set; }

[BsonRef("roles")]
public IList<Role>? Roles { get; set; }
}
15 changes: 15 additions & 0 deletions GroomWise.Domain/Enums/Role.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
// Copyright (C) 2023 Russell Camo (Russkyc).- All Rights Reserved
//
// Unauthorized copying or redistribution of all files, in source and binary forms via any medium
// without written, signed consent from the author is strictly prohibited.

namespace GroomWise.Domain.Enums;

public enum Role
{
Admin,
Manager,
Groomer,
User,
Custom
}
12 changes: 12 additions & 0 deletions GroomWise.Domain/Enums/ViewIdentifier.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
// Copyright (C) 2023 Russell Camo (Russkyc).- All Rights Reserved
//
// Unauthorized copying or redistribution of all files, in source and binary forms via any medium
// without written, signed consent from the author is strictly prohibited.

namespace GroomWise.Domain.Enums;

public enum ViewIdentifier
{
Login,
Main
}
11 changes: 11 additions & 0 deletions GroomWise.Domain/Interfaces/IDialogFactory.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
// Copyright (C) 2023 Russell Camo (Russkyc).- All Rights Reserved
//
// Unauthorized copying or redistribution of all files, in source and binary forms via any medium
// without written, signed consent from the author is strictly prohibited.

namespace GroomWise.Domain.Interfaces;

public interface IDialogFactory
{
bool? Create(string messageBoxText, string caption);
}
50 changes: 31 additions & 19 deletions GroomWise.Infrastructure/Authentication/AuthenticationService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@
using GroomWise.Infrastructure.Session.Entities;
using Russkyc.DependencyInjection.Attributes;
using Russkyc.DependencyInjection.Enums;
using Role = GroomWise.Domain.Enums.Role;

namespace GroomWise.Infrastructure.Authentication;

Expand All @@ -29,21 +30,27 @@ public AuthenticationService(GroomWiseDbContext dbContext, IEncryptionService en
_encryptionService = encryptionService;
}

public void Register(string username, string password, Guid employeeId)
public void Register(
string username,
string password,
Role role = Role.User,
Guid? employeeId = null
)
{
var employee = _dbContext.Employees.Get(employee => employee.Id.Equals(employeeId));
var account = new Account();
account.Username = _encryptionService.Hash(username);
account.Password = _encryptionService.Hash(password);
account.Roles.Add(role);

if (employee is null)
if (employeeId is not null)
{
return;
}
var employee = _dbContext.Employees.Get(employee => employee.Id.Equals(employeeId));

var account = new Account
{
Username = _encryptionService.Hash(username),
Password = _encryptionService.Hash(password),
Employee = employee
};
if (employee is not null)
{
account.Employee = employee;
}
}

_dbContext.Accounts.Insert(account);
}
Expand Down Expand Up @@ -71,11 +78,11 @@ public AuthenticationStatus Login(string username, string password)
return AuthenticationStatus.Authenticated;
}

public string Update(
public UpdateStatus Update(
string username,
string password,
string newUsername = "",
string newPassword = ""
string newUsername,
string newPassword
)
{
var account = _dbContext.Accounts.Get(
Expand All @@ -86,7 +93,7 @@ public AuthenticationStatus Login(string username, string password)

if (account is null)
{
return "Account does not exist.";
return UpdateStatus.InvalidAccount;
}

if (!string.IsNullOrEmpty(username))
Expand All @@ -99,18 +106,23 @@ public AuthenticationStatus Login(string username, string password)
account.Password = _encryptionService.Hash(newPassword);
}

_dbContext.Accounts.Update(account.Id, account);
bool executeUpdate = _dbContext.Accounts.Update(account.Id, account);

if (executeUpdate)
{
return UpdateStatus.Success;
}

return "Account successfully updated";
return UpdateStatus.Fail;
}

public string Logout()
public AuthenticationStatus Logout()
{
lock (_lock)
{
_sessionInfo = null!;
}
return "Logout successful.";
return AuthenticationStatus.NotAuthenticated;
}

public SessionInfo? GetSession()
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -9,5 +9,6 @@ public enum AuthenticationStatus
{
InvalidPassword,
InvalidAccount,
Authenticated
Authenticated,
NotAuthenticated
}
13 changes: 13 additions & 0 deletions GroomWise.Infrastructure/Authentication/Enums/UpdateStatus.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
// Copyright (C) 2023 Russell Camo (Russkyc).- All Rights Reserved
//
// Unauthorized copying or redistribution of all files, in source and binary forms via any medium
// without written, signed consent from the author is strictly prohibited.

namespace GroomWise.Infrastructure.Authentication.Enums;

public enum UpdateStatus
{
InvalidAccount,
Success,
Fail
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,23 +3,20 @@
// Unauthorized copying or redistribution of all files, in source and binary forms via any medium
// without written, signed consent from the author is strictly prohibited.

using GroomWise.Domain.Enums;
using GroomWise.Infrastructure.Authentication.Enums;
using GroomWise.Infrastructure.Session.Entities;

namespace GroomWise.Infrastructure.Authentication.Interfaces;

public interface IAuthenticationService
{
void Register(string username, string password, Guid employeeId);
void Register(string username, string password, Role role = Role.User, Guid? employeeId = null);

AuthenticationStatus Login(string username, string password);

string Update(
string username,
string password,
string newUsername = "",
string newPassword = ""
);
UpdateStatus Update(string username, string password, string newUsername, string newPassword);

string Logout();
AuthenticationStatus Logout();
SessionInfo? GetSession();
}
15 changes: 7 additions & 8 deletions GroomWise.Infrastructure/Encryption/CredentialStore.cs
Original file line number Diff line number Diff line change
Expand Up @@ -13,19 +13,18 @@ public partial class CredentialStore
{
public void Save(string key, string value)
{
using var credential = new Credential
{
Target = key,
Password = value,
Type = CredentialType.Generic,
PersistanceType = PersistanceType.LocalComputer
};
using var credential = new Credential();
credential.Target = key;
credential.Password = value;
credential.Type = CredentialType.Generic;
credential.PersistanceType = PersistanceType.LocalComputer;
credential.Save();
}

public string Get(string key)
{
using var credential = new Credential { Target = key };
using var credential = new Credential();
credential.Target = key;
credential.Load();
return credential.Password;
}
Expand Down
8 changes: 8 additions & 0 deletions GroomWise.Infrastructure/GroomWise.Infrastructure.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -31,4 +31,12 @@
<None Remove=".env" />
</ItemGroup>









</Project>
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
// Copyright (C) 2023 Russell Camo (Russkyc).- All Rights Reserved
//
// Unauthorized copying or redistribution of all files, in source and binary forms via any medium
// without written, signed consent from the author is strictly prohibited.

namespace GroomWise.Infrastructure.Navigation.Interfaces;

public interface INavigationService
{
static INavigationService Instance { get; }

Check warning on line 10 in GroomWise.Infrastructure/Navigation/Interfaces/INavigationService.cs

View workflow job for this annotation

GitHub Actions / build (Debug)

Non-nullable property 'Instance' must contain a non-null value when exiting constructor. Consider declaring the property as nullable.

Check warning on line 10 in GroomWise.Infrastructure/Navigation/Interfaces/INavigationService.cs

View workflow job for this annotation

GitHub Actions / build (Release)

Non-nullable property 'Instance' must contain a non-null value when exiting constructor. Consider declaring the property as nullable.
IWindow CurrentWindow { get; }
void Add(Enum key, IWindow instance);
void Add(Enum key, IPage instance);
void Navigate(Enum key);
}
Loading

0 comments on commit 5535e60

Please sign in to comment.