在C#Web Service中使用WSDL文件中的主机名混淆

时间:2011-06-01 14:24:15

标签: c# web-services wsdl

我已经在部署在Windows服务EXE中的C#中创建了一个WCF Web服务,该服务主要以我想要的方式工作。我以自托管的方式使用它(不在IIS中)。

为了使WSDL文件可用于调用Java Web服务,我将ServiceMetadataBehavior添加到主机创建中。即:

ServiceHost host = new ServiceHost(typeof(MyService));
ServiceMetadataBehavior smb = new ServiceMetadataBehavior();
smb.HttpGetEnabled = true;
host.Description.Behaviors.Add(smb);
host.Open();

这一切都运行良好,直到我将服务移动到另一台具有不同主机名的服务器。当我连接到WSDL(http:// prod-server:55000 / MyService?wsdl)时,我看到开发服务器的主机名在WSDL中是硬编码的。

以下是浏览器中显示的WSDL片段:

<wsdl:definitions name="MyService" targetNamespace="http://tempuri.org/">
<wsdl:import namespace="MyProject.ServiceContracts" location="http://dev-server:55000/MyService?wsdl=wsdl0"/>
<wsdl:types/>

我检查了项目中的所有C#代码,并且开发服务器名称没有在任何地方进行硬编码。

在App.config文件中,我定义了以下内容:

<system.serviceModel>
<services>
  <service name="MyService">
    <endpoint address="http://localhost:55000/MyService" binding="basicHttpBinding"
      bindingConfiguration="" contract="MyProject.ServiceContracts.IMyInterface" />
    <host>
      <baseAddresses>
        <add baseAddress="http://localhost:55000/MyService" />
      </baseAddresses>
    </host>
  </service>
</services>

我希望这会导致localhost机器名被替换,但它仍然作为最初创建/部署服务的开发盒名称而存在。我错了吗?

我还研究了明确指定WSDL文件路径的可能性,但从我可以推断出的情况来看,只有在IIS上托管服务时才能这样做。

最后纯粹出于好奇,我想知道实际的WSDL文件是否真的被创建(我认为是磁盘上的物理文件)还是每次请求都动态呈现?

2 个答案:

答案 0 :(得分:3)

使用WCF,WSDL是动态生成的。

当我需要将WSDL作为文件发送给某人时,我在WCF 3 / 3.5服务上多次遇到此问题。通常我做的是保存文件(通常有3个,服务为wsdl,类型为xsd,.net类型为xsd,但您的里程可能不同),然后手动更新wsdl导入以引用另外两个文件相对于wsdl文件,然后发送所有三个文件。

wsdl:servicewsdl:portsoap:address仍将引用开发服务器,但大多数ws客户端库都会考虑这一点并允许开发人员配置端点。

答案 1 :(得分:3)

它是动态创建的,而不是每次调用IIRC,而是首先请求元数据端点。我不确定为什么你在非DEV机器上看到你的DEV服务器名称,但是,因为你只在你的端点地址中指定localhost,它将使用服务器的主网络地址来解析DNS。您可能需要考虑将useRequestHeadersForMetadataAddress行为添加到配置中,以便实际使用访问该服务的DNS。