ShowTable of Contents
Use your own validation tests
Create a Expression Validator and use JavaScript for comparing stuff. The value of the fields is stored in the variable "value".
value == sessionScope.get("comparevalue");
Here the validator is true if the value of the fields is the same than the value of "comparevalue" in the sessionScope.
Note: if you have a radio button group, you need the validator only in the first field of the group.
Notes for the expression validator
There are several issues with the expression validator you should know:
1.) In a multiline field, the value variable only returns the first line of the field's data. Use getComponent("fieldname").getSubmittedValue() instead.
2.) If you are using \n as multiline separator, the value may contain a \r, too. Use @ReplaceSubstring(getComponent("fieldname").getSubmittedValue(), "\r", "") before splitting the value into an array.
3.) Depending if the field the validator runs on currently has the focus, you may get the value as string or array. Use something like this to make sure you get an array when using \n as multiline separator:
var value1 = @ReplaceSubstring(getComponent("fieldname").getSubmittedValue(), "r", "");
value1 = (typeof value1 == "string" ? value1.split("n") : value1);
Useful regular expressions for the constraint validator
Email address
\b[a-zA-Z0-9._%-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,7}\b
Thanks, Ross S. Swick
Check if one date is greater as the other
var start = value;
var end = getComponent("D_END").getValue();
if (!start) return false;
if (!end) return false;
var dStart:NotesDateTime = session.createDateTime(start);
var dEnd:NotesDateTime = session.createDateTime(end);
return (dEnd.timeDifference(dStart) > 0 )
Check if a value is a mail address
Use a constraints validator with this regex:
^s*[w-+_]+(.[w-+_]+)*@[w-+_]+.[w-+_]+(.[w-+_]+)*s*$
Run validation only on a button click
Standard validators are running on each (full / partial) update, which can be very annoying.
IBM is aware of that problem in 851 and is working on a general solution.
In the meantime, Tommy Valand developed a good workaround. Click here to see Tommy's solution
Update: as of Domino 8.5.2, validators can be enabled and disabled with SSJS.
Display a custom text on a message control
Normally, a message control is bound to a field to display the error messages of it's validators.
Tommy Valand found a solution for sending custom text to a message control, so that you can display all kind of information in such a control:
function addFacesMessage(message, component){
try {
if(typeof component === 'string' ){
component = getComponent(component);
}
var clientId = null;
if (component) {
clientId = component.getClientId(facesContext);
}
facesContext.addMessage(clientId,
new javax.faces.application.FacesMessage(message));
} catch(e){ }
}
The second parameter is the component id of the field (!) to which a message control is bound, or the field control itself.
If the parameter 'component' is null or missing, then the message is displayed in the global scope, that means in app xp:messages (note the "s") controls.
Thanks to Tommy Valand
Displaying validation messages for multiple controls in one message component
Create a xp:message control like this:
<xp:text styleClass="xspMessage"
escape="false" rendered="#{javascript:return ( this.value );}">
<xp:this.value>
<![CDATA[#{javascript:return getFacesMessages( [ 'field1', 'field2' ] ).join( '<br />' );}]]>
</xp:this.value>
</xp:text>
Note that this message controls only renderes if it has something to display.
Then create a SJSS function like this:
function getFacesMessages( components ){
try {
// ensure the parameter is an array
if (typeof components !== 'array') { components = [components]; }
var clientId, component, messages = [], msgIterator;
for (var i = 0; i < components.length; i++ ) {
component = components[i];
if (typeof component === 'string') {
clientId = getClientId(component);
} else {
clientId = component.getClientId(facesContext);
}
msgIterator = facesContext.getMessages(clientId);
if (!msgIterator) {continue;}
while (msgIterator.hasNext()) {
messages.push(msgIterator.next().getSummary());
}
}
return messages;
} catch( e ){ }
}
Another goodie found by Tommy Valand
Validating a Read Only field
By default a field set to be read only cannot be required, but with a little help from my friend Chris Toohey you can add a div tag with a style to make it work like shown below:
<div style="display: none;">
<xp:inputText
id="rptToName1"
value="#{xp_record.RptToName}"
required="#{javascript:return submittedBy( 'questionairreBtn1' )}" styleClass="tableCellLabelLeftNormal">
<xp:this.validators>
<xp:validateRequired message="Who this position reports to is required"></xp:validateRequired>
</xp:this.validators>
</xp:inputText>
</div>
The field property should have read only deselected and the visible property set to true, then you create a visible computed field that uses the value of the now hidden control which is required and magically it works like a charm. I have also submitted this idea - xPages Required Property - on IdeaJam and the developerworks wiki
Dwain A Wuerfel
Custom Control For Enhanced Validation Messages
Tommy Valand created a very nice custom control which displays validation messages with links that point to the appropriate field. And if the field is inside a Dojo Tab Container, the correct tab is selected, too.
Enhanced Validation Message Control