Generating a Schema from a DLL or Executable

The XSD tool also knows how to generate a an XSD from compiled types in a DLL or executable file. When generating a schema, xsd makes certain assumptions about the XSD types of instance variables. For any given CLR type, xsd chooses an XSD type for the schema. Table 8-2 lists each XSD type and its corresponding common language runtime type. In the cases where more than one XSD type maps to a single CLR type, the bold one will be used.

Table 8-2. XSD-to-CLR type mappings

XSD type

CLR type

xs:hexBinary

xs:base64Binary

System.Byte[ ]

xs:Boolean

System.Boolean

xs:byte

System.SByte

xs:normalizedString

xs:ENTITY

xs:ID

xs:IDREF

xs:language

xs:Name

xs:NCName

xs:NMTOKEN

xs:NOTATION

xs:string

xs:token

System.String

xs:date

xs:gMonthDay

xs:gDay

xs:gYear

xs:gYearMonth

xs:month

xs:time

xs:timePeriod

System.DateTime

xs:decimal

xs:integer

xs:negativeInteger

xs:nonNegativeInteger

xs:nonPositiveInteger

xs:positiveInteger

System.Decimal

xs:double

System.Double

xs:ENTITIES

xs:IDREFS

xs:NMTOKENS

System.String[ ]

xs:float

System.Single

xs:int

System.Int32

xs:long

System.Int64

xs:QName

System.Xml.XmlQualifiedName

xs:short

System.Int16

xs:unsignedByte

System.Byte

xs:unsignedInt

System.UInt32

xs:unsignedLong

System.UInt64

xs:unsignedShort

System.UInt16

xs:anyURI

System.Uri

xs:hexBinary

xs:base64Binary

System.Byte[ ]

xs:Boolean

System.Boolean

Angus Hardware might have a class structure for product listings, such as is shown in Example 8-4. This code can be compiled into the library Product.dll.

Example 8-4. Product type in C#
using System;

public class Address {
  public string [ ] Street;
  public string City;
  public string State;
  public string Zip;
}

public class Manufacturer {
  public string Name;
  public Address [ ] Addresses;
}

public class Product {
  public string Name;
  public string ProductCode;
  public Manufacturer Manufacturer;
  public DateTime DateIntroduced;
  public decimal UnitCost;
}

When you run the command xsd Product.dll, you get the generated XSD shown in Example 8-5.

Example 8-5. Generated XML Schema for Product.dll
<?xml version="1.0" encoding="utf-8"?>
<xs:schema elementFormDefault="qualified" xmlns:xs="http://www.w3.org/2001/XMLSchema">
  <xs:element name="Address" nillable="true" type="Address" />
  <xs:complexType name="Address">
    <xs:sequence>
      <xs:element minOccurs="0" maxOccurs="1" name="Street" type="ArrayOfString" />
      <xs:element minOccurs="0" maxOccurs="1" name="City" type="xs:string" />
      <xs:element minOccurs="0" maxOccurs="1" name="State" type="xs:string" />
      <xs:element minOccurs="0" maxOccurs="1" name="Zip" type="xs:string" />
    </xs:sequence>
  </xs:complexType>
  <xs:complexType name="ArrayOfString">
    <xs:sequence>
      <xs:element minOccurs="0" maxOccurs="unbounded" name="string" nillable="true" 
type="xs:string" />
    </xs:sequence>
  </xs:complexType>
  <xs:element name="Manufacturer" nillable="true" type="Manufacturer" />
  <xs:complexType name="Manufacturer">
    <xs:sequence>
      <xs:element minOccurs="0" maxOccurs="1" name="Name" type="xs:string" />
      <xs:element minOccurs="0" maxOccurs="1" name="Addresses" type="ArrayOfAddress" />
    </xs:sequence>
  </xs:complexType>
  <xs:complexType name="ArrayOfAddress">
    <xs:sequence>
      <xs:element minOccurs="0" maxOccurs="unbounded" name="Address" nillable="true" 
type="Address" />
    </xs:sequence>
  </xs:complexType>
  <xs:element name="Product" nillable="true" type="Product" />
  <xs:complexType name="Product">
    <xs:sequence>
      <xs:element minOccurs="0" maxOccurs="1" name="Name" type="xs:string" />
      <xs:element minOccurs="0" maxOccurs="1" name="ProductCode" type="xs:string" />
      <xs:element minOccurs="0" maxOccurs="1" name="Manufacturer" type="Manufacturer" />
      <xs:element minOccurs="1" maxOccurs="1" name="DateIntroduced" type="xs:dateTime" />
      <xs:element minOccurs="1" maxOccurs="1" name="UnitCost" type="xs:decimal" />
    </xs:sequence>
  </xs:complexType>
</xs:schema>

Like the XSD generated for an XML instance, a few assumptions are made. For example, although you know from your previous usage that an Address element can only have up to three Street elements, the XSD does nothing to constrain the number; it’s created a type called ArrayOfString, whose content is an unbounded number of String elements.

You can affect the generated XSD with the judicious use of C# attributes. There are a number of attributes that affect XSD generation, located in the System.Xml.Serialization namespace; a small subset is listed in Table 8-3. Refer to the .NET Framework SDK documentation section entitled “Attributes That Control XML Serialization” for the complete list.

Table 8-3. Attributes affecting XSD generation

Attribute name

Purpose

Properties

XmlRootAttribute

Identifies the class, structure, enumeration, or interface as the root element of an XML instance

DataType
ElementName
IsNullable
Namespace
XmlElementAttribute

Identifies the class, structure, enumeration, or interface as an element in an XML instance

DataType
ElementName
Form
IsNullable
Namespace
Type
XmlAttributeAttribute

Identifies the class, structure, enumeration, or interface as an attribute in an XML instance

DataType
AttributeName
Form
Namespace
Type

With this information, you can alter the original source code to force the generated code to appear in a form more to your liking. To take just the Product type from Product.cs, you can alter xsd’s output significantly by marking some of its fields as attributes:

public class Product {
  [XmlAttributeAttribute(AttributeName="name")]
  public string Name;
  [XmlAttributeAttribute(AttributeName="productCode")]
  public string ProductCode;
  [XmlElementAttribute(IsNullable=false, ElementName="manufacturer")]
  public Manufacturer Manufacturer;
  [XmlAttributeAttribute(AttributeName="dateIntroduced")]
  public DateTime DateIntroduced;
  [XmlAttributeAttribute(AttributeName="unitCost")]
  public decimal UnitCost;
}

The corresponding element in the generated schema0.xsd now looks like this:

<xs:element name="product" type="Product" />
<xs:complexType name="Product">
  <xs:sequence>
    <xs:element minOccurs="0" maxOccurs="1" name="manufacturer" type="Manufacturer" />
  </xs:sequence>
  <xs:attribute name="name" type="xs:string" />
  <xs:attribute name="productCode" type="xs:string" />
  <xs:attribute name="dateIntroduced" type="xs:dateTime" />
  <xs:attribute name="unitCost" type="xs:decimal" />
</xs:complexType>

There’s much more to learn about serialization, and I’ll cover the topic in much more depth in Chapter 9.

..................Content has been hidden....................

You can't read the all page of ebook, please click here login for view all page.
Reset
3.14.70.203