Skip to content

Commit 2d26eb3

Browse files
committed
Password check delay added. Secure storage feature added.
1 parent bdb20dc commit 2d26eb3

8 files changed

Lines changed: 115 additions & 20 deletions

File tree

SharpPasswordManager.BL/Autenticator.cs

Lines changed: 8 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
using System;
2+
using System.Threading.Tasks;
23
using SharpPasswordManager.BL.Interfaces;
34

45
namespace SharpPasswordManager.BL
@@ -22,6 +23,10 @@ value in <autenticate> method is null.
2223
/// </summary>
2324
public class Autenticator : IAuthenticator
2425
{
26+
const int authDelay = 500;
27+
const int authDelayRange = 100;
28+
Random rng = new Random();
29+
2530
ICryptographer cryptographer;
2631

2732
/// <summary>
@@ -39,11 +44,13 @@ public Autenticator(ICryptographer cryptographer = null)
3944
/// </summary>
4045
/// <param name="password">Entered password.</param>
4146
/// <returns></returns>
42-
public bool Autenticate(string password, string encryptedPassword)
47+
public async Task<bool> Autenticate(string password, string encryptedPassword)
4348
{
4449
if (password == null || encryptedPassword == null)
4550
throw new ArgumentNullException();
4651

52+
await Task.Delay(rng.Next(authDelay - authDelayRange, authDelay + authDelayRange));
53+
4754
if (cryptographer != null)
4855
{
4956
cryptographer.ChangeKey(password);
Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,13 @@
1-
namespace SharpPasswordManager.BL.Interfaces
1+
using System.Threading.Tasks;
2+
3+
namespace SharpPasswordManager.BL.Interfaces
24
{
35
/// <summary>
46
/// Provides a mechanism to autentication.
57
/// </summary>
68
public interface IAuthenticator
79
{
8-
bool Autenticate(string password, string encryptedPassword);
10+
Task<bool> Autenticate(string password, string encryptedPassword);
911
void ChangeKey(string newKey);
1012
}
1113
}

SharpPasswordManager.Tests/AutenticatorTests.cs

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,31 +1,32 @@
11
using NUnit.Framework;
22
using SharpPasswordManager.BL;
3+
using System.Threading.Tasks;
34

45
namespace SharpPasswordManager.Tests
56
{
67
public class AutenticatorTests
78
{
89
[Test]
9-
public void Autenticate_WithSamePassword()
10+
public async Task Autenticate_WithSamePassword()
1011
{
1112
string encryptedPassword = "12345";
1213
string password = "12345";
1314
Autenticator autenticator = new Autenticator();
1415

15-
bool result = autenticator.Autenticate(password, encryptedPassword);
16+
bool result = await autenticator.Autenticate(password, encryptedPassword);
1617
bool expected = true;
1718

1819
Assert.That(result, Is.EqualTo(expected));
1920
}
2021

2122
[Test]
22-
public void Autenticate_WithDifferentPasswords()
23+
public async Task Autenticate_WithDifferentPasswords()
2324
{
2425
string encryptedPassword = "12345";
2526
string password = "54321";
2627
Autenticator autenticator = new Autenticator();
2728

28-
bool result = autenticator.Autenticate(password, encryptedPassword);
29+
bool result = await autenticator.Autenticate(password, encryptedPassword);
2930
bool expected = false;
3031

3132
Assert.That(result, Is.EqualTo(expected));

SharpPasswordManager/Handlers/IStorageHandler.cs

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
using System.Collections.Generic;
2+
using System.Threading.Tasks;
23

34
namespace SharpPasswordManager.Handlers
45
{
@@ -17,5 +18,6 @@ public interface IStorageHandler<TCategory, TData>
1718
void AddData(TData data, TCategory toCategory);
1819
void ReplaceCategory(TCategory oldCategory, TCategory newCategory);
1920
void ReplaceData(TData oldData, TData newData);
21+
Task SecureStorageAsync();
2022
}
2123
}

SharpPasswordManager/Handlers/StorageHandler.cs

Lines changed: 43 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,9 @@
1-
using SharpPasswordManager.BL.Interfaces;
1+
using SharpPasswordManager.BL;
2+
using SharpPasswordManager.BL.Interfaces;
23
using SharpPasswordManager.DL.Models;
34
using System;
45
using System.Collections.Generic;
6+
using System.Threading.Tasks;
57

68
namespace SharpPasswordManager.Handlers
79
{
@@ -156,6 +158,46 @@ public void ReplaceData(DataModel oldData, DataModel newData)
156158
}
157159
}
158160

161+
public async Task SecureStorageAsync()
162+
{
163+
await Task.Run(SecureStorage);
164+
}
165+
166+
private void SecureStorage()
167+
{
168+
var dataIndexes = GetUsingDataIndexes();
169+
if (dataIndexes.Count == 0)
170+
return;
171+
172+
List<DataModel> data = new List<DataModel>();
173+
foreach (var index in dataIndexes)
174+
data.Add(dataController.Get(SecureManager.GetIndexOf(index)));
175+
176+
Random rng = new Random();
177+
DataGenerator generator = new DataGenerator();
178+
int storageLength = dataController.Count();
179+
foreach (var item in data)
180+
{
181+
for (int i = 0; i < storageLength / (50 * data.Count); i++)
182+
{
183+
int index;
184+
do
185+
{
186+
index = rng.Next(storageLength);
187+
} while (dataIndexes.Contains(index));
188+
189+
dataController.PasteAt(SecureManager.GetIndexOf(index),
190+
new DataModel
191+
{
192+
Date = item.Date,
193+
Description = item.Description,
194+
Login = item.Login,
195+
Password = generator.GenerateRandomPassword(item.Password.Length)
196+
});
197+
}
198+
}
199+
}
200+
159201
private List<int> GetUsingDataIndexes()
160202
{
161203
List<int> usingIndexes = new List<int>();

SharpPasswordManager/ViewModels/MainViewModel.cs

Lines changed: 38 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,7 @@
22
using SharpPasswordManager.BL.Interfaces;
33
using SharpPasswordManager.DL.Models;
44
using SharpPasswordManager.Handlers;
5+
using System.ComponentModel;
56
using System.IO;
67
using System.Reflection;
78
using System.Windows;
@@ -10,17 +11,20 @@
1011

1112
namespace SharpPasswordManager.ViewModels
1213
{
13-
public class MainViewModel
14+
public class MainViewModel : INotifyPropertyChanged
1415
{
1516
public UserControl CategoriesControl { get; set; }
1617
public UserControl DataControl { get; set; }
1718

19+
public Visibility SecurePanelVisibility { get; set; } = Visibility.Hidden;
20+
IStorageHandler<CategoryModel, DataModel> storageHandler;
21+
1822
public MainViewModel()
1923
{
2024
IStorageController<CategoryModel> categoryController = new StorageController<CategoryModel>(Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), SecureManager.CategoriesFileName));
2125
IStorageController<DataModel> dataController = new StorageController<DataModel>(Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location), SecureManager.DataFileName), new Cryptographer(SecureManager.Key));
2226

23-
IStorageHandler<CategoryModel, DataModel> storageHandler = new StorageHandler(categoryController, dataController);
27+
storageHandler = new StorageHandler(categoryController, dataController);
2428

2529
CategoriesControl = new Views.CategoryView();
2630
CategoryViewModel categoryVM = new CategoryViewModel(storageHandler);
@@ -63,5 +67,37 @@ private void Close()
6367
{
6468
Application.Current.Shutdown();
6569
}
70+
71+
private ICommand secureCmd;
72+
public ICommand SecureCmd
73+
{
74+
get
75+
{
76+
return secureCmd ?? (secureCmd = new CommandHandler(Secure, () => true));
77+
}
78+
}
79+
private async void Secure()
80+
{
81+
SecurePanelVisibility = Visibility.Visible;
82+
OnPropertyChanged(nameof(SecurePanelVisibility));
83+
Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;
84+
await storageHandler.SecureStorageAsync();
85+
Mouse.OverrideCursor = System.Windows.Input.Cursors.Arrow;
86+
SecurePanelVisibility = Visibility.Hidden;
87+
OnPropertyChanged(nameof(SecurePanelVisibility));
88+
}
89+
90+
#region Property changing
91+
public event PropertyChangedEventHandler PropertyChanged;
92+
93+
private void OnPropertyChanged(string propertyName)
94+
{
95+
if (PropertyChanged != null)
96+
{
97+
var args = new PropertyChangedEventArgs(propertyName);
98+
PropertyChanged(this, args);
99+
}
100+
}
101+
#endregion
66102
}
67103
}

SharpPasswordManager/ViewModels/PasswordCheckViewModel.cs

Lines changed: 8 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44
using System.Windows.Input;
55
using System.Windows;
66
using System.Windows.Controls;
7+
using System.Threading.Tasks;
78

89
namespace SharpPasswordManager.ViewModels
910
{
@@ -24,22 +25,20 @@ public ICommand CheckPasswordCmd
2425
{
2526
get
2627
{
27-
return checkPasswordCmd ?? (checkPasswordCmd = new CommandHandler(AccessCheck, (object obj) => true));
28+
return checkPasswordCmd ?? (checkPasswordCmd = new CommandHandler(AccessCheckAsync, (object obj) => true));
2829
}
2930
}
30-
private void AccessCheck(object parameter)
31+
private async void AccessCheckAsync(object parameter)
3132
{
33+
Mouse.OverrideCursor = System.Windows.Input.Cursors.Wait;
3234
var passwordBox = parameter as PasswordBox;
3335
Password = passwordBox.Password;
3436

3537
autenticator.ChangeKey(Password);
36-
bool isAutenticate = false;
37-
try
38-
{
39-
isAutenticate = autenticator.Autenticate(Password, setting.GetByKey(SecureManager.PasswordKey));
40-
}
41-
catch (Exception) { }
42-
38+
bool isAutenticate = await autenticator.Autenticate(Password, setting.GetByKey(SecureManager.PasswordKey));
39+
40+
Mouse.OverrideCursor = System.Windows.Input.Cursors.Arrow;
41+
4342
if (isAutenticate)
4443
{
4544
SecureManager.Key = Password;

SharpPasswordManager/Views/MainView.xaml

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,11 @@
2020

2121
<Border BorderBrush="#FF2F2F82" BorderThickness="2">
2222
<Grid Margin="10">
23-
<Image Source="Logo.png" Width="100" VerticalAlignment="Top" Margin="5"/>
23+
<Button ToolTip="Secure data storage. This may takes some time." VerticalAlignment="Top" HorizontalAlignment="Left" Width="48" Foreground="#FF2F2F82" BorderThickness="0" Style="{DynamicResource MaterialDesignFlatAccentButton}" Command="{Binding SecureCmd}">
24+
<materialDesign:PackIcon Kind="Security" Width="24" Height="24" HorizontalAlignment="Center"/>
25+
</Button>
26+
27+
<Image Source="Logo.png" Width="100" VerticalAlignment="Top" Margin="4"/>
2428

2529
<StackPanel DockPanel.Dock="Top" Orientation="Horizontal" HorizontalAlignment="Right" Height="30" VerticalAlignment="Top">
2630

@@ -39,6 +43,8 @@
3943
<UserControl Content="{Binding DataControl}" Height="385"/>
4044

4145
</StackPanel>
46+
47+
<TextBlock Text="Please wait until programm complete secure operations..." Height="39" Visibility="{Binding Path=SecurePanelVisibility}" Foreground="WhiteSmoke" Background="#FF2F2F82" TextAlignment="Center" VerticalAlignment="Top" Padding="9"/>
4248
</Grid>
4349
</Border>
4450
</Window>

0 commit comments

Comments
 (0)