How to: Prepopulate XmlPreloadedResolver with a File Downloaded from URI Location


Use the XmlPreloadedResolver if you have to prepopulate a cache with content that is going to be referenced more than once. This topic shows how to use XmlPreloadedResolver to prepopulate the cache with a DTD file that is later referenced from an XML file. To get the content of the DTD file from a URI location, you must use an asynchronous Web request.

To configure a Silverlight Visual Studio project to run this example

  1. In Solution Explorer, add assembly references to System.Xml.Linq.dll, System.Xml.Utils.dll, and System.Net.dll.

  2. Modify your page.xaml file so that it includes the following TextBlock element:

    <TextBlock x:Name ="OutputTextBlock" Canvas.Top ="10" TextWrapping="Wrap"/>
  3. Create a DTD file, which you will load from a URI location. The DTD file that is used in this example has the following content:

    <!ENTITY entity 'Replacement text'>
  4. In the page.xaml source file for your application, add the following using statements (Imports in Visual Basic):

    using System.IO;
    using System.Xml.Linq;
    using System.Net;
    using System.Xml.Resolvers;
    using System.Xml;

To cache the DTD file using XmlPreloadedResolver

  1. Create the WebClient object, add the handler, and initiate the request. To request a resource as a stream, you must call an OpenReadAsync method overload. Also initialize the httpURI member variable. In the next step, the XmlPreloadedResolver maps a stream with preloaded data to this URI.

    WebClient wc = new WebClient();
    wc.OpenReadCompleted += wc_OpenReadCompleted;
    // Initialize httpURI member variable.
    httpURI = new Uri(uriString);
  2. Implement the wc_OpenReadCompleted callback function. This function does the following:

    1. Checks the Error propertyfor errors.

    2. If there are no errors, gets the data stream.

    3. Adds the stream with preloaded data to the XmlPreloadedResolver store and maps it to httpURI.

    4. Assigns the resolver to the XmlReaderSettings.

    5. Creates an XML string that references the DTD.

    6. Creates an XmlReader using the specified TextReader that contains the XML data and XmlReaderSettings objects.

    7. Creates a new XDocument and passes the XmlReader object to the Load method overload.

    private void wc_OpenReadCompleted(object sender, OpenReadCompletedEventArgs e)
        if (e.Error != null)
            OutputTextBlock.Text = e.Error.Message;
        using (Stream stream = e.Result)
            XmlPreloadedResolver resolver = new XmlPreloadedResolver();
            // Add the DTD into the XmlPreloadedResolver.
            // The XML string below references this DTD using the full path.
            resolver.Add(httpURI, stream);
            // Assign the resolver to the XmlReaderSettings.
            XmlReaderSettings settings = new XmlReaderSettings();
            settings.XmlResolver = resolver;
            settings.DtdProcessing = DtdProcessing.Parse;
            // To reference the DTD file, include its full URI path. 
            String strXml = @"<!DOCTYPE doc SYSTEM '" + uriString + "'>" +
            using (XmlReader reader = XmlReader.Create(new StringReader(strXml), settings))
                XDocument document = XDocument.Load(reader);
                // Output the content of the document object.  
                OutputTextBlock.Text = document.ToString();

Community Additions