This post is now a part of computer history. See: Silverlight Death and Funeral
Sometime at least 5 years ago I needed to insert custom headers into outgoing messages from a WCF basic http client generated by slsvcutil.exe. The headers were expected on the server-side as proof that the Silverlight client was authenticated and trusted.
I spent many frustrating hours attempting to find a way of using custom Behaviors to automatically insert the headers. At the time I failed and assumed that behaviors were not supported by Silverlight clients. Instead, I used the technique of manually wrapping a context around the proxy to insert the headers. It's a cumbersome technique as you have to make the proxy call inside the using, which means a callback is needed from outside callers to keep the objects alive during the call. A skeleton of the technique looks like this:
// OLD-FASHIONED TECHNIQUE private static void CallWrapper(DemoAppClient client, Action callback) { using (OperationContextScope ocs = new OperationContextScope(client.Proxy.InnerChannel)) { OperationContext.Current.OutgoingMessageHeaders.Add(MessageHeader.CreateHeader("name", "namespace", 123456)); callback(); } }
One morning I suddenly decided I was sick of this ugly technique and went looking for a better way. I soon stumbled upon an article by Adil Mughal where he has minimal sample code that uses IEndpointBehavior and IClientMessageInspector to insert a custom header. This is exactly what I wanted to do all those years ago, but now I have no idea why I failed to discover how to use a behaviour back then. I'm not sure if it's because I was using older frameworks, or the documentation was unclear, or I was misdirected.
In any case, using a custom behavior is more elegant and the code is simpler because it avoids the need for a clumsy callback.
NOTE 24-Sep-2015
The article link above seems to be unreliable, so I have placed a copy of my custom behavior and custom inspector source code here:
http://www.orthogonal.com.au/computers/CustomBehavior.cs.txt
The behavior is added to the Silverlight client proxy by:
client = new ServiceClient(...); client.Endpoint.Behaviors.Add(new CustomBehavior(new HeaderData(id, ticket)));
The HeaderData class is something I used to pass a set of useful information down through the behaviour into the inspector. You can replace it with whatever data your custom classes might need.
NOTE 18-Oct-2018
I forgot to explain how to safely extract the header information in the server-side.
var inheads = OperationContext.Current.IncomingMessageHeaders; int index = inheads.FindHeader("name", "namespace"); if (index >= 0) { T data = inheads.GetHeader("name", "namespace"); }
Note that 'behavior' is US spelling used in code. 'Behaviour' is AU and GB spelling.
No comments:
Post a Comment