WCF service exposing 2 endpoints on 2 different service contracts

Coral Doe picture Coral Doe · Dec 6, 2012 · Viewed 22.6k times · Source

I have an WCF service which I am trying to configure so that it exposes 2 endpoints, refering to different functionalities, under different URLs.

What I want to have is Service1, exposing methods A, B, C, and Service2, exposing methods D, E. I want to be able to browse both localhost/WebServiceName/Service1/Service.svc and localhost/WebServiceName/Service2/Service.svc.

Other applications referencing localhost/WebServiceName/Service1/Service.svc should see only the interface containing the methods A, B and C. They should not see anything regarding Service2 interface. And for Service2 likewise.

So far I have defined two interfaces in my WCF service, I_Service1 and I_Service2.

I have added two endpoints in my web.config like so:

<endpoint address="http://localhost/WebServiceName/Service1/" binding="wsHttpBinding" contract="WebServiceName.I_Service1" bindingConfiguration="Binding1" />
<endpoint address="http://localhost/WebServiceName/Service2/" binding="wsHttpBinding" contract="WebServiceName.I_Service2" bindingConfiguration="Binding2" />  

The suggestion of using full address in the enpoint comes from here: Multiple endpoints under IIS

But still, I can't browse localhost/WebServiceName/Service1/Service.svc. I receive:

Description: HTTP 404. The resource you are looking for (or one of its dependencies) could have been removed, had its name changed, or is temporarily unavailable.  Please review the following URL and make sure that it is spelled correctly. 

I can successfully browse localhost/WebServiceName/Service.svc and the wsdl includes methods A, B, C, D, E. But this should be wrong in the behaviour I want.

Is there something that I have missed?

UPDATE: Following this article http://allen-conway-dotnet.blogspot.ro/2011/09/exposing-multiple-binding-types-for.html I created two different contract services for those endpoints. But currently I am seing only Service1 when I browse it. Service2 apparently does not exist (HTTP 404 error related issues appear).

The configuration looks like:

<services>
   <service behaviorConfiguration="WebServiceName.ServiceBehavior1" name="WebServiceName.Service1">
    <endpoint address="" binding="wsHttpBinding" bindingConfiguration="Binding1"
     contract="WebServiceName.I_Service1" />
    <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
     <host>
       <baseAddresses>
         <add baseAddress="http://localhost/WebServiceName/Service1/Service.svc" />
       </baseAddresses>
     </host>
   </service>
   <service behaviorConfiguration="WebServiceName.ServiceBehavior2" name="WebServiceName.Service2">
    <endpoint address="" binding="wsHttpBinding" bindingConfiguration="Binding1"
     contract="WebServiceName.I_Service2" />
    <endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
     <host>
       <baseAddresses>
         <add baseAddress="http://localhost/WebServiceName/Service2/Service.svc" />
       </baseAddresses>
     </host>
   </service>
  </services>

Answer

Martin picture Martin · Dec 10, 2012

The way I've always done this is as follows: set a single "base address" for the service and specify the endpoint addresses as different text to append onto that base address...

 <service name="MyNamespace.MyService">
    <endpoint address="FirstEndpointAddress" binding="netTcpBinding"
      name="FirstEndpointName"
      contract="MyNamespace.FirstEndpointContract" />
    <endpoint address="SecondEndpointAddress" binding="netTcpBinding"
      name="SecondEndpointName"
      contract="MyNamespace.SecondEndpointContract" />
    <host>
      <baseAddresses>
        <add baseAddress="net.tcp://localhost:8733/MyBaseAddress" />
      </baseAddresses>
    </host>
  </service>

So in your case the base address might be localhost/WebServiceName and the endpoint address for endpoint 1 might be Service1/Service.svc. Likewise for endpoint 2 it might be Service2/Service.svc. I can see that you've followed advice to put the full address in the endpoint address, but all I can say is I've done it this way with success.