【问题标题】:Unobtrusive Validation Keeps breaking in MVC4不显眼的验证不断打破 MVC4
【发布时间】:2012-10-07 15:50:58
【问题描述】:

我遇到了一个让我发疯的奇怪问题。

在运行良好后,它突然出现以下错误:

Validation type names in unobtrusive client validation rules must be unique. The following     
validation type was seen more than once: required

此错误首先在我位于区域/管理/网站的一个控制器上开始。但是,一旦我的 auth cookie 过期,我就会在我的登录页面以及 EditFor(m=>m.UserName) 行上得到它。我梳理了我的代码,在任何可能远程命名相同的模型上的任何地方寻找重复的必需属性,但无济于事。

我什至进入了我的 LoginViewModel,从 UserName 中删除了 [Required]。错误移至 EditFor(m=>m.Password)。我也从 Password 中删除了Required,错误移动了RememberMe 行,但该成员甚至根本没有Required 属性。事实上,我在任何其他类的任何地方都没有其他任何东西,甚至远程命名为 RememberMe。

好吧,我放弃了,开始从头开始重建网站项目(不是解决方案的其余部分),结果还是一样。

出于绝望,我从头开始重建整个解决方案,只复制 *.cs 文件并手动重新加载所有引用,认为某处存在重复引用。

一旦我要再次构建 MVC4 项目,我就分阶段进行,看看我是否能弄清楚发生了什么。它做得很好,加载并且我可以登录等,直到我开始添加区域。起初我只是将 Areas 文件夹直接复制到项目中(所有命名空间名称都相同,所以应该没问题)。但果然我开始以正确的方式得到这个错误。

好的,所以我开始按照最初创建控制器的相反顺序删除控制器。在我完全删除 Areas 文件夹之前,该站点从未恢复正常。

对此进行测试,一旦我在项目中创建了一个区域文件夹,它就会中断。如果我使用 GUI 创建新区域,情况也是如此。

好的,回到绘图板。从头开始重新创建 MVC4 项目,这次是在解决方案之外,并且此时仅提取了对我的解决方案至关重要的 2 个关键 NuGet 包:Ninject.MVC3 和 Mvc3ControlsKit(来自 nuget 的用于 3 和 4 的包)。好吧,一切终于开始运作良好。此时,我的 Jquery 是 1.7.2 版本,带有 MVC4 附带的默认 Jquery UI。

在某个时候,我遇到了 jquery 对话框未关闭的问题,因此我安装了 JQuery 1.8.2 和来自 NuGet 的最新 JQuery UI。一切正常,直到我在我的管理区域中添加一个完全空白的控制器并且再次弹出此错误。

好的,再次回到绘图板...我分阶段重建它,在每个点进行测试。这次不安装最新的 JQuery 好东西。一切又开始正常工作。添加了一个新控制器,然后添加了两个。好的,制作此版本的有效副本并将其放在一边。将 Jquery 和 Jquery UI 更新到最新版本。在该区域添加一个新控制器,它仍然可以继续工作,令我非常沮丧。

我的实体都在使用 Fluent API 来配置我的实体,根本没有 DataAnnotatian 属性。有任何想法吗?我一直在等待它再次破裂。

编辑:

这是我刚刚发现的更多信息。我的登录部分视图中的这行代码发生了错误。我的模型是

public class LoginViewModel 
{
    [Required]
    [Display(Name = "User Name")]
    public string UserName { get; set; }

    [Required]
    [DataType(DataType.Password)]
    [Display(Name = "Password")]
    public string Password { get; set; }

    [Display(Name = "Remember me?")]
    public bool RememberMe { get; set; }

    /// <summary>
    /// Role
    /// </summary>
    public string Role { get; set; }

}

在视图中调用此行时出现错误:

@Html.TextBoxFor(m => m.UserName)

此时,Ninject 接管,并在从 Ninject.Web.Mvc.Validation.NinjectDataAnnotationsModelValidatorProvider 类中的以下方法返回后立即发生上述不显眼的验证错误。此外,我已确认此方法已正确识别所需的验证并注入它们。此方法中没有发生异常,但之后发生了异常。

