1

I am using ASP.NET MVC with Unobtrusive js and it's running perfectly fine but I want to set a rule of Validation for something like this:

I have dropdownlist with two values "Yes" and "No". I have one textbox as well.

Based on selection of the values from dropdownlist if

"Yes" I want to validate that textbox value entered or not using Unobtrusive at client side with server side as well and if

"No" than no validation should work I mean it's ok if textbox value blank or whatever the values entered because I don't want to store that value if dropdownlist value is No no validation should work on that textbox.

Please someone help me out with this problem.

I have already refer so many stackoverflow questions and answers it's pretty good answers too there as well but I am not able to put those to get my solution.

I got the values of dropdown selection in bool i.e.

 public bool IsTestUnit { get; set; }
    [RequiredIfUniTestIsYes("IsTestUnit == true", true, ErrorMessage = "Please Enter Test Unit Job Order Number ")]
        public long TestUnitJobOrder { get; set; }

The code that I have tried:

 public class RequiredIfUniTestIsYes : ValidationAttribute, IClientValidatable
    {
        public RequiredIfUniTestIsYes()
        {

        }

        protected override ValidationResult IsValid(object value, ValidationContext validationContext)
        {
            var countryPropertyInfo = validationContext.ObjectInstance.GetType().GetProperty("IsTestUnit");
            var countryValue = countryPropertyInfo.GetValue(validationContext.ObjectInstance, null).ToString();
            if (countryValue == "True" && (value.ToString().Trim() == "" || Convert.ToInt32(value) == 0))
            {
                return new ValidationResult("Please Enter Unit Test Job Order Number");
            }

            return ValidationResult.Success;
        }

        public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context)
        {
            var rule = new ModelClientValidationRule();
            rule.ErrorMessage = "Please Enter Unit Test Job Order Number";
            rule.ValidationParameters.Add("istestunit", "true");
            rule.ValidationType = "isunittest";

            yield return rule;
        }
    }

Javascript:

$.validator.addMethod("isunittest", function (state, element, country) {
                 var country = $('#WorkOderDetailViewModel_IsTestUnit').val();
                     if (country == 'True' && state == '') {
                         return false;
                     }
                     return true;
                 });

             $.validator.unobtrusive.adapters.addSingleVal("isunittest", "true");

             (function ($) {
                 $.validator.addMethod('customRequire', function (value, element) {
                     // your validation logic here
                     return true; // true if valid, otherwise false 
                 });
                 $.validator.unobtrusive.adapters.add('customRequire');
             })(jQuery);

I have just copy paste the code and do not change the name so please ignore those mistake.

