joestelmach.com

Error Styling in Struts

In light of my last post, I'd like to discuss a new facility available in Struts to apply error styling to your form fields. Since Struts 1.2.5, all form elements now have the optional errorStyle, errorStyleClass, and errorStyleId attributes. These are meant as a means to define the styling of particular form elements that have failed validation (which I think is a pretty good idea.) Imagine the following form definition:

<html:form action="/processForm">
  User Name
  <html:text property="userName">
  Password
  <html:text property="password">
  <html:submit>
<html:form/>

Now, lets suppose we wanted to place a 2 pixel red border around each text field that fails validation. This can be accomplished by adding the desired error style attribute to the text fields, and defining the corresponding style. In our example here, we'll use the errorStyleClass attribute, which means that the framework will apply a class="fieldError" attribute to the rendered input field. Alternatively, we could use the errorStyleId and errorStyle attributes, which will apply the id="fieldError" and style="given style rules" attributes respectively.

<html:form action="/processForm">
  User Name
  <html:text property="userName" errorStyleClass="fieldError">
  Password
  <html:text property="password" errorStyleClass="fieldError">
  <html:submit>
<html:form/>
And in your css file:
.fieldError {
  border:2px solid red;	
}

Now, lets suppose the password field has some crazy requirement that is has to be between 4 and 5 characters, the first two characters must be digits, the third character must be a 'special' character, and the remaining characters can't be digits. (I know, its a bit of an exaggerated example.) The user has forgotten all of these rules and enters an invalid password. The following html will be rendered:

<form action="/processForm.do">
  User Name
  <input type="text" name="userName">
  Password
  <input type="text" name="password" class="fieldError">
  <input type="submit">
<form/>

Thus applying the fieldError style rule to the password field and drawing a 2px border around it. Simple right? Yes its simple. It's too freaking simple! I'd like to vent a bit about the following frustrations I have with this:

- The error style attribute has to be applied to all individual fields

At first, I thought this must be a mistake. I'm sure the following question has crossed at least some of your minds upon reading this post: You mean I have to add errorStyleClass="fieldError" to ALL of my form elements? Yes, you do. And yes, ITS RIDICULOUS! I just want all failed validations to include the class="fieldError" attribute when rendered. Is that so much to ask? Why can't I apply errorStyleClass to the top level form element and have ALL the fields on the form inherit this attribute (like the disable attribute?)

A possible solution to this might be to add a custom implementation of the struts html tags that will apply this class for you. I personally don't think that this is a good idea, but it would work.

- The errorStyleClass and styleClass attributes are mutually exclusive

That's right boys and girls. If you apply a style to your form element using the styleClass attribute, they will be forgotten in favor of your errorStyleClass definition upon failed validation. COME ON! There is no reason why the struts developers couldn't have simply added the class definitions given in the errorStyleClass attribute to the list of classes given in the styleClass attribute. This must be a product of 'design by committee'. Because of this obscure behavior, we now have to use unique error style class names for each element that already defines a style class. Not to mention duplicating the style rules across both class definitions.

If you take the above approach to alleviate yourself from adding the errorStyleClass attribute to every form element, it may also help in this situation. Your custom implementation could check if a style class or list of style classes was given, and simply add the error style class to the list. Again, this is possible and will work, but I'd hate to be the one to maintain it and explain it to new developers.

Comments
blog comments powered by Disqus