protected override IEnumerable<ModelValidator> GetValidators(ModelMetadata metadata, ControllerContext context, IEnumerable<Attribute> attributes)
    {
        var validators = base.GetValidators(metadata, context, attributes);
        foreach (var modelValidator in validators.OfType<DataAnnotationsModelValidator>())
        {
            var attribute = this.getAttributeMethodInfo.Invoke(modelValidator, new object[0]);
            this.kernel.Inject(attribute);
        }

        return validators;
    }

【问题讨论】:

  • 如果您多次包含脚本标签(例如在局部视图中),就会发生这种情况。您需要查看生成的最终 HTML 并找出其中的问题,然后您可以将其追溯到源代码。
  • @MystereMan 谢谢。我假设您的意思是 而不仅仅是引用脚本库?我已经检查以确保库没有被引用两次。如果再次发生这种情况,将检查多个 元素。
  • 嗯,现在又发生了,我所做的就是等到第二天。没有添加任何东西。检查脚本和 nada 的重复添加。
  • 好吧,如果你有一个网址,我们可以去找到有帮助的问题,否则我们无能为力,因为这不是一个常见的问题。
  • 是的,我意识到这一点。不幸的是,我还没有发布这个。我敢打赌这是我做过的蠢事;只是令人沮丧。我在上面的问题中添加了更多信息。我想知道 Ninject 是否是罪魁祸首。只是抓住稻草自动取款机。

标签: jquery asp.net-mvc asp.net-mvc-4 unobtrusive-validation


【解决方案1】:

解决方案(如果正在使用 Ninject)是解除绑定。

kernel.Unbind();

【讨论】:

  • 嗯,这很有道理。不幸的是,我在个人项目中使用 Unity 已经有一段时间了,这个问题在我工作的公司中没有出现(它仍然使用 Ninject)。如果再次出现类似问题,我会记住这一点。我想 Unity 也会有类似的功能。
【解决方案2】:

发生错误是因为您尝试在项目中使用混合验证解决方案,并且两个提供商尝试为字段添加不显眼的必需验证,因此引发了重复问题。

确保您没有同时使用数据注释和流畅验证来对同一属性执行相同的验证(如您的情况所要求的那样)。

【讨论】:

  • 我同意它必须是这样,但我没有直接在我的视图模型上使用 Fluent 验证,肯定不是 LoginViewModel。我怀疑是 Ninject.MVC 程序集内部的东西导致了这种双重验证。
  • 好吧,只是为了看看,我继续卸载了 Ninject 并安装和设置了 Unity.MVC,它目前正在运行。我会给它一些时间并继续看这里,看看是否有人对 Ninject 有明确的答案。考虑到我在这个问题上的记录,它可能会在明天打破。
  • @Mark 为我节省了大量时间.. +1
【解决方案3】:

对于这个问题,这不一定是每个人都满意的答案,但我通过将我的 DI 切换到 Unity 解决了我的问题。我已经确定,是的,这是因为正如马克所说,这可能是由于混合验证。我在我的代码中使用 DataAnnotation;可能是 Ninject 在内部使用 Fluent Validation,但我没有足够的了解来确定,也没有精力继续这个追求,因为我找到了一个让我自己满意的答案。

我喜欢 Ninject,但就我而言,最新版本的 Unity 实际上同样易于使用,因为我所要做的就是添加一个文件 (bootstrapper.cs) 并从启动事件中调用 BootStrapper.BuildUnityContainer()。所以,我现在会坚持这个解决方案。

【讨论】:

    【解决方案4】:

    我在使用流利验证的 MVC4 项目中遇到了同样的错误。我的错误是我使用了 .NotNull() 和 .NotEmpty(对于同一个字段):

    RuleFor(i => i.SomeValue).NotNull().NotEmpty();
    

    删除最后一个 .NotEmpty() 解决了问题。

    【讨论】:

      猜你喜欢
      • 2012-01-05
      • 1970-01-01
      • 1970-01-01
      • 2013-10-17
      • 2014-06-07
      • 2012-11-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多