How config file would look at service end for multiple endpoint - wcf

i am working with wcf service application where svc file is created. now i want to design my service in such a way that people can connect to my service by http url and as well as by tcp url
so i would like to add three endpoint in my config one for wshttp, one for wsDualhttp and another one for tcp. so please someone give me sample config entry with 3 endpoints for wshttp, wsDualhttp and tcp.
in this case do i need to have three different mex endpoint for wshttp, wsDualhttp and tcp.
also tell me 3 url by which i can create proxy classes at client side. thanks

You could have something like this (assuming self-hosting, since only then can you really determine the full service addresses yourself - hosting in IIS, the service address(es) are most determined by where your .svc file lives):
<system.serviceModel>
<behaviors>
<serviceBehaviors>
<behavior name="Default">
<serviceMetadata httpGetEnabled="true"/>
</behavior>
</serviceBehaviors>
</behaviors>
<services>
<service name="YourNamespace.YourService" behaviorConfiguration="Default">
<endpoint name="Default"
address="http://YourServer/Services/MyService"
binding="basicHttpBinding"
contract="YourNamespace.IYourService"/>
<endpoint name="TCP"
address="net.tcp://YourServer/ServicesTCP/MyService"
binding="netTcpBinding"
contract="YourNamespace.IYourService"/>
<endpoint name="mex"
address="http://YourServer/Services/MyService/mex"
binding="mexHttpBinding"
contract="IMetadataExchange"/>
<endpoint name="Dual"
address="http://YourServer/Services/MyService/Dual"
binding="wsDualHttpBinding"
clientBaseAddress="http://localhost:8001/client/"
contract="YourNamespace.IYourDualService"/>
</service>
</services>
</system.serviceModel>
This would define three endpoints:
a HTTP endpoint at http://YourServer/Services/MyService for your service
a HTTP MEX endpoint at http://YourServer/Services/MyService/mex for the metadata exchange (service discoverability)
a Net.TCP endpoint at net.tcp://YourServer/ServicesTCP/MyService for your service
You could of course also use two base addresses to make things a bit easier in the config:
<system.serviceModel>
<behaviors>
<serviceBehaviors>
<behavior name="Default">
<serviceMetadata httpGetEnabled="true"/>
</behavior>
</serviceBehaviors>
</behaviors>
<services>
<service name="YourNamespace.YourService" behaviorConfiguration="Default">
<host>
<baseAddresses>
<add baseAddress="http://YourServer/Services"/>
<add baseAddress="net.tcp://YourServer/ServicesTCP"/>
</baseAddresses>
</host>
<endpoint name="Default"
address="MyService"
binding="basicHttpBinding"
contract="YourNamespace.IYourService"/>
<endpoint name="TCP"
address="MyService"
binding="netTcpBinding"
contract="YourNamespace.IYourService"/>
<endpoint name="mex"
address="MyService/mex"
binding="mexHttpBinding"
contract="IMetadataExchange"/>
</service>
</services>
</system.serviceModel>
This would configure the equivalent service endpoints.
The wsDualHttpBinding is different in that it requires at least a clientBaseAddress for the callback mechanism (the WCF service will call back your client to send back e.g. status messages) - so it needs some extra tweaks and it cannot really be bolted onto an existing service that works over wsHttpBinding - it needs to be done separately. But basically - it's still pretty much all the same thing....
Update: after reading up on the topic (it's not something I use very often), it does appear that duplex communication is indeed possible also using netTcpBinding, but only if you're self-hosting your service - IIS doesn't support duplex communication over netTcpBinding.
Creating a duplex service does still require extra steps and extra code - so you cannot really have a service that's both non-duplex using basicHttpBinding or wsHttpBinding and duplex at the same time. So it really doesn't make sense to have another endpoint in this example using the wsDualHttpBinding because that service either needs to be really duplex (then you can use wsDualHttpBinding and netTcpBinding) - or it's not duplex - then you can use basicHttpBinding, wsHttpBinding, netTcpBinding and a few more "exotic" bindings (like MSMQ, named pipes etc.)

Related

WCF unable to find netTcpBinding

I am trying to create a WCF service that is accessible through both webHttpBinding and netTcpBinding. I have been successful in getting the webHttpBinding to be accessible through a Java client and now I'm working on trying to get the netTcpBinding working.
I have set up the configuration like this;
<system.serviceModel>
<behaviors>
<endpointBehaviors>
<behavior name="httpBehavior">
<webHttp/>
</behavior>
</endpointBehaviors>
<serviceBehaviors>
<behavior name="">
<serviceMetadata httpGetEnabled="true" />
<serviceDebug includeExceptionDetailInFaults="true" />
</behavior>
</serviceBehaviors>
</behaviors>
<serviceHostingEnvironment multipleSiteBindingsEnabled="true" />
<services>
<service name="MR_Jukebox_Service.JukeboxService">
<host>
<baseAddresses>
<add baseAddress="http://localhost:8732/Design_Time_Addresses/MR_Jukebox_Service/"/>
<add baseAddress="net.tcp://localhost:8523/Design_Time_Addresses/MR_Jukebox_Service/net/"/>
</baseAddresses>
</host>
<endpoint address=""
behaviorConfiguration="httpBehavior"
binding="webHttpBinding"
contract="MR_Jukebox_Service.IJukeboxService" />
<endpoint address="mex"
binding="mexHttpBinding"
contract="MR_Jukebox_Service.IJukeboxService" />
<endpoint address="net.tcp://localhost:8523/Design_Time_Addresses/MR_Jukebox_Service/net"
binding="netTcpBinding"
bindingConfiguration=""
contract="MR_Jukebox_Service.IJukeboxService" />
</service>
</services>
</system.serviceModel>
In the same solution, I have a test application that I wish to connect to the netTcpBinding, I've right clicked on "Service References" and chosen "Add Service Reference...".
When I click on "Discover" it finds the service although says;
There was an error downloading 'http://localhost:8732/Design_Time_Addresses/MR_Jukebox_Service'.
The request failed with HTTP status 404: Not Found.
Metadata contains a reference that cannot be resolved: 'http://localhost:8732/Design_Time_Addresses/MR_Jukebox_Service'.
There was no endpoint listening at http://localhost:8732/Design_Time_Addresses/MR_Jukebox_Service that could accept the message. This is often caused by an incorrect address or SOAP action. See InnerException, if present, for more details.
The remote server returned an error: (404) Not Found.
If the service is defined in the current solution, try building the solution and adding the service reference again.
But I am also unable to see the netTcpBinding in order for me to create a service reference to it.
I was wondering whether anyone can see what I am doing wrong as its probably something rather simple, but due to my lack of experience with WCF haven't noticed.
Thanks for any help in advance.
Try changing your mex endpoint to this:
<endpoint address="mex"
binding="mexHttpBinding"
contract="IMetadataExchange" />
You were using your service's contract for the mex endpoint, which I don't believe will work.
You can set up a similar one for the NetTcpBinding:
<endpoint address="net.tcp://localhost:8523/Design_Time_Addresses/MR_Jukebox_Service/net/mex"
binding="mexTcpBinding"
contract="IMetadataExchange" />
I have been successful in getting the webHttpBinding to be accessible through a Java client and now I'm working on trying to get the netTcpBinding working.
Are you trying to get the netTcpBinding to work with a java client ? Because, netTcpBinding only works with a .net client.
NetTcpBinding is not designed for interop, it's designed for performance when both the server and client are .net

How to force a net.tcp mex endpoint (mexTcpBinding) to participate in port sharing?

I have a WCF service which is hosted as a Windows Service. We would like to enable a mex endpoint at the same address (but with a '/mex' suffix). I have been trying to do this (unsuccessfully) using the following configuration:
<system.serviceModel>
<services>
<service
name="MyCompany.MyService"
behaviorConfiguration="defaultServiceBehavior">
<host>
<baseAddresses>
<add baseAddress="net.tcp://localhost"/>
</baseAddresses>
</host>
<endpoint
address="MyService"
binding="netTcpBinding"
contract="MyCompany.IMyService"
bindingConfiguration="netTcpBindingConfig"
/>
<endpoint
address="MyService/mex"
binding="mexTcpBinding"
contract="IMetadataExchange"
/>
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="defaultServiceBehavior">
<serviceMetadata />
</behavior>
</serviceBehaviors>
</behaviors>
<bindings>
<netTcpBinding>
<binding name="netTcpBindingConfig" portSharingEnabled="true" />
</netTcpBinding>
</bindings>
</system.serviceModel>
When it runs, the service host throws an AddressAlreadyInUseException complaining that "There is already a listener on IP endpoint 0.0.0.0:808". This actually makes sense to me because the port sharing service has opened that port in order to serve the MyService endpoint along with any other services requesting to share that port on this machine.
So it seems that the mex endpoint wants exlusive access to port 808. I can work around this by tweaking the mex endpoint like so:
<endpoint
address="net.tcp://localhost:818/MyService/mex"
binding="mexTcpBinding"
contract="IMetadataExchange"
/>
This means that the mex endpoint now has its own exclusive port. The downside with this is that any other service which wants to expose a mex endpoint will also need a unique port for its mex endpoint. This makes it very unpredictable when looking for mex endpoints.
Is there a way to force the mex endpoint to participate in port sharing?
Two options:
The easy way: Change the entire binding for the mex point to netTcpBinding and have it reuse your bindingConfiguration. mexTCPBinding is only meant to be a convenience and is optional. If its not working for you, don’t use it.
The hard way: You can modify the mexTCPBinding to enable sharing. The only example I’ve seen is in code here: Link

WCF: Using multiple bindings for a single service

I have a WCF service (in 3.0) which is running fine with wsHttpBinding. I want to add netTcpBinding binding also to the same service. But the challenge that I am facing is in adding behaviorConfiguration.
How should I modify the following code to enable the service for both the bindings? Please help…
<service name="Lijo.Samples.WeatherService"
behaviorConfiguration="WeatherServiceBehavior">
<host>
<baseAddresses>
<add baseAddress="http://localhost:8000/ServiceModelSamples/FreeServiceWorld"/>
<add baseAddress="net.tcp://localhost:8052/ServiceModelSamples/FreeServiceWorld"/>
<!-- added new baseaddress for TCP-->
</baseAddresses>
</host>
<endpoint address=""
binding="wsHttpBinding"
contract="Lijo.Samples.IWeather" />
<endpoint address=""
binding="netTcpBinding"
contract="Lijo.Samples.IWeather" />
<!-- added new end point-->
<endpoint address="mex"
binding="mexHttpBinding"
contract="IMetadataExchange" />
</service>
</services>
<behaviors>
<serviceBehaviors>
<behavior name="WeatherServiceBehavior">
<serviceMetadata httpGetEnabled="true"/>
<serviceDebug includeExceptionDetailInFaults="False"/>
</behavior>
</serviceBehaviors>
</behaviors>
Please see the following to see further details
WCF using windows service
Thanks
Lijo
I don't completely understand what your problem or issue is - from what I'm understanding, you're unsure how to apply service behaviors?
Two things you need to consider:
a service behavior can be applied to the entire <service> tag - so these things like metadata support etc. will affect the service per se - regardless of which endpoint you connect to
an endpoint behavior can be applied to an endpoint, so that will affect only those endpoints that this behavior is applied to (and not others)
So in your case, the WeatherServiceBehavior will be applied to the service and thus affect all endpoints (e.g. no matter which endpoint your client connects to, it will have metadata support and debug details turned off).
So again: what exactly is your issue? Where are you "blocked" or what are you trying to do that doesn't work??
You should specify the address of the net tcp endpoint, at the endpoint level, not as a base address.
Also test if first with just nettcp binding to make sure that that works, before you try to configure for both.

What is the importance of IMetadataExchange in WCF?

What is the use and importance of IMetadataExchange in WCF?
I have the following app.config file in which I don't use IMetadataExchange endpoint, but I am still able to create my proxy client. I have read that if I don't use IMetadataExchange endpoint, AddServiceReference will not work because my service does not expose the metadata. How is it working without exposing IMetadataExchange endpoint?
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<system.serviceModel>
<behaviors>
<serviceBehaviors>
<behavior name="metaDataBehavior">
<serviceMetadata httpGetEnabled="true"/>
</behavior>
</serviceBehaviors>
</behaviors>
<services>
<service name ="WCFService.Services" behaviorConfiguration="metaDataBehavior">
<host>
<baseAddresses>
<add baseAddress="http://localhost:8090/Services/"/>
</baseAddresses>
</host>
<endpoint address="" binding="basicHttpBinding" contract="WCFService.IMathOperations"/>
</service>
</services>
</system.serviceModel>
</configuration>
ArsenMkrt has the formal answer. Put more simply:
If you don't have it, adding a service reference will not work
You should delete it from production servers, so that a hacker cannot add a service reference
To answer your question more specifically, you have this line on your service:
<service name ="WCFService.Services" behaviorConfiguration="metaDataBehavior">
Which points to this configuration
<behavior name="metaDataBehavior">
<serviceMetadata httpGetEnabled="true"/>
</behavior>
This may be why it still works, although I thought that you needed to specify the MEX endpoint.
IMetadataExchange Interface Exposes methods used to return metadata about a service.
When programming Windows Communication Foundation (WCF) services, it is useful to publish metadata about the service. For example, metadata can be a Web Services Description Language (WSDL) document that describes all of the methods and data types employed by a service. Returning metadata about an WCF service allows consumers of a service to easily create clients for the service.
The difference is:
<serviceMetadata httpGetEnabled="true"/>
allows you to retrieve metadata using the HTTP protocol.
<endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange" />
allows you to retrieve metadata using the ws-metadata protocol.
Just <serviceMetadata httpGetEnabled="true"/> works, but not all clients can call you (because they can't retrieve metadata to create a proxy).
The standard is to publish both.
See also ServiceMetadataBehavior Class (MSDN).
Without IMetadataExchange, a WCF service exposes the metadata information to the client, but WCF does not guarantee to expose the metadata because WCF default features to exposing the metadata to the client.
Exposing the metadata is done in a well-standardized way through IMetadataExchange. The IMetadataExchange interface follows the industry standard.

Why does my WCF service not respond my baseAddress setting in web.config?

I'm trying to learn how to build RESTful services with WCF by recreating the project on this blog post by Anthony Steele. He uses the following XML in his config to setup the endpoint for the service.
<host>
<baseAddresses>
<add baseAddress="http://localhost:8080/greeter"/>
</baseAddresses>
</host>
However, when I try to do the same thing in my ASP.NET 3.5 web site's web.config, I am unable to navigate to my service. Here is the XML I'm using:
<system.serviceModel>
<behaviors>
<serviceBehaviors>
<behavior name="GreeterBehavior">
<serviceMetadata httpGetEnabled="true"/>
<serviceDebug includeExceptionDetailInFaults="false"/>
</behavior>
</serviceBehaviors>
</behaviors>
<services>
<service behaviorConfiguration="GreeterBehavior" name="Greeter">
<host>
<baseAddresses>
<add baseAddress="http://localhost:49268/TestREST/webapi/services/greeter"/>
</baseAddresses>
</host>
<endpoint address="" binding="wsHttpBinding" contract="IGreeter">
<identity>
<dns value="localhost"/>
</identity>
</endpoint>
<endpoint address="mex" binding="mexHttpBinding" contract="IMetadataExchange"/>
</service>
</services>
</system.serviceModel>
I would imagine my configuration would allow me to navigate to http://localhost:49268/TestREST/webapi/services/greeter and see my service. All I get is a resource not found message - am I missing something?
Edit: Part of my problem was my binding was wsHttpBinding. Using webHttpBinding allowed me to use the service correctly - except, the baseAddress config section still has no effect.
My hunch is that the service endpoint is not being created successfully.
In the service "name" attribute you are not including the FQN (Fully Qualified Name) of the service type. Secondarily, in the endpoint "contract" attribute you are also not including the FQN to the contract type.
On the other hand, this MAY be a port issue. In order to be sure, try running the WcfTestClient.exe that is included in the Visual Studio 2008 distribution. If you can connect to http://localhost:49268/TestREST/webapi/services/greeter/mex, then you know it is not a port issue.
Supposing that you can connect via MEX, then try exercising some of the methods, which would presumably be mapped to http://localhost:49268/TestREST/webapi/services/greeter.
If you are operating on server, see some valuable details about HttpCfg.exe here:
WCF ServiceHost basicHttpBinding 503 error
If you need more details on WcfTestClient, look for them here:
Is it possible to make the WcfTestClient work for custom transport channels?
Just In Case: copy the sample verbatim and verify that it works as defined, including the config file, before making the slightest deviation from it.