FSharp.Data.Xsd augments the XML type provider from FSharp.Data with schema support.

The FSharp.Data.Xsd library can be installed from NuGet:
PM> Install-Package FSharp.Data.Xsd


The Schema parameter can be used (instead of Sample) to specify an XML schema. The value of the parameter can be either the name of a schema file or plain text like in the following example:

#r "System.Xml.Linq.dll"
#r "FSharp.Data.Xsd.dll"

open FSharp.Data

type Person = XmlProvider<Schema = """
  <xs:schema xmlns:xs="http://www.w3.org/2001/XMLSchema" 
    elementFormDefault="qualified" attributeFormDefault="unqualified">
    <xs:element name="person">
          <xs:element name="surname" type="xs:string"/>
          <xs:element name="birthDate" type="xs:date"/>

let turing = Person.Parse """

printfn "%s was born in %d" turing.Surname turing.BirthDate.Year

The properties of the provided type are derived from the schema instead of being inferred from samples.

Design notes

The design aims to follow the main ideas of F# Data, favoring ease of use and an open world approach to the shape of data. The XML Schema specification also provides a fair degree of openness which may be difficult to handle in some data binding tools; but in F# Data, when providing typed views on elements becomes too challenging, the underlying XElement is still available.

An important decision is to focus on elements and not on complex types; while the latter may be valuable in schema design, our goal is simply to obtain an easy and safe way to access xml data. In other words the provided types are not intended for domain modeling (it's one of the very few cases where optional properties are preferred to sum types). Hence, we do not provide types corresponding to complex types in a schema but only corresponding to elements (of course the underlying complex types still affect the resulting provided types but this happens only implicitly)

The XML Provider of F# Data infers a type from sample documents: an instance of InferedType represents elements having a structure compatible with the given samples. When a schema is available, we can use it (instead of samples) to derive an InferedType representing elements valid according to the definitions in the given schema.

The InferedType derived from a schema should be essentially the same as one inferred from a significant set of valid samples.

Adopting this perspective we can support XSD leveraging the existing functionalities. The implementation uses a simplified XSD model to split the task of deriving an InferedType:

  • element definitions in xsd files map to this simplified xsd model
  • instances of this xsd model map to InferedType.

Samples & documentation

The library comes with comprehensible documentation. It can include tutorials automatically generated from *.fsx files in the content folder. The API reference is automatically generated from Markdown comments in the library implementation.

  • Tutorial contains a further explanation of this library.

  • API Reference contains automatically generated documentation for all types, modules and functions in the library. This includes additional brief samples on using most of the functions.

Contributing and copyright

The project is hosted on GitHub where you can report issues, fork the project and submit pull requests. If you're adding a new public API, please also consider adding samples that can be turned into a documentation. You might also want to read the library design notes to understand how it works.

The library is available under Public Domain license, which allows modification and redistribution for both commercial and non-commercial purposes. For more information see the License file in the GitHub repository.

Multiple items
namespace FSharp

namespace Microsoft.FSharp
Multiple items
namespace FSharp.Data

namespace Microsoft.FSharp.Data
type Person = XmlProvider<...>

Full name: Index.Person
type XmlProvider

Full name: FSharp.Data.XmlProvider

<summary>Typed representation of a XML file.</summary>
       <param name='Sample'>Location of a XML sample file or a string containing a sample XML document.</param>
       <param name='SampleIsList'>If true, the children of the root in the sample document represent individual samples for the inference.</param>
       <param name='Global'>If true, the inference unifies all XML elements with the same name.</param>
       <param name='Culture'>The culture used for parsing numbers and dates. Defaults to the invariant culture.</param>
       <param name='Encoding'>The encoding used to read the sample. You can specify either the character set name or the codepage number. Defaults to UTF8 for files, and to ISO-8859-1 the for HTTP requests, unless `charset` is specified in the `Content-Type` response header.</param>
       <param name='ResolutionFolder'>A directory that is used when resolving relative file references (at design time and in hosted execution).</param>
       <param name='EmbeddedResource'>When specified, the type provider first attempts to load the sample from the specified resource
          (e.g. 'MyCompany.MyAssembly, resource_name.xml'). This is useful when exposing types generated by the type provider.</param>
       <param name='InferTypesFromValues'>If true, turns on additional type inference from values.
          (e.g. type inference infers string values such as "123" as ints and values constrained to 0 and 1 as booleans. The XmlProvider also infers string values as JSON.)</param>
       <param name='Schema'>Location of a schema file or a string containing xsd.</param>
val turing : XmlProvider<...>.Person

Full name: Index.turing
XmlProvider<...>.Parse(text: string) : XmlProvider<...>.Person

Parses the specified XML string
val printfn : format:Printf.TextWriterFormat<'T> -> 'T

Full name: Microsoft.FSharp.Core.ExtraTopLevelOperators.printfn
property XmlProvider<...>.Person.Surname: string
property XmlProvider<...>.Person.BirthDate: System.DateTime
property System.DateTime.Year: int
Fork me on GitHub