While WSDL is great to understand the syntax of a service – it’s operations, inputs and outputs - it’s not quite so good at gaining a semantic understanding. You can, however, provide textual context for a service and it’s operations through the <wsdl:documentation> element. The documentation element is allowed inside any WSDL 2.0 element and can contain any information you want.
It used to be so easy… using ASMX style services, you could partially control this element in code using the WebService and WebMethod attributes.
[WebService(Description="A description of this service...")]
public class CustomerService : System.Web.Services.WebService
{
[WebMethod(Description="A description of this operation...")]
public string HelloWorld()
{
return "Hello World";
}
}
And this would result in some WSDL like this.
<wsdl:definitions targetNamespace="http://tempuri.org/">
<wsdl:documentation>A description of this service...</wsdl:documentation>
...
<wsdl:portType name="CustomerServiceSoap">
<wsdl:operation name="HelloWorld">
<wsdl:documentation>A description of this operation...</wsdl:documentation>
<wsdl:input message="tns:HelloWorldSoapIn"/>
<wsdl:output message="tns:HelloWorldSoapOut"/>
</wsdl:operation>
</wsdl:portType>
...
</wsdl:definitions>
Unfortunately WCF doesn’t provide an out-of-the-box way of setting these elements – but not to worry you can publish custom WSDL content to include this information. I won’t restate the solution – just download the sample from the previous link and copy the WsdlDocumentationAttribute class into your code base.
You can then use the WsdlDocumentation attribute on your service contracts like this,
[ServiceContract]
[WsdlDocumentation("This service provides access to all of our customers. Information is sourced from a number of key sources including our central CRM and some of our legacy applications.")]
public interface ICustomerService
{
[OperationContract]
[WsdlDocumentation("This operation should be used to return a single, detailed view, of a customer.")]
[return: WsdlParamOrReturnDocumentation("The return element, GetCustomerResponse, contains a full, heirarchical, set of customer properties.")]
GetCustomerResponse GetCustomer(
[WsdlParamOrReturnDocumentation("The request element, GetCustomerRequest, contains the search criteria.")]GetCustomerRequest request);
}
And your WSDL will look like this,
<wsdl:definitions name="CustomerService" targetNamespace="http://tempuri.org/">
...
<wsdl:portType name="ICustomerService">
<wsdl:documentation>
<summary>
This service provides access to all of our customers. Information is sourced from a number of key sources including our central CRM and some of our legacy applications.
</summary>
</wsdl:documentation>
<wsdl:operation name="GetCustomer">
<wsdl:documentation>
<summary>
This operation should be used to return a single, detailed view, of a customer.
</summary>
<returns>
The return element, GetCustomerResponse, contains a full, heirarchical, set of customer properties.
</returns>
<param name="request">
The request element, GetCustomerRequest, contains the search criteria.
</param>
</wsdl:documentation>
...
</wsdl:operation>
</wsdl:portType>
...
</wsdl:definitions>
Which adds service, operation and input/output parameter descriptions to your WSDL.
Just like that.