WSDL issue generated from shared service contract in VS 2008
[Edit] I figured out a way to make it work, comments in the code.
I have dozens and soon you will have hundreds of workflows with the following contract:
[ServiceContract(Namespace = "http://schema.company.com/messages/")]
public interface IBasicContract<TRequest, TResponse>
where TRequest : class
where TResponse : class
{
[OperationContract]
[XmlSerializerFormat]
[ServiceKnownType(typeof(Aggregate))]
TResponse GetReport(TRequest inquiry);
[OperationContract]
[XmlSerializerFormat]
[ServiceKnownType(typeof(Aggregate))]
string GetRawReport(string guid);
[OperationContract]
[XmlSerializerFormat]
[ServiceKnownType(typeof(Aggregate))]
TResponse GetArchiveReport(string guid);
}
I created a generic implementation:
// v added
[ServiceBehavior(Namespace = "http://schema.company.com/messages/")]
// ^ added
public abstract class BasicWorkflowSvc<TRequest, TResponse, TWorkflow> : IBasicContract<TRequest, TResponse>
where TRequest : class
where TResponse : class
where TWorkflow : class
{
//...
}
The actual implementation looks like this:
[XmlSerializerFormat]
// v changed
[ServiceContract(Namespace = "http://services.company.com/messages/")]
// ^ changed
public interface IActualProductSvc : IBasicContract<ActualProductRq_Type, ActualProductRs_Type>
{
}
[ServiceBehavior(Namespace = "http://services.company.com/ActualProduct/v1.0")]
// v added
[MessageContract(WrapperNamespace = "http://services.company.com/ActualProduct/v1.0")]
// ^ added
public class ActualProductSvc : BasicWorkflowSvc<ActualProductRq_Type, ActualProductRs_Type, EF>, IActualProductSvc
{
//...
}
My problem is this: when I add a service reference to this project in another project, the generated code has additional (and useless) request and response types:
[GeneratedCode("System.ServiceModel", "3.0.0.0")]
[ServiceContract(Namespace = "http://services.company.com/ActualProduct/v1.0", ConfigurationName = "ActualProduct.IActualProductSvc")]
public interface IActualProductSvc
{
// CODEGEN: Generating message contract since the wrapper namespace (http://schema.company.com/messages/) of message GetReportRequest does not match the default value (http://services.company.com/ActualProduct/v1.0)
[OperationContract(Action = "http://schema.company.com/messages/IBasicContractOf_ActualProductRq_Type_ActualProductRs_Type/GetReport",
ReplyAction = "http://schema.company.com/messages/IBasicContractOf_ActualProductRq_Type_ActualProductRs_Type/GetReportResponse")]
[XmlSerializerFormat()]
[ServiceKnownType(typeof (Aggregate))]
GetReportResponse GetReport(GetReportRequest request);
// CODEGEN: Generating message contract since the wrapper namespace (http://schema.company.com/messages/) of message GetRawReportRequest does not match the default value (http://services.company.com/ActualProduct/v1.0)
[OperationContract(
Action = "http://schema.company.com/messages/IBasicContractOf_ActualProductRq_Type_ActualProductRs_Type/GetRawReport",
ReplyAction = "http://schema.company.com/messages/IBasicContractOf_ActualProductRq_Type_ActualProductRs_Type/GetRawReportResponse")]
[XmlSerializerFormat()]
[ServiceKnownType(typeof (Aggregate))]
GetRawReportResponse GetRawReport(GetRawReportRequest request);
// CODEGEN: Generating message contract since the wrapper namespace (http://schema.company.com/messages/) of message GetArchiveReportRequest does not match the default value (http://services.company.com/ActualProduct/v1.0)
[OperationContract(
Action = "http://schema.company.com/messages/IBasicContractOf_ActualProductRq_Type_ActualProductRs_Type/GetArchiveReport",
ReplyAction =
"http://schema.company.com/messages/IBasicContractOf_ActualProductRq_Type_ActualProductRs_Type/GetArchiveReportResponse")]
[XmlSerializerFormat()]
[ServiceKnownType(typeof (Aggregate))]
GetArchiveReportResponse GetArchiveReport(GetArchiveReportRequest request);
}
... with a bunch of wrappers:
[DebuggerStepThrough()]
[GeneratedCode("System.ServiceModel", "3.0.0.0")]
[MessageContract(WrapperName = "GetReport", WrapperNamespace = "http://schema.company.com/messages/", IsWrapped = true)]
public partial class GetReportRequest
{
[MessageBodyMember(Namespace = "http://schema.company.com/messages/", Order = 0)]
public ActualProductRq_Type inquiry;
public GetReportRequest()
{
}
public GetReportRequest(ActualProductRq_Type inquiry)
{
this.inquiry = inquiry;
}
}
Is there a way without manually deleting them so that these wrappers are not generated? The reason I'm asking is because they weren't created before I tried to extract a common contract from all workflows - there was no common interface with a different namespace and people who use these workflows complain about the need to update all references and then manually delete many files from the Reference.cs files.
I hate the WSDL importer in Visual Studio :(
a source to share
When you add or configure your client side service link, there is a checkbox that mentions something about generating Async methods.
If it is checked, try unchecking the checkbox and see if that removes the auto-generated request / response methods.
I had a similar problem over a year ago, so the solution is a bit hazy.
a source to share
Do you have the same problem if you use svcutil.exe to generate your proxy classes? If so, then this is not a VS2008 issue.
This problem does not surprise me. Generics in .NET are not macros. You would expect the WSDL generator to subtract the specific type used as the actual type parameter to instantiate the generic service contract. I think it's a non-trivial thing to ask for.
I recommend that you create a simple version of this issue and report it at http://connect.microsoft.com/visualstudio/ . Do a quick search first to see if it has already been reported. When you report it, post the report url as an edit to your question so others can vote for it.
a source to share