Search code examples
c#jqueryasp.net-mvcasp.net-mvc-4partial

JQuery Validate custom method not working after jquery.load()


My attempt at getting JQueryValidate custom validation attributes does not seem to be working when using jquery.load. This is my code:

CreateViewModel.cs

public class CreateViewModel
{
    [DisplayName("Artwork")]
    public int ArtworkId { get; set; }

    [AtLeastOne("selectiongroup")]
    public bool IsPromo { get; set; }
    [AtLeastOne("selectiongroup")]
    public bool IsUpc { get; set; }
    [AtLeastOne("selectiongroup")]
    public bool IsCoupon { get; set; }

    public SelectList ArtworkSelectList { get; set; }
}

AtLeastOneAttribute.cs

[AttributeUsage(AttributeTargets.Property, AllowMultiple = true)]
public class AtLeastOneAttribute : ValidationAttribute, IClientValidatable
{
    public string GroupName { get; private set; }

    public AtLeastOneAttribute(string groupName)
    {
        GroupName = groupName;
    }
    public IEnumerable<ModelClientValidationRule> GetClientValidationRules(ModelMetadata metadata, ControllerContext context)
    {
        yield return new ModelClientValidationRule
        {
            ErrorMessage = "At least one of Coupon or Upc or Promo is required.",
            ValidationType = "atleastone",
            ValidationParameters =
            {
                new KeyValuePair<string, object>("groupname", GroupName),
            }
        };
    }
}

Page.cshtml

<form method="POST" id="signCreationForm">
    <div class="container-fluid">
        <div class="row">
            <div class="col-lg-6">
                @Html.LabelFor(model => model.ArtworkId)
                @Html.DropDownListFor(model => model.ArtworkId, Model.ArtworkSelectList, "Select an Artwork")
            </div>
        </div>
        <div class="row">
            <div class="col-lg-6"></div>
            <div>@Html.ValidationMessageFor(model => model.ArtworkId)</div>
        </div>
        <div class="row">
            <div class="col-lg-10">
                <label>Associated With:</label>
            </div>
        </div>
        <div class="row">
            <div class="col-lg-4">
                @Html.LabelFor(model => model.IsUpc, "UPC")
                @Html.CheckBoxFor(model => model.IsUpc)
                @Html.ValidationMessageFor(model => model.IsUpc)
            </div>
            <div class="col-lg-4">
                @Html.LabelFor(model => model.IsCoupon, "Coupon")
                @Html.CheckBoxFor(model => model.IsCoupon)
                @Html.ValidationMessageFor(model => model.IsCoupon)
            </div>
            <div class="col-lg-4">
                @Html.LabelFor(model => model.IsPromo, "Promotion")
                @Html.CheckBoxFor(model => model.IsPromo)
                @Html.ValidationMessageFor(model => model.IsPromo)
            </div>
        </div>
    </div>
</form>
@Scripts.Render("~/bundles/jqueryval")
<script type="text/javascript">
    $.validator.addMethod("atleastone", function (value, element, params) {
        return $("[data-val-atleastone-groupname="+params+"]:checked").length > 0;
    });

    $.validator.unobtrusive.adapters.add("atleastone", ["groupname"], function (options) {
        options.rules["atleastone"] = options.params.groupname;
        options.messages["atleastone"] = options.message;
    });
</script>

CallingPage.cshtml (javascript that is calling it)

        $("#create-ad[data-link]").on("click", function() {
            var link = $(this).data("link");
            $createDialog.load(link, function() {
                $createDialog.dialog("open");
                $.validator.unobtrusive.parse($("#signCreationForm"));
            });
        });

Now, this code works in a separate project. In this project, the partial view is loaded via jquery.load() event and for some reason this causes the custom method to never execute. I know this because the alerts would normally fire off once for each attribute decorated with atleastone attribute.

Is there anything special that needs to be done on Page.cshtml when using jquery load with custom jqueryvalidate validations?


Solution

  • The suggested duplicate for this scenario answer https://stackoverflow.com/a/16105954/82333 got the first half of the problem which was that the the add $.validator.unobtrusive.adapters.add was not functioning. However, after that the rest of the code wasn't running either.

    @Bhavin Solanki's comment to include the validation files on the calling page fixed the other half, which was that on submit the code was not running.