Added Login validation

This commit is contained in:
TheXamlGuy
2024-06-16 19:19:12 +01:00
parent 8d574362a0
commit 8d76b712be
5 changed files with 92 additions and 40 deletions
+5 -2
View File
@@ -14,7 +14,10 @@ public interface IValidation :
ValidationRule[] rules, ValidationRule[] rules,
ValidationTrigger trigger = ValidationTrigger.Deferred); ValidationTrigger trigger = ValidationTrigger.Deferred);
bool Validate(); Task<bool> Validate<TProperty>(Expression<Func<TProperty>> property,
ValidationRule[] rules);
bool Validate(string name); Task<bool> Validate();
Task<bool> Validate(string name);
} }
+28 -5
View File
@@ -27,7 +27,7 @@ public class Validation(IValidatorCollection validators) :
if (trigger is ValidationTrigger.Immediate) if (trigger is ValidationTrigger.Immediate)
{ {
Validate(name); _ = Validate(name);
} }
} }
@@ -37,7 +37,28 @@ public class Validation(IValidatorCollection validators) :
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName)); PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
} }
public bool Validate(string name)
public async Task<bool> Validate<TProperty>(Expression<Func<TProperty>> property,
ValidationRule[] rules)
{
string? name = GetPropertyName(property);
Validator validator = new(name, rules);
(bool isValid, string? message) = await validator.TryValidate();
if (!isValid)
{
errors[name] = message ?? "";
}
OnPropertyChanged(nameof(Errors), null, null);
OnPropertyChanged(nameof(HasErrors), null, null);
return !HasErrors;
}
public async Task<bool> Validate(string name)
{ {
if (Errors.ContainsKey(name)) if (Errors.ContainsKey(name))
{ {
@@ -48,7 +69,8 @@ public class Validation(IValidatorCollection validators) :
{ {
if (validator is not null) if (validator is not null)
{ {
if (!validator.TryValidate(out string? message)) (bool isValid, string? message) = await validator.TryValidate();
if (!isValid)
{ {
errors[name] = message ?? ""; errors[name] = message ?? "";
} }
@@ -61,14 +83,15 @@ public class Validation(IValidatorCollection validators) :
return !HasErrors; return !HasErrors;
} }
public bool Validate() public async Task<bool> Validate()
{ {
errors.Clear(); errors.Clear();
foreach (Validator? validator in Validators) foreach (Validator? validator in Validators)
{ {
if (validator.PropertyName is string name) if (validator.PropertyName is string name)
{ {
if (!validator.TryValidate(out string? message)) (bool isValid, string? message) = await validator.TryValidate();
if (!isValid)
{ {
errors[name] = message ?? ""; errors[name] = message ?? "";
} }
+33 -10
View File
@@ -2,26 +2,49 @@
public class ValidationRule public class ValidationRule
{ {
public ValidationRule(Func<bool> validation, private readonly Func<bool>? syncValidation;
private readonly Func<Task<bool>>? asyncValidation;
public ValidationRule(Func<bool> validation,
string message) string message)
{ {
Validation = validation; syncValidation = validation;
Message = new Func<string>(() => message); Message = message;
}
public ValidationRule(Func<Task<bool>> validation,
string message)
{
asyncValidation = validation;
Message = message;
} }
public ValidationRule(Func<bool> validation) public ValidationRule(Func<bool> validation)
{ {
Validation = validation; syncValidation = validation;
Message = "";
} }
public ValidationRule(Func<bool> validation, public ValidationRule(Func<Task<bool>> validation)
Func<string> message)
{ {
Validation = validation; asyncValidation = validation;
Message = message; Message = "";
} }
public Func<string>? Message { get; } public async Task<bool> ValidateAsync()
{
if (syncValidation is not null)
{
return syncValidation();
}
public Func<bool>? Validation { get; } if (asyncValidation is not null)
{
return await asyncValidation();
}
return false;
}
public string Message { get; }
} }
+10 -21
View File
@@ -1,33 +1,22 @@
using System.Diagnostics.CodeAnalysis; namespace Toolkit.Foundation;
namespace Toolkit.Foundation; public class Validator(string propertyName,
ValidationRule[] rules)
public class Validator
{ {
private readonly ValidationRule[] rules = []; private readonly ValidationRule[] rules = rules;
public Validator(string propertyName, public string? PropertyName { get; } = propertyName;
ValidationRule[] rules)
public async Task<(bool isValid, string? message)> TryValidate()
{ {
PropertyName = propertyName;
this.rules = rules;
}
public string? PropertyName { get; }
public bool TryValidate([MaybeNull] out string message)
{
message = "";
foreach (ValidationRule rule in rules) foreach (ValidationRule rule in rules)
{ {
if (rule.Validation?.Invoke() == false) if (!await rule.ValidateAsync())
{ {
message = rule.Message?.Invoke(); return (false, rule.Message);
return false;
} }
} }
return true; return (true, null);
} }
} }
@@ -12,12 +12,21 @@ public class KeyBindingTriggerBehaviour :
public static readonly StyledProperty<KeyGesture> GestureProperty = public static readonly StyledProperty<KeyGesture> GestureProperty =
AvaloniaProperty.Register<KeyBindingTriggerBehaviour, KeyGesture>(nameof(Gesture)); AvaloniaProperty.Register<KeyBindingTriggerBehaviour, KeyGesture>(nameof(Gesture));
public static readonly StyledProperty<bool> IsEnabledProperty =
AvaloniaProperty.Register<KeyBindingTriggerBehaviour, bool>(nameof(IsEnabled), true);
public KeyGesture Gesture public KeyGesture Gesture
{ {
get => GetValue(GestureProperty); get => GetValue(GestureProperty);
set => SetValue(GestureProperty, value); set => SetValue(GestureProperty, value);
} }
public bool IsEnabled
{
get => GetValue(IsEnabledProperty);
set => SetValue(IsEnabledProperty, value);
}
public event EventHandler? CanExecuteChanged; public event EventHandler? CanExecuteChanged;
protected override void OnAttached() protected override void OnAttached()
@@ -38,6 +47,11 @@ public class KeyBindingTriggerBehaviour :
public bool CanExecute(object? parameter) => true; public bool CanExecute(object? parameter) => true;
public void Execute(object? parameter) => public void Execute(object? parameter)
Interaction.ExecuteActions(AssociatedObject, Actions, null); {
if (IsEnabled)
{
Interaction.ExecuteActions(AssociatedObject, Actions, null);
}
}
} }