WCF DispatchMessageInspector - 处理并使操作可用

时间:2011-09-23 19:51:19

标签: .net wcf

我想为我的WCF服务创建一个DispatchMessageInspector,它将在每个操作之前运行,执行一些处理,然后使该处理的结果可用于该操作。

创建MessageInspector很简单。但是,在我做了我需要做的事情后,我可以在哪里放置我创建的对象,以便每次操作中的代码都可以访问它?在MessageInspector中,我只是将它存储在OperationConext中,还是有更清洁的解决方案?

1 个答案:

答案 0 :(得分:4)

您通常将此信息存储在消息属性中,然后通过操作的操作上下文访问它(请参阅下面代码中的示例)。

public class StackOverflow_7534084
{
    const string MyPropertyName = "MyProp";
    [ServiceContract]
    public interface ITest
    {
        [OperationContract]
        string Echo(string text);
    }
    public class Service : ITest
    {
        public string Echo(string text)
        {
            Console.WriteLine("Information from the inspector: {0}", OperationContext.Current.IncomingMessageProperties[MyPropertyName]);
            return text;
        }
    }
    public class MyInspector : IEndpointBehavior, IDispatchMessageInspector
    {
        public void AddBindingParameters(ServiceEndpoint endpoint, BindingParameterCollection bindingParameters)
        {
        }

        public void ApplyClientBehavior(ServiceEndpoint endpoint, ClientRuntime clientRuntime)
        {
        }

        public void ApplyDispatchBehavior(ServiceEndpoint endpoint, EndpointDispatcher endpointDispatcher)
        {
            endpointDispatcher.DispatchRuntime.MessageInspectors.Add(this);
        }

        public void Validate(ServiceEndpoint endpoint)
        {
        }

        public object AfterReceiveRequest(ref Message request, IClientChannel channel, InstanceContext instanceContext)
        {
            request.Properties[MyPropertyName] = "Something from the inspector";
            return null;
        }

        public void BeforeSendReply(ref Message reply, object correlationState)
        {
        }
    }
    public static void Test()
    {
        string baseAddress = "http://" + Environment.MachineName + ":8000/Service";
        ServiceHost host = new ServiceHost(typeof(Service), new Uri(baseAddress));
        host.AddServiceEndpoint(typeof(ITest), new BasicHttpBinding(), "").Behaviors.Add(new MyInspector());
        host.Open();
        Console.WriteLine("Host opened");

        ChannelFactory<ITest> factory = new ChannelFactory<ITest>(new BasicHttpBinding(), new EndpointAddress(baseAddress));
        ITest proxy = factory.CreateChannel();
        Console.WriteLine(proxy.Echo("Hello"));

        ((IClientChannel)proxy).Close();
        factory.Close();

        Console.Write("Press ENTER to close the host");
        Console.ReadLine();
        host.Close();
    }
}