1
XSD element with nillable attributes changes name of element in generated XML
Question asked by Lee Carter - September 6 at 2:07 PM
Answered
I have a 3rd party XSD (cannot provide full XDS but will attempt to provide sensible snippets) that defines an element with the nillable attribute:
 
  <xs:element name="locationType" nillable="true">
    <xs:complexType>
      <xs:simpleContent msdata:ColumnName="locationType_Text" msdata:Ordinal="4">
        <xs:extension base="xs:string">
          <xs:attribute name="units" type="xs:string" use="required" />
          <xs:attribute name="datum" type="xs:string" />
          <xs:attribute name="zone" type="xs:string" />
          <xs:attribute name="north" type="xs:string" />
        </xs:extension>
      </xs:simpleContent>
    </xs:complexType>
  </xs:element>
This element is then used in other elements such as:
  <xs:element name="TopLevelElement">
    <xs:complexType>
      <xs:element name="LocationDefinition" minOccurs="0" maxOccurs="1">
        <xs:complexType>
          <xs:sequence>
            <xs:element ref="locationType" minOccurs="1" maxOccurs="1" />
          </xs:sequence>
        </xs:complexType>
      </xs:element>
    </xs:complexType>
  </xs:element>  
When XSD is processed by the Data Binder to produce C++ code, it appears to create both CLocationType and CLocationType_nillable classes and the relevant CSmartPtr<class> typedefs.
 
The class generated for LocationDefinition has get/set methods for LocationType but these methods only return/take a LocationType_nillable pointer.
 
When the XML string is generated for TopLevelElement where a LocationDefinition has been added, the XML looks something like:
 
<?xml version="1.0"?>
<TopLevelElement>
  <LocationDefinition>
    <locationType_nillable units="someunits" datum="somedatum" north="Grid">GPS</locationType_nillable>
  </LocationDefinition>
</TopLevelElement>
The above is not what I expected.  The locationType within the LocationDefinition should not have the "_nillable" in its element name.
 
I would have expected the LocationType class to have had a SetIsNil(bool) method and GetIsNil() method that returns a bool but it is only the LocationType_nillable class that has these.
 
The CLocationDefinition::SetLocationType(...) method will not take a CLocationType* as the parameter, only a CLocationType_nillable*
 
The only way I have found to make the XML acceptable to the 3rd party server receiving the XML is to override the name of the element when creating CLocationType_nillable object with CLocationType_nillable::CreateInstance("locationType") before passing it to CLocationDefinition::SetLocationType(...) but having to do this does not seem right to me.
 
Am I doing something wrong in the data binder or use of the generated C++ library?

2 Replies

Reply to Thread
0
Liquid Support Replied
September 11 at 11:55 AM
Employee Post
Hi,
Yes you are correct, the nillable generated class should use the element name "locationType". I have raised this as an issue to be fixed in the next point release.
 
Your workaround is also correct, the following works OK:
CTopLevelElementPtr elm = CTopLevelElement::CreateInstance();
CLocationDefinitionPtr def = CLocationDefinition::CreateInstance();
CLocationType_NillablePtr type = CLocationType_Nillable::CreateInstance("locationType");
type->SetUnits("test");
def->SetLocationType(type);
elm->SetLocationDefinition(def);
 
1
Liquid Support Replied
September 13 at 1:39 PM
Employee Post
This fix is now live and can be downloaded from:

Reply to Thread