Saxon allows assertions on simple types to be defined. The mechanism is to define an xs:assert
element as a child of the xs:restriction
child of the xs:simpleType
element (that is, it acts
as an additional facet). The type must
be an atomic type. The value of the test
attribute of xs:assert
is an XPath expression. .
The expression is evaluated with the value being validated supplied as the value of the variable $value
.
This will be an instance of the
base type: for example, if you are restricting from xs:string
, it will be a string; if you are
restricting from xs:date
, it will be an xs:date
; if you are validating a list of integers,
then $value
will be a sequence of integers.
If the effective boolean value of the expression is true, the value is valid. If the effective boolean value is
false, or if a dynamic error occurs while evaluating the expression, the value is invalid. Currently no diagnostics
are produced to indicate why the value is deemed invalid, other than a statement that the xs:assert
facet is violated. You can supply a message in a saxon:message
attribute.
The XPath expression has no access to any part of the document being validated, other than the atomic value of the actual element or attribute node. So the validation cannot be context-sensitive.
The XPath expression may make calls on Java extension functions in the normal way: see Writing extension functions (Java). This facility has not been tested on .NET but there is no intrinsic reason why it should not work. Allowing call-out to procedural programming languages means that you can perform arbitrary procedural validation of element and attribute values. Take care to disable use of extension functions if validating against a schema that is untrusted.
The following example validates that a date is in the past:
<xs:element name="date">
<xs:simpleType>
<xs:restriction base="xs:date">
<xs:assert test="$value lt current-date()"/>
</xs:restriction>
</xs:simpleType>
</xs:element>
The following example validates that a string is a legal XPath expression. This relies on the fact that a failure evaluating the assertion is treated as "false":
<xs:element name="xpath">
<xs:simpleType>
<xs:restriction base="xs:string">
<xs:assert test="exists(saxon:expression($value))" xmlns:saxon="http://saxon.sf.net/"/>
</xs:restriction>
</xs:simpleType>
</xs:element>
Note how the in-scope namespaces for the XPath expression are taken from the in-scope namespaces of the
containing xs:assert
element.