Monthly Archives: April 2010

MVP again

Microsoft has been kind enough to give me the Microsoft Most Valuable Professional Award again. That’s the 8th year I can call myself an MVP. Thanks Microsoft for the recognition. As a token of my gratitude I’ve made some long overdue blog posts :).

WSDL and WCF: WCF requires <sp:OnlySignEntireHeadersAndBody>

If you’ve ever tried svcutil.exe to import WSDL which has doesn’t have <sp:OnlySignEntireHeadersAndBody> specified in the security policy, you’ll know that this doens’t fly. SvcUtil will tell you the the security policy is not supported. So why is this? I assume this has something to do with the a statement in paragraph 6.6 in the WS-SecurityPolicy specification, which states:

Setting the value of this property to ‘true’ mitigates against some possible re-writing attacks.

So apparently Microsoft decided that setting it to false is not a good idea, and decided not to support setting it to false (omitting the element).

Removing the ReplyTo element if it is anonymous

Talking to a non-WCF webservice is like a box of chocolates… you never know what you’re going to get. After solving the issue mentioned in my previous blog post, I had another problem. For some reason the service didn’t expect a <wsa:ReplyTo> element if the value was anonymous. Later on the other party adjusted the service so it actually worked as expected from WCF, but in the mean time I did write a message inspector to solve the problem. Besides solving the problem it also is a nice little example of a message inspector.

public class RemoveAnonymousReplyToMessageInspector : IClientMessageInspector
{
    private const string ReplyToNode = "ReplyTo";
    private const string WSAddressingNamespace = "http://www.w3.org/2005/08/addressing";

    public void AfterReceiveReply(ref System.ServiceModel.Channels.Message reply, object correlationState)
    {} // Not used for this scenario.

    public object BeforeSendRequest(ref System.ServiceModel.Channels.Message request, System.ServiceModel.IClientChannel channel)
    {
        // This method is called before the request is sent. You can read/manipulate the message here.
        // If you’re using signing or encryption, that is done after this, this is the
        // unencrypted/unsigned mesage.
        request = RemoveAnonymousReplyTo(request);
        return null;
    }

    private Message RemoveAnonymousReplyTo(Message message)
    {
        if (message.Headers.ReplyTo.IsAnonymous == true)
        {
            int index = message.Headers.FindHeader(ReplyToNode, WSAddressingNamespace);
            message.Headers.RemoveAt(index);
        }
        return message;
    }
}

To use this, you’ll need to create a class implementing the IEndpoint behavior and add the MessageInspector in ApplyClientBehavior, as follows:

public void ApplyClientBehavior(ServiceEndpoint endpoint, ClientRuntime clientRuntime)
{
    RemoveAnonymousReplyToMessageInspector inspector = new RemoveAnonymousReplyToMessageInspector();
    clientRuntime.MessageInspectors.Add(inspector);
}

Troubles with WCF and certificate signing

Recently I found myself trying to talk to a webservice using signing. It was a WCF calling a Java webservice using a certificate to sign messages. I kept getting the following exception message:
The incoming message was signed with a token which was different from what used to encrypt the body. This was not expected.
After a wild goose chase we finally figured out that the certificate was corrupted. Just installing the certificate again solved the issue.