2009-05-01 4 views
19

Я столкнулся с этой проблемой раньше, но так и не смог ее решить. У меня есть форма с несколькими валидаторами, а также CustomValidator.Элегантный способ работы CustomValidator с сообщением ValidationSummary

<asp:Label ID="lblMemberNum" runat="server" Text="Membership #:" CssClass="LabelMedium" ></asp:Label> 
<asp:TextBox ID="txtMemberNum" runat="server" CssClass="TextBox" ></asp:TextBox> 
<asp:RequiredFieldValidator ID="rfvMemberNum" SetFocusOnError="True" runat="server" 
    ControlToValidate="txtMemberNum" ErrorMessage="[ Membership # ] is required" 
    CssClass="ValidationMessage" Display="Dynamic" >*</asp:RequiredFieldValidator> 
<asp:RegularExpressionValidator ID="revMemberNum" Display="Dynamic" runat="server" 
    ControlToValidate="txtMemberNum" CssClass="ValidationMessage" 
    ErrorMessage="[ Membership # ] can only contain letters" 
    ValidationExpression="^([a-zA-Z\d]+)$" >*</asp:RegularExpressionValidator> 
<asp:CustomValidator ID="cvMemberNum" runat="server" 
    CssClass="ValidationMessage" Display="Dynamic" 
    ControlToValidate="txtMemberNum" ValidateEmptyText="false" 
    OnServerValidate="cvMemberNum_Validate" 
    ErrorMessage="This membership number is already registered">*</asp:CustomValidator> 

<asp:ValidationSummary ID="ValidationSummary1" runat="server" 
    CssClass="ValidationMessage" 
    ShowMessageBox="True" ShowSummary="False" /> 

и на стороне сервера:

protected void cvMemberNum_Validate(object source, ServerValidateEventArgs args) 
{ 
    try 
    { 
     args.IsValid = (!CampaignRegistration.IsMemberRegistered(args.Value)); 
    } 
    catch 
    { 
     args.IsValid = false; 
    } 
} 

Моя проблема заключается в следующем: ValidationSummary никогда не показывает сообщение от CustomValidator. Этот вопрос задавали в нескольких местах, но я не нашел удовлетворительного ответа.

ответ

10

Попробуйте использовать свойство ValidationGroup на всех ваших валидаторах и ValidationSummary.

EDIT: "!" Другая возможность может быть Validation Server Code

args.IsValid = (!CampaignRegistration.IsMemberRegistered(args.Value)); 

если возвращается ложь, делает его истинным и, следовательно, делает его действительным. Я думаю, вы должны избавиться от "!" следующим образом:

args.IsValid = CampaignRegistration.IsMemberRegistered(args.Value); 

UPDATE: для того, чтобы ValidationSummary отображать персонализированное сообщение валидатор в MessageBox, вам нужно иметь ClientValidationFunction код. Если вам нужно отобразить только сводку без всплывающего окна, это не требуется.

<asp:CustomValidator ID="cvMemberNum" runat="server" 
    CssClass="ValidationMessage" Display="Dynamic" 
    ControlToValidate="txtMemberNum" ValidateEmptyText="false" 
    OnServerValidate="cvMemberNum_Validate" 
    ClientValidationFunction = "ClientValidate" 
    ErrorMessage="This membership number is already registered">*</asp:CustomValidator> 
    //JavaScript Code. 
    function ClientValidate(source, args) 
    {   
     args.IsValid = false; //you need to add validation logic here 
    } 

БОЛЬШЕ: Если вы не хотите, чтобы сделать валидацию на стороне клиента, попробуйте этот трюк, чтобы показать предупреждение. Сделать это изменение вашего CustomValidator метода ServerValidate:

protected void cvMemberNum_Validate(object source, ServerValidateEventArgs args) 
{ 
    bool isValid = true; 
    try 
    { 
     isValid = (!CampaignRegistration.IsMemberRegistered(args.Value)); 
    } 
    catch 
    { 
     isValid = false; 
    } 
    args.IsValid = isValid; 

    if(!isValid) 
    { 
     if(!Page.IsClientScriptBlockRegistered("CustomValidation")) 
     Page.RegisterClientScriptBlock("CustomValidation", "<script>alert('This membership number is already registered');</script>"); 

    } 

} 
+0

Я уверен, что это не проблема. Однако я попробую это и отчитаю. –

+0

Я обновил свой пост после наблюдения. Пожалуйста подтвердите. –

+0

Код, который вы выделили, на самом деле хорошо. Проверка не выполняется, если пользователь уже зарегистрирован. Эта часть работает. Случается, что рядом с текстовым полем появляется «*», но ValidationSummary не отображает сообщение. –

1

Вы должны написать свойство

ValidationGroup="ValidationSummary1"

на каждом валидатора в вашем случае.

Также проверьте, если ваша страница имеет

AutoEventWireup="true" 
+0

Пользовательский валидатор фактически проверяет и выполняет код на стороне сервера. Когда он недействителен, он показывает свой текст («*») рядом с текстовым полем. Тем не менее, ValidationSummary показывает другие сообщения, но не из CustomValidator. –

+0

Просто попробуйте две инструкции и скажите мне. Потому что у меня абсолютно такой же случай, и сообщение с пользовательского валидатора появляется в validationsummary – DaDa

+0

Спасибо за ваш ответ DaDa. Может быть, я должен уточнить, что ValidationSummary показывает ошибку из CustomValidator ЕСЛИ я устанавливаю ShowSummary = "true". Проблема в том, когда я хочу показать сообщение. –

