How To Create A WCF Client Proxy Without Having a Deployed WCF Service

At work we are currently using a very very Agile process, which involves 1/4 hourly builds, which was all going brilliantly with a WPF solution and some Mocks and some NUnit test projects. Then we got to the point where we had to start building our WCF service and have the WPF project obtain a new service reference client proxy based on the newly built WCF service project. This is easily achieved using NANT and wiring up dependencies in a NANT script, but we were not in a position where we could actual deploy the WCF Service with every build, due to the fact that we are hosting the WCF service inside a Windows service.

We could have also automated this using InstallUtil.exe to install the service, but this would have added more complexity to an already complex build arrangement within our CI build server AKA “Cruise Control”. We could have done it, but we simply wanted to be able to create a new service reference client proxy. Normally what one would do would be to add a service reference within Visual Studio, something like the figure shown below:

ServiceReference

When you add a service reference using Visual Studio, you typically have to have, the service both deployed and running, and you then point the wizard at the deployed and running service address, which exposes some metadata which allows the wizard to be able to see information about the service. This will then create a bunch of items in Visual Studio, such as the following :

ref

One of the these generated files is the service reference client proxy. In this case it is called “Reference.cs”, which if we examine a small section of it, contains all the DataContract / ServiceContract class definitions.

dc

Which is fine, but as I stated above, what was needed for a continuous build environment (Cruise Control) was the ability to create this service reference client proxy class “Reference.cs” without a deployed service. Mmmm, how could we do that.

Well luckily there is a command line tool which can be run as part of a NANT script. This utility is called “svcutil.exe”, and has many options, which you can find using the svcutil.exe /? switch.

But to help you out here is what we had to do in order to duplicate the functionality provided by the Visual Studio wizard using just svcutil.exe.

It was a 2 phase operation, the phases are as follows:

Create WSDL from Dlls

You can create a WSDL by using the Dlls themselves, and then you can use the WSDL to create a service reference client proxy class. Here is how we did this.

Switch Description
/d: /d:<directory> Directory to create files in (default: current directory)
/reference: /reference:<file path> : Add the specified assembly to the set of assemblies used for resolving type references.

svcutil /directory:c:SOMEDIRECTORY “<SERVICE CONTRACT DLL PATH>”
/reference:”<DATACONTRACT DLL PATH>”

NOTE : You may have all your ServiceContract and DataContract classes all in one Dll, so in this case you would not need the /reference: switch, this is only need to link in additional Dlls.

Use WSDL to create WPF client service reference proxy class

Once we had a WSDL we could the use this to create the create a service reference client proxy class. We did this as follows:

Switch Description
/d: /d:<directory> Directory to create files in (default: current directory)
/l: Language C# or VB
/out: Name of output file
/noconfig Do not generate a client layer App.Config file
/s /serializable : Generate classes marked with the Serializable Attribute
/ct /collectionType: <type> : A fully-qualified or assembly-qualified name of the type to use as a collection data type when code is generated from schemas.
/ser: /serializer: Auto – Automatically select the serializer. This tries to use the Data Contract serializer and uses the XmlSerializer if that fails.
/tcv: /targetClientVersion:Version35 : Generate code that references functionality in .NET Framework assemblies 3.5 and before.
/n: /namespace:<string,string> : A mapping from a WSDL or XML Schema targetNamespace to a CLR namespace.
/edb /enableDataBinding : Implement the System.ComponentModel.INotifyPropertyChanged interface on all Data Contract types to enable data binding.

svcutil
/d:c:SOMEDIRECTORY
c:SOMEDIRECTORY*.wsdl c:SOMEDIRECTORY*.xsd
/l:C#
/out:Reference.cs
/noconfig
/s
/ct:System.Collections.Generic.List`1
/ser:Auto
/tcv:Version35
/n:*,<THE NAMESPACE TO USE>
/edb

And that was enough for us to generate a new WPF client service reference proxy class in an automated manner, without the need to have the WCF service deployed and running.

Hope this helps someone out there

About these ads

23 thoughts on “How To Create A WCF Client Proxy Without Having a Deployed WCF Service

  1. Nice blog Sacha! I encountered similar problems when switching to WCF. Having the service running and generating the proxy class was such a pain!

    We found it much easier to programatically generate the proxy class in c# code AND use generics. Now we have a handful of classes that can proxy any service we need to develop.

  2. Sure thing! My core design has two classes:

    1. internal class GeneralProxy : ClientBase

    GeneralProxy has the following method:

    public T Get()
    {
    return base.Channel;
    }

    2. public class GeneralClient : ICommunicationObject, IDisposable

    which has the instance method

    public T Service
    {
    get { return _genClient.Get(); }
    }

    GeneralClient has a GeneralProxy instance variable, some logic to ensure the channel is in a working state (if it becomes faulted, we restart it), and some configuration classes to parse connection strings from an app.config.

    In the simplest case, usage boils down to:

    IMyCustomService service = (new GeneralClient).Service;

    Of course, its recommended to tweak this based on needs/experience/debugging, etc.

    Hope this was useful :)

  3. Adam thanks for that. I see where you are coming from now. If you hang on a while and read and article I am working on which will be coming to codeproject soon, you will see how I do that. Its quite elegant approach actually.

    It to uses generic/lamdas, and is pretty cool.

  4. o0o0 I will for sure! This kind of WCF programming is going to form a crucial part of some software i am building at the moment, so i am certainly keen to see your approach :)

  5. sacha says:

    Adam

    Cool I will let you know when I finish the beast. Its a big article and has a lot of stuff in it.

    Its practically a working app.

  6. greg says:

    Hi Sacha,
    I too am interested in your generic proxy article. Is it posted yet? If so what is the link?… looking forward to it. Thanks!

  7. leon says:

    Sacha, another option is to use a IChannelFactory and instead of using a generated service, seperate shared objects (i.e. Interfaces/BusObj) in a seperate dll if they aren’t already.

    Both client/wcfproj reference this and you’ll know at build time wether they are in sync. Michelle has great examples of this at http://www.thatindigogirl.com/

    Ofcourse, you can still have metadata endpoints but since you own both ends of the app, perhaps you can do this instead.

  8. Jigisha says:

    Good one..

    Is it possible to create a application through .net framework 3.5 which send sms to ne mobile number.
    Please tell me asap…This project is very important for me.

  9. Ganesh Pai M V says:

    Hi Sacha,

    There is something I wanted to know… I am really new to this…

    The proxy class i generated has a ContractClient class inside, which describes the client (I suppose).

    I am getting the Message Contracts described in a peculiar way.. with the following attribute…

    [System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Advanced)]
    Also, the access modifier (public, in this case) is absent.

    further down, another description of the same message contract is present with a different set of parameters…

    Can I avoid this part and just have the simplest form of MessageContract being described inside? Is there any option that I have to use with svcutil for this?

    Would be grateful if you could advice me at the earliest…

    Thanks in advance

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s