3 rules
  • 1,359
  • 3
  • 26
  • 54
  • Please post what you've tried !. – Mihai Alexandru-Ionut Nov 23 '16 at 07:24
  • Consider a [foolproof](http://foolproof.codeplex.com/) `[RequiredIf]` or similar validation attribute Or you can write your own - [The Complete Guide To Validation In ASP.NET MVC 3 - Part 2](http://www.devtrends.co.uk/blog/the-complete-guide-to-validation-in-asp.net-mvc-3-part-2) –  Nov 23 '16 at 07:25
  • @StephenMuecke I do not have permission to use extra or third party code sir. – 3 rules Nov 23 '16 at 07:26
  • Then write your own! –  Nov 23 '16 at 07:27
  • @StephenMuecke I don't have any idea how to do custom code for validation I just update the question please help me with that. – 3 rules Nov 23 '16 at 07:28
  • 1
    Read the 2nd link I gave you. –  Nov 23 '16 at 07:33
  • @Alexandru-IonutMihai thanks for the link it's pretty good but I don't know how to implement that please can you code it for validate only if selection is "Yes" please. – 3 rules Nov 23 '16 at 07:42
  • Why not use validation on client-side ? It is more easily. – Mihai Alexandru-Ionut Nov 23 '16 at 07:52
  • @Alexandru-IonutMihai yes that is also solution but same issue with client side as well I don't have any idea how to add rule for the same in Unobtrusive js. – 3 rules Nov 23 '16 at 08:05
  • @Alexandru-IonutMihai Ok I have used foolproof for validation but in [RequiredIfTrue("IsTestUnit", true)] but it gives me an error in both in case Yes and in case No as well, Please tell me now am I doing wrong anything! I want only validate if I choose Yes. – 3 rules Nov 23 '16 at 09:01
  • Please look here : http://stackoverflow.com/questions/12176205/disable-validation-for-an-element-with-jquery-unobtrusive-validation – Mihai Alexandru-Ionut Nov 23 '16 at 09:07
  • @Alexandru-IonutMihai No sir still having the same issue, it validated in both cases, I only want it if choose Yes – 3 rules Nov 23 '16 at 09:13
  • I got this validation at server side when I check ModelState.IsValid. – 3 rules Nov 23 '16 at 09:37

1 Answers1

2

Given that you render the fields as below:

@Html.DropDownListFor(m => m.IsTestUnit,
new[] { true, false }.Select(b => new SelectListItem { Text = b ? "Yes" : "No", Value = b.ToString().ToLower() }),
new { id = "WorkOderDetailViewModel_IsTestUnit" })

@Html.TextBoxFor(m => m.TestUnitJobOrder)
@Html.ValidationMessageFor(m => m.TestUnitJobOrder)

with the model properties declared as:

    public bool IsTestUnit { get; set; }

    [RequiredIfUniTestIsYes("IsTestUnit", ErrorMessage = "Please Enter Test Unit Job Order Number ")]
    public long? TestUnitJobOrder { get; set; }

You can define a custom validator like this:

public class RequiredIfUniTestIsYes : ValidationAttribute, IClientValidatable
{
    private string _dependency;

    public RequiredIfUniTestIsYes(string dependency)
    {
        _dependency = dependency;
    }

    protected override ValidationResult IsValid(object value, ValidationContext validationContext)
    {
        var countryPropertyInfo = validationContext.ObjectInstance.GetType().GetProperty(_dependency);
        var countryValue = (bool)countryPropertyInfo.GetValue(validationContext.ObjectInstance, null);
        var number = default(long);
        if (countryValue && (value == null || !long.TryParse(value.ToString(), out number)))
        {
            return new ValidationResult("Please Enter Unit Test Job Order Number");
        }

        return ValidationResult.Success;
    }

    public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context)
    {
        var rule = new ModelClientValidationRule();
        rule.ErrorMessage = "Please Enter Unit Test Job Order Number";
        rule.ValidationParameters.Add("istestunit", "true");
        rule.ValidationType = "isunittest";

        yield return rule;
    }
}

And register client-side unobtrusive validation like this:

    $.validator.unobtrusive.adapters.add("isunittest", ['istestunit'], function(options){
        options.rules['isunittest'] = options.params;
        options.messages['isunittest'] = options.message;
    });    
    $.validator.addMethod('isunittest', function (state, element, params) {
        var country = $('#WorkOderDetailViewModel_IsTestUnit').val();
        if (country == 'true' && state == '') {
            return false;
        }
        return true;
    });
plr108
  • 1,201
  • 11
  • 16
Bob Dust
  • 2,370
  • 1
  • 17
  • 13
  • it gives me validation error in both cases in Yes and in No both. – 3 rules Nov 23 '16 at 09:51
  • @padhiyar, you meant the validation failed even when you entered nothing and `No` was selected? – Bob Dust Nov 23 '16 at 10:12
  • Yes exactly I want validation only If I choose Yes in selection, Validation must not fire when I choose No. – 3 rules Nov 23 '16 at 10:16
  • Did you render dropdown like the one in my example: `@Html.DropDownListFor(m => m.IsTestUnit, new[] { true, false }.Select(b => new SelectListItem { Text = b ? "Yes" : "No", Value = b.ToString().ToLower() }), new { id = "WorkOderDetailViewModel_IsTestUnit" })` and the respective condition in JS: `if (country == 'true' && state == '') {` ? – Bob Dust Nov 23 '16 at 10:20
  • That's weird 'cause those code snippets have been tested and ran well. – Bob Dust Nov 23 '16 at 10:31
  • Let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/128801/discussion-between-padhiyar-and-bob-dust). – 3 rules Nov 23 '16 at 10:33
  • I think you may double check if you have enabled client unobtrusive valition in your Web.config, have referenced to jQuery validation JS files in your razor view, and have placed code block to register `isunittest` outside document ready handler. – Bob Dust Nov 23 '16 at 10:35
  • Ohhh Great Sir it's working now don't know how but I just clean the project and debug again and just start it's working fine. Thank You so much – 3 rules Nov 23 '16 at 11:52
  • It validate's server side but it's ok I am fine with it. – 3 rules Nov 23 '16 at 12:35