确保使用特定网络接口执行传出WCF请求

时间:2013-07-09 15:38:02

标签: c# wcf wcf-binding

我有一个远程WCF Web服务,我正在从我的应用程序连接。

应用程序可能在具有多个IP地址(或多个物理网络接口)的服务器上运行

我需要确保我可以控制哪个IP地址用于出站请求,而不是仅按照常规度量规则使用“首选”接口。

原因是该软件的多个副本将在同一台机器上运行,每个副本都绑定到一个特定的IP地址用于自己的操作,并且连接的远程服务需要知道哪个正在使用哪个稍后再连接回来(因为地址错误意味着连接到错误的服务)

使用旧版ASMX服务,可以通过覆盖为服务生成的分部类GetWebRequest(Uri uri)来完成。但我无法弄清楚如何使用WCF做到这一点。

unrelated SO post上,MVP @JohnSaunders建议通过接管WCF使用的整个传输机制来实现这一点。但我还没弄明白如何做到这一点。

3 个答案:

答案 0 :(得分:4)

这是一个棘手的问题,WCF似乎并不能很好地迎合这一问题。

.NET框架中唯一似乎直接处理客户端地址问题的组件是ServicePoint类。具体来说,它具有BindIPEndPointDelegate属性,可让您控制它如何选择客户端IP。该物业的文件包括:

  

某些负载平衡技术要求客户端使用特定的本地IP地址和端口号,而不是IPAddress.Any(或IPAddress.IPv6Any用于Internet协议版本6)和短暂端口。您的BindIPEndPointDelegate可以满足此要求。

因此,您应该能够在以下代码中修改与您的URL关联的服务点:

var servicePoint =  ServicePointManager.FindServicePoint(
    new Uri("http://contoso.com/service.svc"));

servicePoint.BindIPEndPointDelegate =
    (sp, remote, retryCount) => new IPEndPoint(address, portNumber);

显然,这种代码要求您的类能够了解客户端将要与之通信的协议和端点地址。将此逻辑设置为可应用于客户端通道的客户端行为可能是最合适的。

答案 1 :(得分:0)

您可以使用消息属性(HttpRequestMessageProperty)将HTTP标头添加到任何传出请求。您需要创建一个“范围”,在该范围中将属性添加到当前“操作上下文”,并将该属性与所需的所有标头一起附加到上下文的外发消息属性中。

请看这个:

how-to-override-getwebrequest-method-using-service-reference-instead-of-web-reference-in-wcf

答案 2 :(得分:0)

使用此: 新班级:

using System.Web.Services.Protocols;
using System.Windows.Forms;
using System;

public static class ExtensionMethods
{
    public static string ApplyServerURL(this SoapHttpClientProtocol service)
    {
        try
        {
            string name = service.GetType().Name;
            return string.Format("{0}{1}.svc", Settings.Instance.ServerAddress, name);
        }
        catch
        { return string.Empty; }
    }
}

现在是这样的:

YourService us = new YourService();
us.Url = us.ApplyServerURL();