Document-Centric .NET
The principle "program to an interface, not an implementation" helps control the complexity and enhance the flexibility of systems. XML interfaces are a natural extension of this principle that bring a number of new benefits in terms of flexibility, reusability, simplified code, and readiness for enterprise environments.
We will walk through a sample application to see how the .NET framework classes can work together in an application centered around an XML interface. This XML interface will be the hub of present and future requirements. Our application will produce a bar graph from a variety of data sources. Though this example is relatively trivial, similar approaches can solve larger and more complex problems.
The Schema
Our bar graph application will revolve around a schema written in the W3C XML Schema language. Specifying this schema will be one of the first and most important design steps. Stability is key and all the better if you can use a standardized schema for your application. However, keep in mind that there are W3C XML Schema features that are not directly compatible with .NET's XML-to-database and XML-to-object mapping tools.

For this application we'll use a custom schema: BarGraph.xsd. An instance document conforming to this schema looks like the following:
<BarGraph xmlns="http://example.org/bargraph">
<Bar>
<Title>Portland</Title>
<Value>32</Value>
</Bar>
<Bar>
<Title>Berlin</Title>
<Value>20</Value>
</Bar>
<Bar>
<Title>Pune</Title>
<Value>16</Value>
</Bar>
</BarGraph>
Taming the Winds: Input into our Application
We'll start by gathering input from a variety of sources. The following three examples will each produce the same result: an XmlReader containing bar graph XML. XmlReader is an abstract class that plays a similar role to other platforms' use of SAX, in that it can be used to pass the contents of a XML text file, a DOM tree, or a high-throughput dynamic data source.
GetXml() #1: REST web service
The most familiar benefit of XML interfaces is that they allow applications to span machine and platform boundaries. Techniques that are well described asREST can be an easy way to pull XML from a network resource.
We will use the XmlTextReader subclass of XmlReader, which can be used to read data from files or remote REST URLs.
public XmlReader GetXml() { string url = "http://somehost/graph.asmx?id=cities"; XmlReader graphReader = new XmlTextReader(url); return graphReader; }
GetXml() #2: Database
Another data source might be a database. Microsoft has placed XML at the center of its ADO.NET data access library with the DataSet, which is simultaneously a disconnected set of relational data and a XML document.
-
The first step to get the XML is to create a DataAdapter, which is a bridge between the database and the DataSet. Here we construct a SqlDataAdapter, a SQL Server specific DataAdapter, with a connection string and a SQL statement.
public XmlReader GetXml() { string sql = "SELECT * FROM [Category Sales for 1997]"; string conn = "Data Source=(local);Database=Northwind;" + "Integrated Security=SSPI;"; SqlDataAdapter da = new SqlDataAdapter(sql,conn); -
Next we create a new empty DataSet and fill it with data using the DataAdapter's Fill method.
DataSet ds = new DataSet(); da.Fill(ds); -
The default schema of the dataset does not match bar graph XML. We could use XSLT to transform it, but in some cases we can do this more efficiently by directly modifying the DataSet.
ds.DataSetName = "BarGraph"; ds.Namespace = "http://example.org/bargraph"; ds.Tables[0].TableName="Bar"; ds.Tables[0].Columns[0].ColumnName="Title"; ds.Tables[0].Columns[1].ColumnName="Value"; -
There are a number of ways to obtain the DataSet's XML, including the WriteXml and GetXml methods. Here we will use the XmlDataDocument class to expose the DataSet as a DOM object, and then create an XmlNodeReader, which is a XmlReader that reads the contents of a DOM object.
XmlDocument xmlDoc = new XmlDataDocument(ds); XmlReader graphReader = new XmlNodeReader(xmlDoc); return graphReader; }
GetXml() #3: User Form
The previous example showed how a DataSet object can be used as a bridge between a database and XML. The DataSet can also be used as a bridge between controls in a Windows form and XML. The complete source code for this example is at form2graph.zip.
-
In our form's constructor, we'll create a DataSet and give it a structure by reading in our BarGraph schema using the ReadXmlSchema method.
private DataSet ds; private DataGrid grid; public BarGraphForm() { InitializeComponent(); // Create a dataset based on the schema ds = new DataSet(); ds.ReadXmlSchema("BarGraph.xsd"); -
Then we'll bind the DataSet to a DataGrid control in our form. The DataGrid will automatically create columns that conform to the schema in the DataSet.
// Bind the dataset to a DataGrid control grid.SetDataBinding(ds,"Bar"); } -
Now when the form is displayed, the DataGrid will conform to the schema, and the user can add and edit data.
-
Once the user is finished, we will use the WriteXml method to extract the XML from the dataset.
public XmlReader GetXml() { Stream streamXml = new MemoryStream(); ds.WriteXml(streamXml); streamXml.Position = 0; XmlReader graphReader = new XmlTextReader(streamXml); return graphReader; }
Application Output
Each of the following examples will perform some action using an XmlReader containing bar graph XML. Naturally the choice of our input source is unimportant, since all the sources produce XmlReaders conforming to the same schema.
Pages: 1, 2 |