21 September 2012
Contract-first web service development using WCF and .Net 4.5
Contract first web service development in .Net has always been hampered by the limited availability of any appropriate tooling. The new tool in Visual Studio 2012 is only a partial solution to this.
Why contract first?
The WSDL and XSD files that make up a SOAP service definition are a contract between the client and service. This contract describes the data and operations provided by the service and any expectations over their use. These contracts are supposed to be platform-independent and fully interoperable constructs that can be consumed by any client.
However, these contracts tend to give rise to long and highly structured XML documents that can be difficult to read and complex to work with. Developers often prefer to work with toolsets such as WCF where service contracts are generated automatically from object-based code. This “code-first” approach can be a useful abstraction that allows developers to create services in a familiar language without having to worry about the subtleties of schema development.
The problem is that this can be a leaky abstraction that undermines interoperability. Subtle .NET idiosyncrasies can creep into service definitions if they are automatically generated and these are often very difficult to pick up. Services can often suffer from subtle compatibility issues on different frameworks if they are deployed without any awareness of the underlying contracts. Code-first development can also give rise to more fragile contracts as there is less direct control over the WSDL and XSD files than define them.
Given that you cannot ignore the underlying contracts then it makes sense to take a "contract-first" approach to development where implementation code is generated directly from the WSDL and XSD schemas. This approach serves to de-couple contracts from any underlying development tools and can be helpful in a genuinely multi-platform environment that emphasises the need for interoperability. It also allows the service contract to be fully separated from any implementation code to facilitate easier design, testing and version control.
There’s nothing particularly new about contract first development. It was first proposed as part of Eiffel in the mid-1980s and is a big part of frameworks such as Java Spring. It’s never been a big part of the .Net world as WCF was been built around a code-based abstraction of service definitions.
The one drawback with contract-first development in .Net has been the lack of any reliable tooling as WCF is very much orientated around code-first development. The tooling that is available tends to be limited and requires a bit of tweaking to get working with Visual Studio 2012.
Visual Studio’s new Contract-First tool
Microsoft added a contract-first tool to version 4.5 of the .Net framework that can generate code from schemas as a build task in Visual Studio 2012. Note that this will only generate data contract classes so won’t do anything to generate stubs for service methods or endpoints. In this sense it doesn’t enable “full” data contract development, but it’s a start.
Rigging up a basic example in Visual Studio 2012 is pretty straightforward. In the Properties windows of a WCF Service Library project the WCF Options tab now has an option labelled "Enable XSD as a type definition language". This switches on the Contract First tool and also enables a set of more advanced options that control how data contracts are interpreted. Note that these options are only available for projects using version 4.5 of the .Net framework.
Once this option is switched on, data contracts will be generated at build time for schemas that are added directly into your project. Note that this does not work for remote schemas. The generated code will appears in a file called GeneratedXsdTypes.cs which appears in the obj\Debug\XsdGeneratedCode folder by default.
Using WSCF.blue for full contract-first development
Ideally, contract-first development should also include generating the full service interface, i.e. the messages as well as the types. WSCF.blue is an open source code generation tool that can be used to support this kind of “full” contract-first development. It is implemented as an add-in for Visual Studio and works on XSD schemas that have been added directly to a Visual Studio project.
The first step in creating a service is to generate a WSDL document from the XSD schema. This is initiated by right-clicking on your messages schema and selecting WSCF.blue -> Create WSDL Service Description. The wizard-based process that it uses is covered in detail by the product walk-though document but it does give you a lot of control over how operations are defined including the ability to specify fault contracts and message headers.
The tool does have a few limitations. For example, it only supports BasicHttpBinding and only lets you create a single end-point (or SVC file) where in reality you might want to support a variety of endpoints and bindings. The generated WSDLs also tend to require the occasional tweak in order to make them fully interoperable. For example, BizTalk requires a targetNamespace attribute to be added to the <imports> element of any generated WSDL.
Despite these relatively minor shortcomings, WSCF.blue does give rise to an uncluttered WSDL that does not contain much of the extra “baggage” you would normally see in a WSDL generated via WCF.
Once the WSDL in place you can generate the server-side stubs and data classes that will form the basis of your service implementation. This is done by right-clicking on the generated WSDL and selecting WSCF.blue -> Generate Web Service Code. The stubs can be generated either as partial classes, abstract base classes or skeleton methods that throw a NotImplementedException. The abstract classes are the most convenient option as they allow the underlying code to be re-generated more easily.
WSCF.blue can also be used to generate some proxy classes to consume the service, though you may wish to use the default Visual Studio tooling for this, if only to test that vanilla WCF clients can work with the generated WSDL.
Using WSCF.blue with Visual Studio 2012
The catch with WSCF.blue is that development on the project appears to have stalled and there hasn’t been a new release since October 2011. It can be made to work in Visual Studio 2012, but you’ll need to hack the add-on which was designed for an earlier version of Visual Studio:
- Go to the installation directory (C:\Program Files (x86)\thinktecture\WSCF.blue) and make a copy of the add-in file WSCF.blue.VS2010.addin, renaming it to WSCF.blue.VS2012.addin.
- Open the renamed file and change the <Version> element from 10.0 to 11.0.
- Open up Visual Studio 2012 and make sure that the installation directory is listed in the paths in Tools -> Options -> Environment-> Add-in Security
- Re-start Visual Studio and it will load the add-in.