Skip to content

Async validation

Vsevolod Pilipenko edited this page Jul 16, 2023 · 3 revisions

Create async validation rules

You can use rule Mustand pass Task<> there.

builder.RuleFor(vm => vm.Email)
    .NotEmpty().When(vm => vm.PhoneNumber, phoneNumber => string.IsNullOrEmpty(phoneNumber))
    .Must(IsValidEmail)
    .Must(CheckEmailIsInUseAsync).WithMessage("Email is already using");

...

/// <summary>
/// Check of email is valid.
/// </summary>
private static bool IsValidEmail(string? email)
{
    // Some sync logic.
}

/// <summary>
/// Async check that email is already using.
/// </summary>
private static async Task<bool> CheckEmailIsInUseAsync(string? email, CancellationToken cancellationToken)
{
    // Some async logic.
}

Important moments

  1. It's better to use for properties with async validation CascadeMode.Stop. Your first rules will check validity of property and you don't need to run a long async operation if property is not valid. About CascadeMode describing here.
  2. Remember about CancellationToken. If you don't use it, you will have a lot of parallel execution if property value changed quickly.
  3. If validating property can change very fast (for example, some string which user types char by char), it's good idea to use delay before validation (property throttling).

Waiting async validation completeness

While async validation is running - there is not messages for it. So, if you want to pass some of your properties further, you need to wait until validation is completed. For this, you can use method IObjectValidator.WaitValidatingCompletedAsync. Note: make sure that you block UI. If user will be changing property constantly, async validation won't ever end.

Create custom async validation rules

You can inherit from class BaseAsyncPropertyValidator<TObject, TProp> and create your own async validation rule.