3

I have this in an ascx file:

<asp:textbox ID="AddHourlyRate" runat="server" width="55px" />
<asp:RegularExpressionValidator  ID="AddHourlyRateRegexValidator"
    ErrorMessage="Please enter a valid charge rate (whole number only)" 
    ValidationExpression="^\$?[0-9]+(\.[0]{2})?$" ControlToValidate="AddHourlyRate" 
    Display="Dynamic" runat="server" />

How can I reuse the ValidationExpression in other asp:RegularExpressionValidators without having to copy-paste the regex expression? I am new to asp.NET.

2
  • Do you want to validate another control? The Validator Controls are generally designed to validate one control per validator. You can copy the tag wholesale, paste it in next to the other control you want to validate give it a new Id, and just change the ControlToValidate to point at that other control you want to validate. Commented May 15, 2012 at 22:32
  • @dash Cheers for the response. Yeah, they will be validating different controls, but it's the expression (^\$?[0-9]+(\.[0]{2})?$) that I don't want to copy - I'd rather only this written in one place. Commented May 15, 2012 at 22:33

5 Answers 5

6

Make a class with const string for each regular expression, I use that solution for your exact problem. That class is in a common assembly that is shared among number of projects. And you probably use regular expression on some other places not just validator controls.

Something like this :

public class RegularExpressions
{
  public const string TelephoneValidation = @"^[0-9 ]+$";
  public const string IntegerValidation = @"^\d+$";
}

You can then set validator expression from code behind :

validator.ValidationExpression = RegularExpressions.IntegerValidation;

or in markup :

<%@ Import Namespace="RegularExpression.Class.Namespace" %>  
.
.
.  
<asp:RegularExpressionValidator  ID="AddHourlyRateRegexValidator"
        ErrorMessage="Please enter a valid charge rate (whole number only)" 
        ValidationExpression="<%# RegularExpressions.IntegerValidation %>" ControlToValidate="AddHourlyRate" 
        Display="Dynamic" runat="server" />

Of course write proper namespace in import directive.

Sign up to request clarification or add additional context in comments.

3 Comments

This is my favourite so far. How would I then pull those statics into the ascx file?
Yes, I like this answer too - simple and easy. +1.
Cannot currently edit only one character in answer. Will accept after <%= RegularExpressions.IntegerValidation %> is changed to <%# RegularExpressions.IntegerValidation %> (note opening asp tag - Response.Write -> binding style).
2

You can re-use your regex expression(extract it to the constant and set it in the Page_Load function for all required regex validators)

public const string WholeNumbersValidation = @"^\$?[0-9]+(\.[0]{2})?$";

protected void Page_Load(object sender, EventArgs e)
{
   AddHourlyRateRegexValidator.ValidationExpression = WholeNumbersValidation;
   AddHourlyRateRegexValidator.ErrorMessage= "Please enter a valid charge rate (whole number only)";
   validatorIdForNextField.ValidationExpression = WholeNumbersValidation;
   validatorIdForNextField.ErrorMessage= "Error message text 2";

}

, but you couldn't re-use one regex ASP.NET validator for a couple of fields, because do not accept more than one ID in the ControlToValidate property.

You could write your own client-side validation function that validates the textboxes all at once upon submit to resolve this issue and you should also have to write a validation function for the server side as well.

Comments

1

Have you considered adding the expression as a project-level setting, and then setting the "ValidationExpression" in code-behind?

4 Comments

I did consider this, but thought it was conceptually a little confusing for the validators to be built every time the page loads.
I'm not sure I understand. What is the difference between the validator being added in the aspx page and and code-behind page?
Not sure. I come from MVC - I guess I see the code-behind as the controller, directing user-input rather than static validation rules. I'd also rather the validation wasn't in the ascx "view", but that seems to be the standard.
Ah OK. Well my answer is pretty much like @AntonioBakula 's answer. But his is more in-depth. I would choose his.
1

You will have to use multiple validators, but you should be able to store the expression as a value in the web.config file, then access it via inline C#.

In web.config:

<appSettings>
  <add key="myRegExString" value="^\$?[0-9]+(\.[0]{2})?$" />
</appSettings>

In YourPage.aspx:

<asp:textbox ID="AddHourlyRate" runat="server" width="55px" />
<asp:RegularExpressionValidator  ID="AddHourlyRateRegexValidator"
    ErrorMessage="Please enter a valid charge rate (whole number only)" 
    ValidationExpression="<% = ConfigurationSettings.AppSettings["myRegExString"]%>" ControlToValidate="AddHourlyRate" 
    Display="Dynamic" runat="server" />

1 Comment

Thanks for the response, but I'd rather not have the regex in the config file.
1

You can certainly do something like the following:

private RegularExpressionValidator GetValidatorControl(string controlToValidate, string errorMessage)
{

    RegularExpressionValidator validator = new RegularExpressionValidator();
    validator.ID = String.Format("{0}RegExValidator", controlToValidate);
    validator.ValidationExpression = @"^\$?[0-9]+(\.[0]{2})?$";
    validator.ControlToValidate = controlToValidate;
    validator.ErrorMessage = errorMessage;
    return validator;

}

And, in the Page_Load event or similar, you can call it this way:

Page.Controls.AddAt(Page.Controls.IndexOf(AddHourlyRate) + 1, GetValidatorControl(control.ID, "my validation message"));

This will add the validator control to your page and your expression will only be defined here (it can be placed into another class as a static method and shared throughout the project).

You could also use the method in this Stack Overflow answer to get all of the RegEx validators on your page, and then set the ValidationExpression on each one. For example, if you wrap all of your controls in a Panel (with an ID of RootPanel in my example) or similar container control then you could just:

IEnumerable<Control> validators = RootPanel.FlattenChildren();

IEnumerator<Control> enumerator = validators.GetEnumerator();

while (enumerator.MoveNext() == true)
{
    if (enumerator.Current is RegularExpressionValidator) //Only interested in RegularExpressionValidators. You could even filter this further by naming them consistently and checking for a fragment of the ID here.
    {
        ((RegularExpressionValidator)enumerator.Current).ValidationExpression = @"^\$?[0-9]+(\.[0]{2})?$"; //Load from config if necessary!
    }
}

To use the FlattenChildren method, place it into a public static class somewhere inside your project and reference it with the appropriate using directives. See this article for extension methods in .Net.

No matter what happens, you'll need one RegularExpressionValidator per control. Your other option, is, of course, to validate these manually yourself in javascript or on PostBack.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.