Is it possible to make XSD conditional on element and attribute values, not names? - xsd

Is it possible to write conditional based xsd. I have list of countries defined in my xsd, If user choose country as UNITED STATES, xsd should allow user to select the states which belong to above choosen country, Else it should show validation error. Below example, perfectly allow user to select country and state for the below list, But it does not perform any validations agaist country. If you have any suggestions to write choice based xsd, Please let me know. Please note that, I have tried <xs:choice>, it does not work for this scenario.
<xs:complexType name="header-type">
<xs:sequence>
<xs:element name="country" type="country-type" />
<xs:element name="states" type="state-type" />
</xs:complextType>
<xs:simpleType name="country-type">
<xs:restriction base="xs:string">
<xs:enumeration value="UNITEDSTATES"></xs:enumeration>
<xs:enumeration value="AUS"></xs:enumeration>
</xs:restriction>
</xs:simpleType>
<xs:simpleType name="state-type">
<xs:restriction base="xs:string">
<xs:enumeration value="California"></xs:enumeration>
<xs:enumeration value="Sydney"></xs:enumeration>
<xs:enumeration value="Texas"></xs:enumeration>
</xs:simpleType>

Related

xsd - not allowing values defined in the enumeration list

I would like to enforce a rule on the attribute which should not allow a value defined in enumeration values associated with another attribute.
Here is my sample schema.
<xs:complexType name="component">
<xs:attribute name="type" type="componentMainType"/>
<xs:attribute name="category" type="forbiddenCategoryTypes" use="optional"/>
</xs:complexType>
<xs:simpleType name="forbiddenCategoryTypes">
<xs:restriction base="xs:string">
**<xs:pattern value="not in forbiddenCategoryTypes"/>**
</xs:restriction>
</xs:simpleType>
<xs:simpleType name="componentMainType">
<xs:restriction base="xs:string">
<xs:enumeration value="Component1"/>
<xs:enumeration value="Component2"/>
<xs:enumeration value="Component3"/>
<xs:enumeration value="Component4"/>
<xs:enumeration value="Component5"/>
</xs:restriction>
</xs:simpleType>
In my opinion not possible, pattern only takes a regex. I could not find any other relevant restriction.
I would suggest to change approach to regex with values (I know it is not optimal solution).

It's possible to use multiple value in single enumeration tag?

I'm using XSD validation in WEB API project.
now i'm using following method for check string value.
<xs:simpleType name="CoverageTierPattern">
<xs:restriction base="xs:string">
<xs:enumeration value="EE"/>
<xs:enumeration value="ES"/>
<xs:enumeration value="EC"/>
<xs:enumeration value="Fam"/>
<xs:enumeration value="WO"/>
<xs:enumeration value="WP"/>
<xs:enumeration value="NE"/>
<xs:enumeration value="RC"/>
</xs:restriction>
</xs:simpleType>
this list value must be added more in future.
So i need to know it's possible to use values in single enumeration element
like
<xs:enumeration value="EE|ES|EC|..."/>
other wise if any other method present plz tell me.
You can use pattern element instead of enumeration like this:
<xs:pattern value="EE|ES|EC|..."/>
Full example from here in the middle of the page.
<xs:element name="gender">
<xs:simpleType>
<xs:restriction base="xs:string">
<xs:pattern value="male|female"/>
</xs:restriction>
</xs:simpleType>
</xs:element>

SimpleType - Aggregation or Abstraction

I face a weird problem. I'm supposed to use a number of third party XSDs for a webservice. My framework of choice is Apache CXF, and I generate code using its Maven plugin. So far so good, everything works, neither generation nor webservice itself is problematic.
But, since the authors of the XSDs are weird and I cannot change them myself, I face a problem: They use a lot of basically duplicated SimpleType-definitions. They all bear their own name, but do the same thing.
Example:
<xs:simpleType name="VehicleFittedWithEcoInnovInd">
<xs:restriction base="xs:string">
<xs:maxLength value="1"/>
<xs:enumeration value="Y"/>
<xs:enumeration value="N"/>
</xs:restriction>
</xs:simpleType>
<xs:simpleType name="TypeApprTranspDangerGoodsInd">
<xs:restriction base="xs:string">
<xs:maxLength value="1"/>
<xs:enumeration value="Y"/>
<xs:enumeration value="N"/>
</xs:restriction>
</xs:simpleType>
And many more (Numbers, Stringdefinitions etc etc).
So the question is, is it possible, through a jaxb-plugin or similar, to aggregate these SimpleTypes into one, or at least generate an abstract class structure, so that the amount of irrelevant duplicate code is reduced?

How to allow typed values to be empty with an XML schema?

I have some XML documents over which I have no control whatsoever. Their structure is well-defined, but it is described in a bunch of PDFs, which, despite being very exact, don't make automated validation very tractable. I'm trying to write a XML schema to make (most of) the rules in those PDFs executable.
All the elements are mandatory. But about half of them can be either empty or have simple typed content.
When defining datatypes for these elements, I defined two versions of each: a "normal" one, and another that can be empty. I did this by defining unions with an empty datatype:
<xs:simpleType name="empty">
<xs:restriction base="xs:string">
<xs:length value="0"/>
</xs:restriction>
</xs:simpleType>
<xs:simpleType name="codPostal">
<xs:restriction base="xs:string">
<xs:pattern value="^[0-9]{4}-[0-9]{3}$"/>
</xs:restriction>
</xs:simpleType>
<xs:simpleType name="opt_codPostal">
<xs:union memberTypes="empty codPostal"/>
</xs:simpleType>
Is there a less repetitive way of doing this?
You can use xs:nillable.
In XSD
<xs:simpleType name="codPostal">
<xs:restriction base="xs:string">
<xs:pattern value="^[0-9]{4}-[0-9]{3}$"/>
</xs:restriction>
</xs:simpleType>
<xs:element name="OptionalString" type="codPostal" nillable="true" />
In Document
<OptionalString xsi:nil="true"
xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" />
This is most useful for non-string types (e.g. datetime etc) as for strings you could just use zero length.
<OptionalString />
Unfortunately you need to specify the "nil" attribute on the document. As far as I know, the only non-intrusive way to do what you want is the union type approach that you've already chosen.

How to define xsd restrinction xs:enumeration to also accept empty element?

I have xsd schema that define Gender element that accepts only F or M value but I want it also to accept empty <Gender/> element. How to fix following schema?
...
<xs:simpleType name="Gender">
<xs:restriction base="xs:string">
<xs:enumeration value="M" />
<xs:enumeration value="F" />
</xs:restriction>
</xs:simpleType>
...
Have you tried adding:
<xs:enumeration value="" />
?
However, this is bad practice. If you want to represent this information in the instance documents, you should omit the <Gender> element altogether, rather than providing an empty one. Also, it's unclear what <Gender/> means - does this mean "no gender", or "unknown gender"? If it's one of those possibilities, perhaps you should add those to the eneration:
<xs:simpleType name="Gender">
<xs:restriction base="xs:string">
<xs:enumeration value="M" />
<xs:enumeration value="F" />
<xs:enumeration value="unknown" />
</xs:restriction>
</xs:simpleType>
You could use a pattern instead:
<xs:simpleType name="Gender">
<xs:restriction base="xs:string">
<xs:pattern value="(M|F)?"/>
</xs:restriction>
</xs:simpleType>

Resources