7

Опция ShowMessageBox является полностью на стороне клиента, поэтому он будет оценивать только если вы установили ClientValidationFunction на CustomValidator.

Вы также можете подделать его, зарегистрировав скрипт, который делает предупреждение, поэтому, когда вы вернетесь с проверки сервера, он предложит сообщение об ошибке. Это может быть либо зарегистрировано в методе ServerValidate (за @Jose Basilio), или вы можете вызвать следующий метод во время события PreRender зарегистрировать всплывающее окно со всеми недействительными валидаторами на странице:

/// <summary> 
    /// Registers a script to display error messages from server-side validation as the specified <see cref="UserControl"/> or <see cref="Page"/> loads from a postback. 
    /// </summary> 
    /// <remarks> 
    /// Must be called in the PreRender if used to validate against the Text property of DNNTextEditor controls, otherwise Text will not be populated. 
    /// Must set the ErrorMessage manually if using a resourcekey, otherwise the resourcekey will not have overridden the ErrorMessage property. 
    /// </remarks> 
    /// <param name="ctrl">The <see cref="UserControl"/> or <see cref="Page"/> which is being posted back.</param> 
    /// <param name="validationGroup">The validation group against which to validate.</param> 
    public static void RegisterServerValidationMessageScript(TemplateControl ctrl, string validationGroup) 
    { 
     if (ctrl != null && ctrl.Page.IsPostBack) 
     { 
      ctrl.Page.Validate(validationGroup); 
      if (!ctrl.Page.IsValid) 
      { 
       StringBuilder errorMessage = new StringBuilder("<script language='javascript'>alert('"); 
       for (int i = 0; i < ctrl.Page.Validators.Count; i++) 
       { 
        IValidator validator = ctrl.Page.Validators[i]; 
        if (!validator.IsValid) 
        { 
         errorMessage.Append("- " + validator.ErrorMessage); 
         if (i < ctrl.Page.Validators.Count - 1) 
         { 
          errorMessage.Append(@"\r\n"); 
         } 
        } 
       } 

       errorMessage.Append("');</script>"); 
       ctrl.Page.ClientScript.RegisterStartupScript(typeof(IValidator), "validationAlert", errorMessage.ToString(), false); 
      } 
     } 
    } 
+0

Спасибо МНОГО! Работает как шарм! –

+0

проблема только в настоящий момент, мне не разрешено создавать пользовательские js. –

1

Это работает для меня:

<asp:CustomValidator runat="server" ID="cv" 
ClientValidationFunction="ValidateFunction" 
ErrorMessage="Default error 
message">*</asp:CustomValidator> 

<script type="text/javascript"> 
function ValidateFunction(sender, args) 
{ 

var msg =''; 
var formValid = true; 

[various checks setting msg and formValid] 

if (msg.length > 0) { sender.errormessage = msg; } 
args.IsValid = formValid; 

} 
</script> 
5

У меня была такая же проблема. ValidationSummary не показывал ErrorMessage из CustomValidator, когда ServerValidate указал на ошибку проверки.Поскольку по умолчанию (как показала моя маленькая обратная инженерия) сводка валидации визуализируется на стороне клиента при обратной передаче, я просто добавил скрипт, который проверяет все валидаторы на завершение загрузки документа/async и запускает сводку проверки достоверности для неудачных групп проверки:

$(document).ready(function() { 
    var displayAlert = function() { 
     if (typeof Page_Validators == 'undefined') return; 

     var groups = []; 
     for (i = 0; i < Page_Validators.length; i++) 
      if (!Page_Validators[i].isvalid) { 
       if (!groups[Page_Validators[i].validationGroup]) { 
        ValidationSummaryOnSubmit(Page_Validators[i].validationGroup); 
        groups[Page_Validators[i].validationGroup] = true; 
       } 
      } 
    }; 

    displayAlert(); 

    Sys.WebForms.PageRequestManager.getInstance().add_endRequest(
        function() { 
         displayAlert(); 
        }); 
} 
); 

В моем сценарии у меня были вложенные элементы управления пользователя с помощью валидаторов, панели обновления и сводки проверки на родительской странице.

More details here.

1

Я нашел обходной путь для того, когда Javascript отключен и ValidationSummary не показывает errorMessage свойства CustomValidator. Это необходимо, так как сценарий или предупреждения для инъекций, как описано выше, не будут работать.

Добавить новый элемент управления Validator, назовем его CustomValidatorProxy, установите его свойство ControlToValidate в любое из элементов управления формы и EnableClientScript=false.

В обработчик события ServerValidate выполнить пользовательскую проверку, и если проверка не пройдена установить IsValid свойства CustomValidator и CustomValidatorProxy к ложным и аналогично установленным как ErrorMessage свойств.

Если подтверждена проверка в ServerValidate, убедитесь, что для свойства IsValid значения CustomValidatorProxy установлено значение true.

При условии, что CustomValidatorProxy находится перед CustomValidator в ValidatorCollection страницы, то обработчик ServerValidate будет переопределить значение IsValid свойства, что CustomValidatorProxy бы вернулись Проверив значение ControlToValidate и ваш ErrorMessage от вашего CustomValidator будет отображаться в ValidationSummary ,

+2

Что вы делаете, было бы более читаемым, если бы был показан код –

1

bduke's RegisterServerValidationMessageScript «фальсифицирует», но это не так. Это действительно исправляет проблему. Каждое пространство имен Utility нуждается в этой функции где-то.