asp:RequiredFieldValidator不validation隐藏字段

ASP.NETvalidation器似乎不validation隐藏字段。 我得到这样的消息:

无法validation由“hiddenFieldValidator”的ControlToValidate属性引用的控件“hiddenField”。

我的页面中有一个 ,它在客户端填充了一些值。 我需要在服务器上出现一次,所以我添加了一个RequiredFieldValidator

它不起作用!

在我看来,作为一种解决方法,我可以:

1.使用自定义validation器而不是将其绑定到隐藏字段,只需在OnServerValidate上调用方法;

2.使用带有CSS样式display:none ,它应该可以工作。

但我想确保我在这里没有遗漏一些东西。 是否可以以与其他文本字段相同的方式validation隐藏字段? 哦,也许是第三个,更优雅的选择?

TIA!

正如您所说的exception消息所示,似乎HiddenField控件无法直接通过标准validation控件进行定位。 我会使用CustomValidator解决方法。

@Peter的回答让我思考, ControlPropertiesValid实际检查了什么?

查看MSDN主题,它会查找ValidationPropertyAttribute … Hhmm,所以如果我们只是从HiddenField派生并用ValidationPropertyAttribute设置为Value (为了我的目的)来装饰新类,那么“一切正常”。 确实如此。

 using System.Web.UI; using System.Web.UI.WebControls; namespace Partner.UserControls { [ValidationProperty("Value")] public class HiddenField2 : HiddenField { } // nothing else required other than ValidationProperty } 

用法 – 确保注册包含控件的程序集:

 <%@ Register Assembly="MyApp" Namespace="MyApp.Controls" TagPrefix="sw" %> 

在您的Page / UserControl内容中:

  

所有validation器都适用于此。 额外的好处是,如果您(像我一样)使用自定义validationfunction,您可以轻松评估HiddenField2.Value因为它包含在args.Value字段中(在服务器端,这是ServerValidateEventArgs )。

这是我提出的解决方法,因为遗憾的是我找不到任何可靠的方法来使用RequiredFieldValidator或CustomValidator开箱validation。 如果将ControlToValidate属性保留为空,则会对您大喊大叫。 您所要做的就是创建一个自定义控件,如下所示:

 public class HiddenFieldValidator : RequiredFieldValidator { protected override bool ControlPropertiesValid() { return true; } } 

通过覆盖属性有效检查以使其始终返回true,它不再关心您正在使用HiddenField,它将从中提取值并validation没有问题。

这是对Scotty.NET解决方案的回应。 我只是没有足够的声誉来回复。

+1到Scotty.NET!

对于我们这些对.NET和编译不够了解的人来说,这可能有助于简化他人对其他人的回答。

我想在使用Visual Web Developer 2010 Express的网站中使用它:

1)我将/ App_Code中的派生HiddenField2保存为HiddenField2.cs,只需更改一次 – > namespace Controls

2)然后,注册控件:

a)在页面上, <%@ Register Assembly="App_Code" Namespace="Controls" TagPrefix="local" %>

b)在web.config中,在system.web> pages> controls中, controls

3)最后,当然,将其称为

它确实使得时髦的代码着色。 可能相当容易改进命名空间来处理它。 在我当地的环境中为我精彩地工作; 我不知道它不会在实时服务器上出现问题。

附加参考: 在网站项目中扩展asp.net控件

要扩展@Anders的解决方案,使用CustomValidator方法,您可以通过首先找到控件,强制转换它,然后使用其UniqueIDPage.Request.Form[]查找其值来轻松获取标准HiddenField控件的值Page.Request.Form[]

示例1:改进比较validation器

此示例可能对您的实现更为本地化。 以下是CompareValidator.EvaluateIsValid()方法调用的改进版本,以便添加对validationHiddenField控件的支持。 请注意,此技术可应用于任何validation程序,而不是将HiddenField包装在自定义控件中,但还应重写ControlPropertiesValid方法以识别并在存在HiddenField返回true。

 ... private new string GetControlValidationValue(string id) { var control = this.NamingContainer.FindControl(id); if (control != null) { if (control is HiddenField) { return Page.Request.Form[((HiddenField)control).UniqueID]; } else { return base.GetControlValidationValue(id); } } } protected override bool EvaluateIsValid() { // removed 'base.' from the call to 'GetControlValidationValue' string controlValidationValue = GetControlValidationValue(base.ControlToValidate); if (controlValidationValue.Trim().Length == 0) { return true; } bool flag = (base.Type == ValidationDataType.Date) && !this.DetermineRenderUplevel(); if (flag && !base.IsInStandardDateFormat(controlValidationValue)) { controlValidationValue = base.ConvertToShortDateString(controlValidationValue); } bool cultureInvariantRightText = false; string date = string.Empty; if (this.ControlToCompare.Length > 0) { //same as above date = GetControlValidationValue(this.ControlToCompare); if (flag && !base.IsInStandardDateFormat(date)) { date = base.ConvertToShortDateString(date); } } else { date = this.ValueToCompare; cultureInvariantRightText = base.CultureInvariantValues; } return BaseCompareValidator.Compare(controlValidationValue, false, date, cultureInvariantRightText, this.Operator, base.Type); } ... 

示例2:自定义动态validation器

这个例子比第一个例子复杂一点。 我经常使用根据页面上另一个控件的值启用或禁用的自定义动态validation器(例如,如果选中该框,则需要此文本框;否则不需要validation)。 一个这样的validation器是我的DynamicRequiredFieldValidator ,它inheritance自内置的RequiredFieldValidator 。 动态validation器有两个自定义属性ControlThatEnablesControlValueThatEnables ,用于决定是否应该打开validation器。 下面是该方法的片段,用于确定是否应启用validation器,但请注意,如上所述,可以将此相同技术应用于validationHiddenField而无需将其包装在自定义控件中。

 ... var enablingControl = this.NamingContainer.FindControl(ControlThatEnables); if (enablingControl != null) { if (enablingControl is HiddenField) { var hfValue = Page.Request.Form[((HiddenField)enablingControl).UniqueID]; isValidatorEnabled = hfValue == ControlValueThatEnables; } } ... 

最后的想法

作为开发人员,实现决策最终取决于您,但我的首选是在自定义控件中包装现有validation器,而不是在自定义控件中包装HiddenFieldsTextBoxesDropDownLists等。 我有两个主要的理由来选择这个解决方案:(1)包装validation器只需要几分钟而不仅仅是添加ValidationProperty ,但为进一步改进.NETvalidation提供了更大的灵活性和机会,例如可以指向FindControl调用一些自定义方法,在当前NamingContainer中搜索所需的控件ID(默认),然后在未找到控件的情况下将搜索扩展到外部PageNamingContainer的父级; (2)恕我直言,如果一个人试图改进validation,改进validation就更清晰了,相反,如果一个人试图改进WebControl ,那么对WebControl进行改进WebControl清晰了。

我完全尊重@ Scotty的解决方案,并且会首先承认,如果这是唯一的改变,那么他的解决方案将比你节省5分钟。 然而,恕我直言,从长远来看,@安德斯可能是一个更好的选择。

我会使用CustomValidator客户端