This post will cover the second method of extending a HealthVault data type. If you haven't read about the first method, please do so now. We'll wait.

In the first method, we had to deal with all the XML details ourselves, which made it a bit clumsy. This time, we'll encapsulate it in a class:

public class UserSpineStateExtension: HealthRecordItemExtension
{
    static readonly string ExtensionSource = "Fabrikam.UserSpineState";

    string m_spineState;

    public UserSpineStateExtension()
    {
    }

    public UserSpineStateExtension(string spineState)
                   :
base(ExtensionSource)
    {
        m_spineState = spineState;
        Source = ExtensionSource;
    }

    public string SpineState
    {
        get { return m_spineState; }
        set { m_spineState = value; }
    }

 

    protected override void ParseXml(System.Xml.XPath.IXPathNavigable extensionData)
    {
        XPathNavigator navigator = extensionData.CreateNavigator();
        XPathNavigator spineStateNode = navigator.SelectSingleNode("extension/SpineState");

        if (spineStateNode != null)
        {
            m_spineState = spineStateNode.Value;
        }
    }

    protected override void WriteXml(System.Xml.XmlWriter writer)
    {
        writer.WriteStartElement(
"SpineState");
        writer.WriteString(m_spineState);
        writer.WriteEndElement();
    }

    public static void RegisterExtensionHandler()
    {
        ItemTypeManager.RegisterExtensionHandler(ExtensionSource, typeof(UserSpineStateExtension), true);
    }
}

There are to constructors. The empty one is used by the system when it is creating an instance for us. The other one takes in the value that we want to store, and then sets the sources appropriately.

In ParseXml(), we find the appropriate node, pull out the value, and store it in our own variable. In WriteXml(), we add in the xml for our spine state value.

Note that the parse and write methods are not symmetrical. In the write one, we're already inside the <extension> tag, while in the parse one, we're up a level, pointing at the <extension> tag.

Finally, the RegisterExtensionHandler() method registers the type with the system so it knows where to find it. That needs to be called someplace before you try to use the type.

Using the custom extension

To use the extension is very simple. To add an extension, we use this code:

UserSpineStateExtension extension = new UserSpineStateExtension("Extended");
height.CommonData.Extensions.Add(extension);

And to get it back, here's what we write: 

foreach (HealthRecordItemExtension extension in height.CommonData.Extensions)
{
    UserSpineStateExtension userSpineState = extension as UserSpineStateExtension;
    if (userSpineState != null)
    {
       
string spineState = userSpineState.SpineState;
    }
}