Search code examples
asp.net-mvc-5unobtrusive-validationclient-side-validation

Implementing custom client validation based off of another textbox input


I've been dabbling a little into MVC 5's custom client validation (MVC's GetClientValidationRules and jQuery's validator). I've been able to successfully implement a validator to check whether the user selects a date that is in the past. But what about if I need to check if a user's textbox input is greater than another textbox's input of theirs?

I have it working fine without unobtrusive validation/server-side, but not with unobtrusive validation.

Here's an example.

Model

public Nullable<int> ItemsPurchased
public Nullable<int> ItemsReturned

A custom DataAnnotation has been made for ItemsReturned to check whether its value <= ItemsPurchased. Implementing GetClientValidationRules to actually get ItemsPurchased's current value is where I'm having trouble in the code.


Solution

  • I had a variable in my custom data annotation. I'm not sure why this didn't come to me naturally...but here's my solution.

    DataAnnotation (Applied to ItemsReturned)

    public string purchasedQuantityField { get; set; }
    public ReturnedAttribute(string quantity) {
        purchasedQuantityField = quantity;
    }
    ...
    (in GetClientValidationRules)
    ModelClientvalidationRule purchaseRule = new ModelClientValidationRule();
    purchaseRule.ValidationType = "purchaserestriction";
    purchaseRule.ErrorMessage = ErrorMessageString;
    purchaseRule.ValidationParameters["otherfield"] = purchasedQuantityField;
    

    Usage in the model:

    [Returned("ItemsPurchased", ErrorMessage = "Returned Items cannot be greater than the number of Items Purchased.")]
    

    Then I made my own JS file with the custom client validation rules, CustomClientValidation.js:

    jQuery.validator.addMethod("purchaserestriction", function (value, element, params) {
        var purchasedFieldVal = $('input[name="' + params.otherfield + '"]').val();
        if (purchasedFieldVal && value) {
            var returnedVal = parseInt(value);
            var purchasedVal = parseInt(purchasedFieldVal);
            if (returnedVal <= purchasedVal) return true;
            else return false;
        }
    );
    jQuery.validator.unobtrusive.adapters.add("purchaserestriction", ["otherfield"], function (options) {
        options.rules["purchaserestriction"] = options.params;
        if (options.message) options.messages["purchaserestriction"] = options.message;
    });