Reputation: 3437
Is there any possibility to send some contextual information with each request / message? E.g. to automatically inject preferred language the user has been chosen in FrontEnd and to have it available for any request, without being necessary to send it parameter for each operation call.
Any idea is appreciated.
Upvotes: 1
Views: 231
Reputation: 3437
On client-side, add an endpoint behavior:
public class AddHeaderBehavior : IEndpointBehavior
{
public void Validate(ServiceEndpoint endpoint)
{
}
public void AddBindingParameters(ServiceEndpoint endpoint, BindingParameterCollection bindingParameters)
{
}
public void ApplyDispatchBehavior(ServiceEndpoint endpoint, EndpointDispatcher endpointDispatcher)
{
}
public void ApplyClientBehavior(ServiceEndpoint endpoint, ClientRuntime clientRuntime)
{
clientRuntime.MessageInspectors.Add(new HeaderMessageInspector());
}
}
public class HeaderMessageInspector: IClientMessageInspector
{
public object BeforeSendRequest(ref Message request, IClientChannel channel)
{
var typedHeader = new MessageHeader<string>("my custom info");
var untypedHeader = typedHeader.GetUntypedHeader("myKey", "myNamespace");
request.Headers.Add(untypedHeader);
return null;
}
public void AfterReceiveReply(ref Message reply, object correlationState)
{
}
}
On server-side, add a service behavior:
public class AddHeaderBehavior : Attribute, IServiceBehavior
{
public void AddBindingParameters(ServiceDescription serviceDescription, System.ServiceModel.ServiceHostBase serviceHostBase, System.Collections.ObjectModel.Collection<ServiceEndpoint> endpoints, BindingParameterCollection bindingParameters)
{
}
public void ApplyDispatchBehavior(ServiceDescription serviceDescription, System.ServiceModel.ServiceHostBase serviceHostBase)
{
foreach (var channelDispatcherBase in serviceHostBase.ChannelDispatchers)
{
var cDispatcher = (ChannelDispatcher)channelDispatcherBase;
foreach (var eDispatcher in cDispatcher.Endpoints)
{
eDispatcher.DispatchRuntime.MessageInspectors.Add(new OrganizationHeaderMessageInspector());
}
}
}
void IServiceBehavior.Validate(ServiceDescription serviceDescription, System.ServiceModel.ServiceHostBase serviceHostBase)
{
}
}
public class HeaderMessageInspector : IDispatchMessageInspector
{
public object AfterReceiveRequest(ref Message request, IClientChannel channel, InstanceContext instanceContext)
{
var header = request.Headers.GetHeader<string>("myKey", "myNamespace");
if (header != null)
{
OperationContext.Current.IncomingMessageProperties.Add("myKey", header);
}
return null;
}
public void BeforeSendReply(ref Message reply, object correlationState)
{
}
}
Upvotes: 1